Unitäre Operationen synthetisieren
Paketversionen
Der Code auf dieser Seite wurde mit den folgenden Anforderungen entwickelt. Wir empfehlen die Verwendung dieser oder neuerer Versionen.
qiskit[all]~=2.3.0
Eine unitäre Operation beschreibt eine normerhaltende Änderung an einem Quantensystem. Für Qubits wird diese Änderung durch eine dimensionale, komplexe Matrix beschrieben, deren Adjungierte der Inversen entspricht, d. h. .
Das Synthetisieren spezifischer unitärer Operationen in eine Menge von Quantengattern ist eine grundlegende Aufgabe, die zum Beispiel beim Entwurf und der Anwendung von Quantenalgorithmen oder beim Kompilieren von Quantenschaltkreisen verwendet wird.
Während eine effiziente Synthese für bestimmte Klassen von Unitären möglich ist – etwa solche, die aus Clifford-Gattern aufgebaut sind oder eine Tensorproduktstruktur besitzen – fallen die meisten Unitären nicht in diese Kategorien. Für allgemeine unitäre Matrizen ist die Synthese eine komplexe Aufgabe, deren Rechenaufwand exponentiell mit der Anzahl der Qubits wächst. Wenn du daher eine effiziente Zerlegung für die zu implementierende Unitäre kennst, wird diese wahrscheinlich besser als eine allgemeine Synthese sein.
Falls keine Zerlegung verfügbar ist, stellt das Qiskit SDK dir die Werkzeuge zur Verfügung, um eine zu finden. Beachte jedoch, dass dabei im Allgemeinen tiefe Schaltkreise entstehen, die sich möglicherweise nicht für den Betrieb auf verrauschten Quantencomputern eignen.
# Added by doQumentation — required packages for this notebook
!pip install -q numpy qiskit
import numpy as np
from qiskit import QuantumCircuit
U = 0.5 * np.array(
[[1, 1, 1, 1], [-1, 1, -1, 1], [-1, -1, 1, 1], [-1, 1, 1, -1]]
)
circuit = QuantumCircuit(2)
circuit.unitary(U, circuit.qubits)
<qiskit.circuit.instructionset.InstructionSet at 0x7fedb83e7a90>
Re-Synthese zur Schaltkreisoptimierung
Manchmal ist es sinnvoll, eine lange Folge von Ein- und Zwei-Qubit-Gattern neu zu synthetisieren, wenn sich die Länge dadurch reduzieren lässt. Der folgende Schaltkreis verwendet beispielsweise drei Zwei-Qubit-Gatter.
from qiskit import QuantumRegister, ClassicalRegister, QuantumCircuit
qreg_q = QuantumRegister(2, "q")
creg_c = ClassicalRegister(4, "c")
circuit = QuantumCircuit(qreg_q, creg_c)
circuit.h(qreg_q[0])
circuit.cx(qreg_q[0], qreg_q[1])
circuit.sx(qreg_q[1])
circuit.cz(qreg_q[0], qreg_q[1])
circuit.x(qreg_q[1])
circuit.x(qreg_q[0])
circuit.cx(qreg_q[0], qreg_q[1])
circuit.h(qreg_q[0])
circuit.draw("mpl")
Nach der erneuten Synthese mit dem folgenden Code wird jedoch nur noch ein einziges CX-Gatter benötigt. (Hier verwenden wir die Methode QuantumCircuit.decompose(), um die bei der Re-Synthese der Unitären verwendeten Gatter besser zu visualisieren.)
from qiskit.quantum_info import Operator
# compute unitary matrix of circuit
U = Operator(circuit)
# re-synthesize
better_circuit = QuantumCircuit(2)
better_circuit.unitary(U, range(2))
better_circuit.decompose().draw()
global phase: 6.2071
┌───────────────┐ ┌────────────────┐
q_0: ─┤ U(π/2,π/2,-π) ├────■────┤ U(π/2,-π,-π/2) ├─
┌┴───────────────┴─┐┌─┴─┐┌─┴────────────────┴┐
q_1: ┤ U(1.7229,π/2,-π) ├┤ X ├┤ U(π/2,0.15207,-π) ├
└──────────────────┘└───┘└───────────────────┘
Qiskits Funktion transpile führt diese Re-Synthese bei einem ausreichend hohen Optimierungslevel automatisch durch.
Nächste Schritte
- Sieh dir ein Beispiel zur Schaltkreiszerlegung im Tutorial Grover-Algorithmus an.
- Weitere Informationen zum Qiskit-Transpiler findest du im Abschnitt Transpilierung.