From a83774799af3eff065bd2fd72c134017bea4d7ba Mon Sep 17 00:00:00 2001 From: soranjh Date: Wed, 4 Dec 2024 11:29:28 -0500 Subject: [PATCH] add pl angles --- demonstrations/tutorial_qsvt_hardware.py | 60 ++++++++++++++---------- 1 file changed, 36 insertions(+), 24 deletions(-) diff --git a/demonstrations/tutorial_qsvt_hardware.py b/demonstrations/tutorial_qsvt_hardware.py index 9314e3f87f..03ca7aced8 100644 --- a/demonstrations/tutorial_qsvt_hardware.py +++ b/demonstrations/tutorial_qsvt_hardware.py @@ -26,22 +26,34 @@ - **Projection angles**: A list of angles that will determine the coefficients of the polynomial to be applied. - **Block encoding**: The strategy used to encode the Hamiltonian. We will use the :doc:`linear combinations of unitaries ` approach via the PennyLane :class:`~.qml.PrepSelPrep` operation. -Calculating angles is not a trivial task, but there are tools such as `pyqsp `_ that do the job for us. -For instance, to find the angles to apply the polynomial :math:`p(x) = -x + \frac{x^3}{2}+ \frac{x^5}{2},` we can run this code: - -.. code-block:: python - - from pyqsp.angle_sequence import QuantumSignalProcessingPhases - import numpy as np - - # Define the polynomial, the coefficients are in the order of the polynomial degree. - poly = np.array([0,-1, 0, 0.5, 0 , 0.5]) - - ang_seq = QuantumSignalProcessingPhases(poly, signal_operator="Wx") - -The angles obtained after execution are as follows: - +Calculating angles is not a trivial task, but we can use the PennyLane function :func:`~.pennylane.poly_to_angles` +to obtain them. There are also tools such as `pyqsp `_ that can do the job for us. +Let's try both tools to calculate the angles for applying the +polynomial :math:`p(x) = -x + \frac{x^3}{2}+ \frac{x^5}{2}`. + +The :func:`~.pennylane.poly_to_angles` function in PennyLane accepts the coefficients of the +polynomial, ordered from lowest to highest power, as input. We also need to the routine for which +the angles are computed, which is ``'QSVT'`` here. """ +import pennylane as qml +poly = [0, -1.0, 0, 1/2, 0, 1/2] +angles_pl = qml.poly_to_angles(poly, "QSVT") +print(angles_pl) + +###################################################################### +# To find the angles with ``pyqsp`` we can run this code: +# +# .. code-block:: python +# +# from pyqsp.angle_sequence import QuantumSignalProcessingPhases +# import numpy as np +# +# # Define the polynomial, the coefficients are in the order of the polynomial degree. +# poly = np.array([0,-1, 0, 0.5, 0 , 0.5]) +# +# ang_seq = QuantumSignalProcessingPhases(poly, signal_operator="Wx") +# +# The angles obtained after execution are as follows: ang_seq = [ -1.5115007723754004, @@ -53,10 +65,9 @@ ] ###################################################################### -# We use these angles to apply the polynomial transformation. -# However, we are not finished yet: these angles have been calculated following the "Wx" -# convention [#unification]_, while :class:`~.qml.PrepSelPrep` follows a different one. Moreover, the angles obtained in the -# context of QSP (the ones given by ``pyqsp``) are not the same as the ones we have to use in QSVT. That is why +# The angles obtained by ``pyqsp`` are in the +# context of QSP and are not the same as the ones we have to use in QSVT. Moreover, these angles have been calculated following the "Wx" +# convention [#unification]_, while :class:`~.qml.PrepSelPrep` follows a different one. That is why # we must transform the angles: import numpy as np @@ -73,11 +84,12 @@ def convert_angles(angles): return angles + update_vals -angles = convert_angles(ang_seq) -print(angles) +angles_pg = convert_angles(ang_seq) +print(angles_pg) ###################################################################### -# Using these angles, we can now start working with the template. +# Using the angles computed with :func:`~.pennylane.poly_to_angles` or ``pyqsp``, we can now start +# working with the template. # # QSVT on hardware # ----------------- @@ -113,8 +125,8 @@ def convert_angles(angles): block_encode = qml.PrepSelPrep(H, control=control_wires) projectors = [ - qml.PCPhase(angles[i], dim=2 ** len(H.wires), wires=control_wires + H.wires) - for i in range(len(angles)) + qml.PCPhase(angles_pl[i], dim=2 ** len(H.wires), wires=control_wires + H.wires) + for i in range(len(angles_pl)) ]