-
Notifications
You must be signed in to change notification settings - Fork 127
Description
What is your issue?
Hi,
I would like to optimize gates for a circuit using CircuitMPS since I would like to use the MPS to approximate the statevector.
I followed the example from https://github.com/jcmgray/quimb/blob/main/docs/tensor-circuit-mps.ipynb to build a CircuitMPS, but I opted to make the U3 parametrized so that I can optimize it. However, I get the error mentioned in the title. Perhaps, I am doing something wrong. Any help would be appreciated. Example code:
def gen_gates(N=64, x=0.1, depth=10, seed=42):
"""Generate a long range circuit that only slowly builds up entanglement.
Parameters
----------
N : int, optional
The number of qubits.
x : float, optional
The average angle magnitude of U3 rotations.
depth : int, optional
The number of fully entangling gate layers.
seed : int, optional
A random seed.
Yields
------
qtn.Gate
"""
rng = np.random.default_rng(seed)
qubits = list(range(N))
for _ in range(depth):
# random small single qubit rotations
for q in qubits:
yield qtn.Gate("U3", params=rng.normal(scale=x, size=3), qubits=[q],parametrize=True)
# random CZs between arbitrary qubit pairs
rng.shuffle(qubits)
for i in range(0, N, 2):
qa = qubits[i]
qb = qubits[i + 1]
yield qtn.Gate("CZ", params=(), qubits=[qa, qb])
circ = qtn.CircuitMPS(N=10, max_bond=200, cutoff=1e-16)
for gate in gen_gates(N=10, x=0.1, depth=10, seed=42):
if len(gate.params)==1:
circ.apply_gate(gate,contract=False)
else:
circ.apply_gate(gate)
and the error message:
KeyError Traceback (most recent call last)
File /opt/homebrew/anaconda3/envs/qiskit/lib/python3.10/site-packages/autoray/autoray.py:548, in get_lib_fn(backend, fn)
547 try:
--> 548 lib_fn = _FUNCS[backend, fn]
549 except KeyError:
KeyError: ('quimb', 'tensordot')
During handling of the above exception, another exception occurred:
AttributeError Traceback (most recent call last)
File /opt/homebrew/anaconda3/envs/qiskit/lib/python3.10/site-packages/autoray/autoray.py:515, in import_lib_fn(backend, fn)
514 # store the function!
--> 515 lib_fn = _FUNCS[backend, fn] = wrapper(getattr(lib, fn_name))
517 except AttributeError:
518 # check if there is a backup function (e.g. for older library version)
AttributeError: module 'quimb' has no attribute 'tensordot'
During handling of the above exception, another exception occurred:
ImportError Traceback (most recent call last)
Cell In[86], line 5
3 circ.apply_gate(gate,contract=False)
4 else:
----> 5 circ.apply_gate(gate)
File /opt/homebrew/anaconda3/envs/qiskit/lib/python3.10/site-packages/quimb/tensor/circuit.py:2058, in Circuit.apply_gate(self, gate_id, params, qubits, controls, gate_round, parametrize, *gate_args, **gate_opts)
2016 """Apply a single gate to this tensor network quantum circuit. If
2017 gate_round is supplied the tensor(s) added will be tagged with
2018 'ROUND_{gate_round}'. Alternatively, putting an integer first like
(...)
2047 default gate_opts.
2048 """
2049 gate = parse_to_gate(
2050 gate_id,
2051 *gate_args,
(...)
2056 parametrize=parametrize,
2057 )
-> 2058 self._apply_gate(gate, **gate_opts)
File /opt/homebrew/anaconda3/envs/qiskit/lib/python3.10/site-packages/quimb/tensor/circuit.py:2000, in Circuit._apply_gate(self, gate, tags, **gate_opts)
1997 G = self._backend_gate_cache[key]
1999 # apply the gate to the TN!
-> 2000 self.psi.gate(G, gate.qubits, tags=tags, **opts)
2002 # keep track of the gates applied
2003 self._gates.append(gate)
File /opt/homebrew/anaconda3/envs/qiskit/lib/python3.10/site-packages/quimb/tensor/tensor_1d.py:668, in TensorNetwork1DVector.gate(self, inplace, *args, **kwargs)
666 @functools.wraps(gate_TN_1D)
667 def gate(self, *args, inplace=False, **kwargs):
--> 668 return gate_TN_1D(self, *args, inplace=inplace, **kwargs)
File /opt/homebrew/anaconda3/envs/qiskit/lib/python3.10/site-packages/quimb/tensor/tensor_1d.py:265, in gate_TN_1D(tn, G, where, contract, tags, propagate_tags, info, inplace, cur_orthog, **compress_opts)
255 return tn.gate_nonlocal(
256 G,
257 where,
(...)
261 **compress_opts,
262 )
264 # can use generic gate method
--> 265 return TensorNetworkGenVector.gate(
266 tn,
267 G,
268 where,
269 contract=contract,
270 tags=tags,
271 propagate_tags=propagate_tags,
272 info=info,
273 inplace=inplace,
274 **compress_opts,
275 )
File /opt/homebrew/anaconda3/envs/qiskit/lib/python3.10/site-packages/quimb/tensor/tensor_arbgeom.py:530, in tensor_network_ag_gate(self, G, where, contract, tags, propagate_tags, which, info, inplace, **compress_opts)
527 tags.update(old_tags)
529 # perform the actual gating
--> 530 tn.gate_inds_(
531 G, inds, contract=contract, tags=tags, info=info, **compress_opts
532 )
534 # possibly add tags based on where the gate was applied
535 if propagate_tags == "register":
File /opt/homebrew/anaconda3/envs/qiskit/lib/python3.10/site-packages/quimb/tensor/tensor_core.py:4029, in tensor_network_gate_inds(self, G, inds, contract, tags, info, inplace, **compress_opts)
4022 raise ValueError(
4023 "For a parametrized gate acting on more than one site "
4024 "contract must be false to preserve the array shape."
4025 )
4027 if basic:
4028 # no splitting of the gate on its own involved
-> 4029 _tensor_network_gate_inds_basic(
4030 tn, G, inds, ng, tags, contract, isparam, info, **compress_opts
4031 )
4032 else:
4033 # possible splitting of gate itself involved
4034 if ng > 2:
File /opt/homebrew/anaconda3/envs/qiskit/lib/python3.10/site-packages/quimb/tensor/tensor_core.py:3627, in _tensor_network_gate_inds_basic(tn, G, inds, ng, tags, contract, isparam, info, **compress_opts)
3625 (ix,) = inds
3626 (t,) = tn.inds_get(ix)
-> 3627 t.gate(G, ix)
3628 t.add_tag(tags)
3629 return tn
File /opt/homebrew/anaconda3/envs/qiskit/lib/python3.10/site-packages/quimb/tensor/tensor_core.py:2658, in Tensor.gate(self, G, ind, preserve_inds, transposed, inplace)
2656 new_data = do("tensordot", G, t.data, ((0,), (ax,)))
2657 else:
-> 2658 new_data = do("tensordot", G, t.data, ((1,), (ax,)))
2660 if preserve_inds:
2661 # gated index is now first axis, so move it to the correct position
2662 perm = (*range(1, ax + 1), 0, *range(ax + 1, t.ndim))
File /opt/homebrew/anaconda3/envs/qiskit/lib/python3.10/site-packages/autoray/autoray.py:80, in do(fn, like, *args, **kwargs)
31 """Do function named fn on (*args, **kwargs), peforming single
32 dispatch to retrieve fn based on whichever library defines the class of
33 the args[0], or the like keyword argument if specified.
(...)
77 <tf.Tensor: id=91, shape=(3, 3), dtype=float32>
78 """
79 backend = _choose_backend(fn, args, kwargs, like=like)
---> 80 func = get_lib_fn(backend, fn)
81 return func(*args, **kwargs)
File /opt/homebrew/anaconda3/envs/qiskit/lib/python3.10/site-packages/autoray/autoray.py:550, in get_lib_fn(backend, fn)
548 lib_fn = _FUNCS[backend, fn]
549 except KeyError:
--> 550 lib_fn = import_lib_fn(backend, fn)
551 return lib_fn
File /opt/homebrew/anaconda3/envs/qiskit/lib/python3.10/site-packages/autoray/autoray.py:523, in import_lib_fn(backend, fn)
520 if backend_alt in _MODULE_ALIASES:
521 return import_lib_fn(backend_alt, fn)
--> 523 raise ImportError(
524 f"autoray couldn't find function '{fn}' for "
525 f"backend '{backend.replace('[alt]', '')}'."
526 )
528 return lib_fn
ImportError: autoray couldn't find function 'tensordot' for backend 'quimb'.