Skip to content

ImportError: autoray couldn't find function 'tensordot' for backend 'quimb' when building parametrized CircuitMPS #324

@ermalrrapaj

Description

@ermalrrapaj

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'.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions