qiskit-community / qiskit-machine-learning

Quantum Machine Learning
https://qiskit-community.github.io/qiskit-machine-learning/
Apache License 2.0
647 stars 316 forks source link

TorchConnector tutorial fails due to changes in Terra #84

Closed adekusar-drl closed 3 years ago

adekusar-drl commented 3 years ago

Information

What is the current behavior?

TorchConnector tutorial fails.

Steps to reproduce the problem

A script to reproduce the error:

import numpy as np
import matplotlib.pyplot as plt

from torch import Tensor
from torch.nn import Linear, CrossEntropyLoss, MSELoss
from torch.optim import LBFGS

from qiskit  import Aer, QuantumCircuit
from qiskit.utils import QuantumInstance
from qiskit.opflow import AerPauliExpectation
from qiskit.circuit import Parameter
from qiskit.circuit.library import RealAmplitudes, ZZFeatureMap
from qiskit_machine_learning.neural_networks import CircuitQNN, TwoLayerQNN
from qiskit_machine_learning.connectors import TorchConnector

if __name__ == '__main__':
    qi = QuantumInstance(Aer.get_backend('statevector_simulator'))

    num_inputs = 2
    num_samples = 20
    X = 2 * np.random.rand(num_samples, num_inputs) - 1
    y01 = 1 * (np.sum(X, axis=1) >= 0)  # in { 0,  1}
    y = 2 * y01 - 1  # in {-1, +1}

    X_ = Tensor(X)
    y01_ = Tensor(y01).reshape(len(y)).long()
    y_ = Tensor(y).reshape(len(y), 1)

    for x, y_target in zip(X, y):
        if y_target == 1:
            plt.plot(x[0], x[1], 'bo')
        else:
            plt.plot(x[0], x[1], 'go')
    plt.plot([-1, 1], [1, -1], '--', color='black')
    plt.show()

    # set up QNN
    qnn1 = TwoLayerQNN(num_qubits=num_inputs, quantum_instance=qi)

    # set up PyTorch module
    initial_weights = 0.1 * (2 * np.random.rand(qnn1.num_weights) - 1)
    model1 = TorchConnector(qnn1, initial_weights=initial_weights)

    # test with a single input
    r = model1(X_[0, :])
    print(r)

Fails with:

....
  File "...qiskit\circuit\parameterexpression.py", line 114, in bind
    bound_symbol_expr = self._symbol_expr.subs(symbol_values)
  File "symengine_wrapper.pyx", line 934, in symengine.lib.symengine_wrapper.Basic.subs
  File "symengine_wrapper.pyx", line 794, in symengine.lib.symengine_wrapper.get_dict
  File "symengine_wrapper.pyx", line 718, in symengine.lib.symengine_wrapper._DictBasic.add
  File "symengine_wrapper.pyx", line 529, in symengine.lib.symengine_wrapper.sympify
  File "symengine_wrapper.pyx", line 572, in symengine.lib.symengine_wrapper._sympify
  File "symengine_wrapper.pyx", line 495, in symengine.lib.symengine_wrapper.sympy2symengine
symengine.lib.symengine_wrapper.SympifyError: sympy2symengine: Cannot convert '0.058050297' (of type <class 'numpy.float32'>) to a symengine type.

What is the expected behavior?

The script should run without exceptions.

mtreinish commented 3 years ago

Hmm, interesting we should probably open a bug with symengine about this, they should be able to easily support single precision floats as a bind type. But int the meantime wesshould fix this in terra with a float cast on symbol values if it's a np float type.

mtreinish commented 3 years ago

I filed an issue with symengine here: https://github.com/symengine/symengine.py/issues/351

mtreinish commented 3 years ago

I pushed up a terra PR to fix this https://github.com/Qiskit/qiskit-terra/pull/6368 if you could test that this resolves the issue for the TorchConnector that would be great.

adekusar-drl commented 3 years ago

@mtreinish Thanks a lot! The patch fixes the problem. Waiting for the PR to unblock the CI.