qml.QNGOptimizer

I try to combine the quantum natural gradient descent on the variable fraction quantum circuit. The variational quantum circuit will be used to simulate as a classifier.

Using Optimizer: NesterovMomentumOptimizer is it is possible to work properly.

The following is the code for the relevant section:

@qml.qnode(dev)
def circuit(params, X, Y):
    for d in range(depth):
        for (w,x,p) in zip(range(n_qubit),X,params):
            qml.Rot.compute_decomposition(x[d*2]+p[d*3], x[d*2]+p[d*3+1], p[d*3+2], wires=w)
        for i in range(n_qubit):
            qml.CNOT(wires = [i, (i + 1) % n_qubit])
    H = [qml.PauliZ(position) for position in range(n_qubit)]
    return qml.expval(qml.Hamiltonian(Y,H))

Error reported during training:

> weights = opt.step(circuit, weights, input[0], labels[0])
> LinAlgError : Singular matrix![7E9%5B%7B0C%5B7VZIOD(K)A4S(3S|690x492](upload://bXVrjmQazDNCgx6VML3LPgIM0EX.png) 

During the reference to the source code I exported two relevant parameters and I did not find any exceptions to them.

def apply_grad(self, grad, args):
 grad_flat = np.array(list(_flatten(grad)))
        x_flat = np.array(list(_flatten(args)))
        print(self.metric_tensor.shape)
        print(grad_flat)
        x_new_flat = x_flat - self.stepsize * np.linalg.solve(self.metric_tensor, grad_flat)
        return unflatten(x_new_flat, args)

I need your help!

After testing, I found that the matrix self.metric_tensor has a value of 0 on the diagonal. What is the cause of this and how should it be solved?

Hi @Pengl, welcome to the forum!

A singular matrix (which is the error you’re getting) is a matrix where the determinant is zero.

It’s very hard to know without seeing some code that I can use to try to reproduce your problem. However here are some steps that you can follow:

  1. Make sure you’re using the latest version of PennyLane by using qml.about()
  2. Change your qnode (try first with a very simple ansatz) to see if you can avoid the singularity. If it does then you can make it more complex later.
  3. Try changing your data to see if you can avoid this singularity.
  4. Create a Minimum Example of your code which reproduces the error. This means stripping your problem of every bit of complexity so that it’s easier to analyze the source of the singularity.

If none of this helps then please post the Minimum Example you have built here. This should be a minimal version of your code which is however complete-enough that we can run it on our end and look into the source of the problem. Please also post your full error traceback.

I hope these steps can help you find a solution!

Thank you very much for your prompt answer, I tried to modify the contents of qng.py to make it run successfully.

def apply_grad(self, grad, args):
grad_flat = np.array(list(_flatten(grad)))
x_flat = np.array(list(_flatten(args)))
for ii in range(len(self.metric_tensor)):
self.metric_tensor[ii][ii] += 1e-6
x_new_flat = x_flat - self.stepsize * np.linalg.solve(self.metric_tensor, grad_flat)
return unflatten(x_new_flat, args)

He can run successfully but qml.metric_tensor can only load one piece of data at a time to build and pass in opt.step.

additional note: I used torch’s dataset building method I wanted to implement multi-type classification.

So each batch contains multiple data and cost_fn can be executed on multiple data, but qml.metric_tensor doesn’t seem to work, so I’d like to ask you guys for any suggestions to improve it.

It is working fine now and cost is dropping fine, but I just want to ask if there is anything I can do to optimize this.

Since this work is related to a work that we will release soon, I’m sorry for not showing the full code.

Hi @Pengl, no problem with not showing the code! We totally get that.

I’m not sure whether or not it will work but you could potentially try using a batch transform. You can try with the transform that seems more appropriate from our Transforms module.

Please let me know if this works for you or not, if not we can keep looking for a solution.