mitiq
mitiq copied to clipboard
User defined new package and circuit interface
Pre-Request Checklist
- [x] I checked to make sure that this feature has not already been requested.
Issue Description
Currently, if we want to interface mitiq with quantum packages that not listed in interfaces
submodule, we can take the following workaround:
import mypackage
mycircuit = mypackage.Circuit()
def to_cirq(mycircuit):
# ...
return cirq.Circuit
cirqcircuit = to_cirq(mycircuit)
def from_cirq(cirqcircuit):
# ...
return mypackage.Circuit()
def executor(cirqcircuit):
mycircuit = from_cirq(cirqcircuit)
return mypackage.run(mycircuit)
zne.execute_with_zne(cirqcircuit, executor)
However, this workflow is not straightforward and error-prone. Since we have defined from_cirq
and to_cirq
anyway, a better integration would be a hook to register these two methods to convert_to_mitiq
and convert_from_mitiq
. Then the above work flow will be simplified to
# after to and from mitiq registeration
mycircuit = mypackage.Circuit()
def executor(mycircuit):
return mypackage.run(mycircuit)
zne.execute_with_zne(mycircuit, executor)
Namely, just native user experience as the currently supported quantum software packages.
Proposed Solution
For now, the extension on convert_to_mitiq
and convert_from_mitiq
is impossible since the two function are hand coded if else branch with no user customized fallback. Therefore, a possible API for the hook and the corresponding implementation may be as follows:
# the proposed API
mitiq.interfaces.register_to_mitiq(package_name="mypackage", convert_function=to_cirq)
mitiq.interfaces.register_from_mitiq(package_name="mypackage", convert_function=from_cirq)
# the impl for convert_to_mitiq
def register_to_mitiq(package_name, convert_function):
global register_dict
register_dict[package_name] = convert_function
def convert_to_mitiq(circuit):
if
elif
# ...
else:
for package_name in register_dict:
if package_name in package:
conversion_function = register_dict[package_name]
break
else:
raise UnsupportedCircuitError
Additional References
Hello @refraction-ray, thank you for your interest in Mitiq! If this is a bug report, please provide screenshots and/or minimum viable code to reproduce your issue, so we can do our best to help get it fixed. If you have any questions in the meantime, you can also ask us on the Unitary Fund Discord.
Thanks @refraction-ray, we'll think about your proposal.
Honestly, the solution of your first code snippet doesn't look so bad to me.
It requires two lines of codes (manual insertion of from_cirq
and to_cirq
functions). The proposed solution also requires two lines of code:
mitiq.interfaces.register_to_mitiq(package_name="mypackage", convert_function=to_cirq)
mitiq.interfaces.register_from_mitiq(package_name="mypackage", convert_function=from_cirq)
Do you have strong arguments in favor of the second approach?
Thanks for your reply.
Do you have strong arguments in favor of the second approach?
Yes, consider the scenario of three parties (user, mypackage developer and mitiq developer) instead of two parties (user and mitiq developer). It is mypackage's developers responsibility to implement to_cirq
, from_cirq
and register these new interfaces in mitiq. All these implementation are in mypackage module (say mypackage/mitiq_interface.py
). So that users of mypackage can directly use the following code (regarding mypackage similar as packages with mitiq native support)
mycircuit = mypackage.Circuit()
def executor(mycircuit):
return mypackage.run(mycircuit)
zne.execute_with_zne(mycircuit, executor)
Ah, now I see the advantage thanks! Sounds interesting to me. I'll ping other Mitiq devs: @nathanshammah, @natestemen, @Misty-W
I personally really like the idea of allowing user-defined to_mitiq
/from_mitiq
functions that hook into our code. The solution proposed by Shixin seems like a good one.
I'd like to pick this one up, but if anyone wants to collaborate I'm certainly happy to get some new folks involved with Mitiq as well!
Tagging @unitaryfund/engineering .