tensorflow / quantum

Hybrid Quantum-Classical Machine Learning in TensorFlow
https://www.tensorflow.org/quantum
Apache License 2.0
1.79k stars 572 forks source link

TypeError: Invalid input argument for exponent. (tfq.convert_to_tensor) #712

Closed Shuhul24 closed 2 years ago

Shuhul24 commented 2 years ago

I have written following code:

def convert_to_circuit(image):
  values = tf.reshape(image, [-1])
  qubits = cirq.GridQubit.rect(4, 4)
  circuit = cirq.Circuit()
  for i in range(4):
    for j in range(4):
      k = (4 * i) + j
      circuit.append(cirq.H(cirq.GridQubit(i, j)))
      circuit.append(cirq.Rx(rads=values[k]).on(cirq.GridQubit(i, j)))
  return circuit

Here, the input in the function is a tensor. Basically, I have considered the image dataset into a tensor instead of a numpy.ndarray.

After this function, I wrote the following block of code and raised an error:

input_dis = [convert_to_circuit(x) for x in img]
input_disc = tfq.convert_to_tensor(input_dis)

The error is:

---------------------------------------------------------------------------
TypeError                                 Traceback (most recent call last)
[<ipython-input-58-49439858826a>](https://localhost:8080/#) in <module>
      3 # print(type(input_dis))
      4 # print(type(input_dis[0]))
----> 5 input_disc = tfq.convert_to_tensor(input_dis)

10 frames
[/usr/local/lib/python3.7/dist-packages/tensorflow_quantum/core/serialize/serializer.py](https://localhost:8080/#) in _symbol_extractor(x)
     88     """This is the second extractor for above."""
     89     if not isinstance(x, (numbers.Real, sympy.Expr)):
---> 90         raise TypeError("Invalid input argument for exponent.")
     91 
     92     if isinstance(x, numbers.Real):

TypeError: Invalid input argument for exponent.

Can you please help me out why is this happening? The only change I did was taking input the tensor instead of numpy.ndarray.

lockwo commented 2 years ago

You can't use a tensor to specify rotations, it must be a numbers.Real or sympy.Expr. Simply cast the tensor to a numpy array to solve this problem. This worked for me (I actually don't know whether casting to numpy as a single value or as an array is more efficient since I'm not sure what that looks like in the underlying memory operations, but may be worth considering if you iterate a lot over this function), where the key difference is rads=values[k].numpy():

import tensorflow_quantum as tfq
import cirq
import tensorflow as tf

def convert_to_circuit(image):
  values = tf.reshape(image, [-1])
  qubits = cirq.GridQubit.rect(4, 4)
  circuit = cirq.Circuit()
  for i in range(4):
    for j in range(4):
      k = (4 * i) + j
      circuit.append(cirq.H(cirq.GridQubit(i, j)))
      circuit.append(cirq.Rx(rads=values[k].numpy()).on(cirq.GridQubit(i, j)))
  return circuit

img = tf.random.uniform(shape=[1, 16])
input_dis = [convert_to_circuit(x) for x in img]
input_disc = tfq.convert_to_tensor(input_dis)
lockwo commented 2 years ago

I believe https://github.com/tensorflow/quantum/issues/713 resolved this.

Shuhul24 commented 2 years ago

Thanks for this as well !