Infleqtion / client-superstaq

https://superstaq.readthedocs.io
Apache License 2.0
84 stars 19 forks source link

Proxy benchmarks simulate entire system to generate circuits #63

Open ausbin opened 1 year ago

ausbin commented 1 year ago

The Vanilla QAOA, Fermionic-Swap QAOA, and VQE benchmarks seem to simulate the whole system to generate a circuit:

https://github.com/SupertechLabs/SupermarQ/blob/bc06e85dff2033b9ab74207d7e4540699b648602/supermarq/benchmarks/qaoa_vanilla_proxy.py#L99 https://github.com/SupertechLabs/SupermarQ/blob/bc06e85dff2033b9ab74207d7e4540699b648602/supermarq/benchmarks/qaoa_fermionic_swap_proxy.py#L122 https://github.com/SupertechLabs/SupermarQ/blob/bc06e85dff2033b9ab74207d7e4540699b648602/supermarq/benchmarks/vqe_proxy.py#L120-L121

I get why this is the case β€” to choose a realistic set of parameters to the ansatz in the proxy circuit instead of making something up. However, it seems to me like this means the current implementation cannot generate proxy circuits for a variational run with quantum advantage.

Just to give an example, if you try to instantiate a 64-bit Vanilla QAOA circuit with QAOAVanillaProxy(64).circuit(), you'll probably get something like this:

  File "/home/aadams80/.local/lib/python3.9/site-packages/supermarq/benchmarks/qaoa_vanilla_proxy.py", line 40, in __init__
    self.params = self._gen_angles()
  File "/home/aadams80/.local/lib/python3.9/site-packages/supermarq/benchmarks/qaoa_vanilla_proxy.py", line 114, in _gen_angles
    params, cost = self._get_opt_angles()
  File "/home/aadams80/.local/lib/python3.9/site-packages/supermarq/benchmarks/qaoa_vanilla_proxy.py", line 105, in _get_opt_angles
    out = scipy.optimize.minimize(f, init_params, method="COBYLA")
  File "/home/aadams80/.local/lib/python3.9/site-packages/scipy/optimize/_minimize.py", line 705, in minimize
    res = _minimize_cobyla(fun, x0, args, constraints, callback=callback,
  File "/home/aadams80/.local/lib/python3.9/site-packages/scipy/optimize/_cobyla_py.py", line 34, in wrapper
    return func(*args, **kwargs)
  File "/home/aadams80/.local/lib/python3.9/site-packages/scipy/optimize/_cobyla_py.py", line 273, in _minimize_cobyla
    xopt, info = cobyla.minimize(calcfc, m=m, x=np.copy(x0), rhobeg=rhobeg,
  File "/home/aadams80/.local/lib/python3.9/site-packages/scipy/optimize/_cobyla_py.py", line 261, in calcfc
    f = fun(np.copy(x), *args)
  File "/home/aadams80/.local/lib/python3.9/site-packages/supermarq/benchmarks/qaoa_vanilla_proxy.py", line 99, in f
    probs = supermarq.simulation.get_ideal_counts(circ)
  File "/home/aadams80/.local/lib/python3.9/site-packages/supermarq/simulation.py", line 9, in get_ideal_counts
    for i, amplitude in enumerate(circuit.final_state_vector(ignore_terminal_measurements=True)):
  File "/home/aadams80/.local/lib/python3.9/site-packages/cirq/circuits/circuit.py", line 1129, in final_state_vector
    return final_state_vector(
  File "/home/aadams80/.local/lib/python3.9/site-packages/cirq/sim/mux.py", line 166, in final_state_vector
    result = sparse_simulator.Simulator(dtype=dtype, seed=seed).simulate(
  File "/home/aadams80/.local/lib/python3.9/site-packages/cirq/sim/simulator.py", line 491, in simulate
    return self.simulate_sweep(
  File "/home/aadams80/.local/lib/python3.9/site-packages/cirq/sim/simulator.py", line 506, in simulate_sweep
    return list(self.simulate_sweep_iter(program, params, qubit_order, initial_state))
  File "/home/aadams80/.local/lib/python3.9/site-packages/cirq/sim/simulator_base.py", line 328, in simulate_sweep_iter
    for step_result in self._core_iterator(circuit=prefix, sim_state=sim_state):
  File "/home/aadams80/.local/lib/python3.9/site-packages/cirq/sim/simulator_base.py", line 220, in _core_iterator
    protocols.act_on(op, sim_state)
  File "/home/aadams80/.local/lib/python3.9/site-packages/cirq/protocols/act_on_protocol.py", line 153, in act_on
    result = arg_fallback(action, qubits=qubits, allow_decompose=allow_decompose)
  File "/home/aadams80/.local/lib/python3.9/site-packages/cirq/sim/simulation_product_state.py", line 109, in _act_on_fallback_
    op_args_opt = op_args_opt.kronecker_product(self.sim_states[q])
  File "/home/aadams80/.local/lib/python3.9/site-packages/cirq/sim/simulation_state.py", line 172, in kronecker_product
    args._state = self._state.kron(other._state)
  File "/home/aadams80/.local/lib/python3.9/site-packages/cirq/sim/state_vector_simulation_state.py", line 108, in kron
    target_tensor = transformations.state_vector_kronecker_product(
  File "/home/aadams80/.local/lib/python3.9/site-packages/cirq/linalg/transformations.py", line 531, in state_vector_kronecker_product
    return np.outer(t1, t2).reshape(t1.shape + t2.shape)
  File "<__array_function__ internals>", line 180, in outer
  File "/home/aadams80/.local/lib/python3.9/site-packages/numpy/core/numeric.py", line 942, in outer
    return multiply(a.ravel()[:, newaxis], b.ravel()[newaxis, :], out)
numpy.core._exceptions._ArrayMemoryError: Unable to allocate 1.00 PiB for an array with shape (268435456, 262144) and data type complex128
vtomole commented 1 year ago

Thanks for bringing this to our attention @ausbin. The best path forward is to implement these variational proxy benchmarks as full application benchmarks. We'll keep this issue open until we've done so.

perlinm commented 1 year ago

@ausbin are you asking to get the ansatz circuit with symbolic (or random) parameters? That might be reasonable for SupermarQ to do, although the performance of a QAOA circuit with random parameters is of course going to be poor.

ausbin commented 1 year ago

Sorry if I was unclear, @perlinm β€” as a user, I am asking to be able to generate an instance of e.g. QAOA without Supermarq trying to allocate a petabyte of memory.

I ran into this because I was using Supermarq benchmarks to test some compiler passes, and in this case, the particular values of the ansatz angles weren't important. So I just assigned them some random values: ausbin/Supermarq@cc4343b2337eb4bebeace3e119eb928bde806a5d. I didn't make that a PR because yeah, I agree random angles may not be suitable for other usecases (like benchmarking hardware)

perlinm commented 1 year ago

I agree that we should make this possible in SupermarQ. If you have an implementation in mind, we would certainly appreciate a PR πŸ™‚