Bruchgatter
Der Code auf dieser Seite wurde unter Berücksichtigung der folgenden Anforderungen entwickelt. Wir empfehlen die Verwendung dieser oder neuerer Versionen.
qiskit[all]~=2.5.2 qiskit-ibm-runtime~=0.47.0
Auf dieser Seite werden zwei neue Gattertypen vorgestellt, die von der IBM Quantum® QPU-Flotte unterstützt werden. Diese gebrochenen Gatter werden auf den Heron QPUs in Form von unterstützt:
- für
- für jede
Auf dieser Seite werden die Anwendungsfälle erörtert, in denen die Implementierung von fraktionalen Gattern die Effizienz Ihrer Arbeitsabläufe verbessern kann, und es wird erläutert, wie diese Gatter auf IBM Quantum QPUs verwendet werden können.
Verwendung von Bruchteil-Gates
Intern funktionieren diese Bruchteilgatter, indem sie direkt eine und Rotation für einen beliebigen Winkel ausführen. Die Verwendung des „ “-Gatters kann die Dauer und Fehlerquote bei Einzelqubit-Rotationen mit beliebigem Winkel um bis zu den Faktor zwei reduzieren. Die direkte Ausführung der Gate-Rotation „ “ vermeidet die Zerlegung in mehrere CZGate Objekte und reduziert so ebenfalls die Dauer und Fehler einer Schaltung. Dies ist besonders nützlich für Schaltungen, die viele Einzel- und Zwei-Qubit-Rotationen enthalten, beispielsweise bei der Simulation der Dynamik eines Quantensystems oder bei der Verwendung eines Variationsansatzes mit vielen Parametern.
Diese Gattertypen sind zwar in der Bibliothek der Standardgatter enthalten, über die ein System verfügen QuantumCircuit kann, sie können jedoch nur auf bestimmten QPUs von IBM Quantum verwendet werden, die mit dem auf gesetzten use_fractional_gates Flag True geladen werden müssen (siehe unten). Dieses Flag sorgt dafür, dass Bruchteilsgatter in die Backend-Implementierung Target des Transpilers aufgenommen werden.
service = QiskitRuntimeService()
backend = service.backend('ibm_torino', use_fractional_gates=True)Dieses Codebeispiel demonstriert die Verwendung von fraktionierten Gattern im Rahmen eines Arbeitsablaufs, der die Dynamik einer Ising-Kette mit Hilfe von fraktionierten Gattern simuliert. Die Dauer der Schaltung wird dann mit einem Backend verglichen, das keine gebrochenen Gatter verwendet.
Der Fehlerwert, der in der Target eines Backends mit aktivierten fraktionalen Gattern gemeldet wird, ist lediglich eine Kopie des Gegenstücks des nicht-fraktionalen Gatters (das möglicherweise nicht dasselbe ist). Der Grund dafür ist, dass die Meldung von Fehlerquoten bei den fraktionierten Gates noch nicht unterstützt wird.
Da jedoch die Gatterzeit von fraktionierten und nicht-fraktionierten Gattern gleich ist, ist es eine vernünftige Annahme, dass ihre Fehlerraten vergleichbar sind - vor allem, wenn die dominierende Fehlerquelle in einer Schaltung auf Relaxation zurückzuführen ist.
from qiskit import QuantumCircuit
from qiskit.circuit import Parameter
from qiskit.transpiler import generate_preset_pass_manager
from qiskit.visualization.timeline import draw as draw_timeline, IQXSimple
from qiskit_ibm_runtime import QiskitRuntimeService
num_qubits = 5
num_time_steps = 3
rx_angle = 0.1
rzz_angle = 0.1
ising_circuit = QuantumCircuit(num_qubits)
for i in range(num_time_steps):
# rx layer
for q in range(num_qubits):
ising_circuit.rx(rx_angle, q)
for q in range(1, num_qubits - 1, 2):
ising_circuit.rzz(rzz_angle, q, q + 1)
# 2nd rzz layer
for q in range(0, num_qubits - 1, 2):
ising_circuit.rzz(rzz_angle, q, q + 1)
ising_circuit.barrier()
ising_circuit.draw("mpl")Output:
Geben Sie zwei Backend-Objekte an: eines mit aktivierten und eines mit deaktivierten Fractional Gates, und transpilieren Sie dann beide.
service = QiskitRuntimeService()
backend_name = service.least_busy(operational=True, simulator=False).name
backend_fractional = service.backend(backend_name, use_fractional_gates=True)
backend_conventional = service.backend(
backend_name, use_fractional_gates=False
)
pm_fractional = generate_preset_pass_manager(
optimization_level=3, backend=backend_fractional, scheduling_method="alap"
)
pm_conventional = generate_preset_pass_manager(
optimization_level=3,
backend=backend_conventional,
scheduling_method="alap",
)
ising_circuit_fractional = pm_fractional.run(ising_circuit)
ising_circuit_conventional = pm_conventional.run(ising_circuit)Zeigen Sie die Zeitachse der Schaltung mit den beiden Gattertypen an.
# Draw timeline of circuit with conventional gates
draw_timeline(
ising_circuit_conventional,
idle_wires=False,
target=backend_conventional.target,
time_range=(0, 500),
style=IQXSimple(),
)Output:
# Draw timeline of circuit with fractional gates
draw_timeline(
ising_circuit_fractional,
idle_wires=False,
target=backend_fractional.target,
time_range=(0, 500),
style=IQXSimple(),
)Output:
Winkelbeschränkungen
Für das Zwei-Qubit- -Gatter können auf der Hardware von IBM Quantum nur Winkel zwischen und ausgeführt werden. Enthält eine Schaltung „ “-Gatter mit einem Winkel außerhalb dieses Bereichs, wird dies von der Standard-Transpilations-Pipeline in der Regel durch eine entsprechende Schaltungstransformation (im Pass FoldRzzAngle ) korrigiert. Für jedes „ “-Gatter, das ein oder mehrere Parameter„s“ enthält, geht der Transpiler jedoch davon aus, dass diesen Parametern zur Laufzeit Winkel innerhalb dieses Bereichs zugewiesen werden. Der Auftrag schlägt fehl, wenn einer der im „ PUB “ angegebenen Parameterwerte, der an den „ IBM Quantum Compute Service“ übermittelt wurde, außerhalb dieses Bereichs liegt.
Wo fraktionierte Gates verwendet werden sollten
In der Vergangenheit waren die auf IBM Quantum QPUs verfügbaren Basisgatter CZ, X, RZ, SX, und **ID**die nicht in der Lage sind, Schaltungen mit Ein- und Zwei-Qubit-Rotationen, die keine Vielfachen von sind, effizient darzustellen. Beispielsweise muss ein -Gatter, wenn es transpiliert wird, in eine Reihe von - und -Gattern zerlegt werden, wodurch eine Schaltung mit zwei Gattern von endlicher Dauer anstelle von einem entsteht.
Wenn Zwei-Qubit-Rotationen, wie z. B. ein -Gatter, transponiert werden, erfordert die Zerlegung ebenfalls zwei CZ gatter und mehrere Ein-Qubit-Gatter, was die Schaltungstiefe erhöht. Diese Zerlegungen sind im folgenden Code dargestellt.
qc = QuantumCircuit(1)
param = Parameter("θ")
qc.rx(param, 0)
qc.draw("mpl")Output:
# Decomposition of an RX(θ) gate using the IBM Quantum QPU basis
service = QiskitRuntimeService()
backend = service.least_busy(operational=True, simulator=False)
optimization_level = 3
pm = generate_preset_pass_manager(optimization_level, backend=backend)
transpiled_circuit = pm.run(qc)
transpiled_circuit.draw("mpl", idle_wires=False)Output:
from qiskit import QuantumCircuit
from qiskit.circuit import Parameter
from qiskit.transpiler import generate_preset_pass_manager
from qiskit_ibm_runtime import QiskitRuntimeService
qc = QuantumCircuit(2)
param = Parameter("θ")
qc.rzz(param, 0, 1)
qc.draw("mpl")Output:
# Decomposition of an RZZ(θ) gate using the IBM Quantum QPU basis
service = QiskitRuntimeService()
backend = service.least_busy(operational=True, simulator=False)
optimization_level = 3
pm = generate_preset_pass_manager(optimization_level, backend=backend)
transpiled_circuit = pm.run(qc)
transpiled_circuit.draw("mpl", idle_wires=False)Output:
Bei Arbeitsabläufen, die viele Ein-Qubit- oder Zwei-Qubit-Rotationen erfordern (z. B. in einem Variationsansatz oder bei der Simulation der zeitlichen Entwicklung von Quantensystemen), führt diese Einschränkung dazu, dass die Schaltungstiefe schnell wächst. Mit fraktionierten Gattern entfällt diese Anforderung jedoch, da die Ein- und Zwei-Qubit-Drehungen direkt ausgeführt werden und eine effizientere (und damit fehlerunterdrückte) Quantenschaltung entsteht.
Wann man keine fraktionierten Gates verwenden sollte
Es ist wichtig zu beachten, dass „Fractional Gates“ eine experimentelle Funktion sind und sich das Verhalten des Flags use_fractional_gates in Zukunft ändern kann. Weitere Informationen finden Sie qiskit-ibm-runtime in den Versionshinweisen zu den neuen Versionen von. Siehe auch die API-Referenzdokumentation zu „ QiskitRuntimeService.backend“, in der dies beschrieben wird use_fractional_gates.
Außerdem kann der Qiskit-Transpiler in seinen Optimierungsläufen nur begrenzt verwenden. Daher müssen Sie bei der Erstellung und Optimierung von Schaltungen, die diese Anweisungen enthalten, mehr Sorgfalt walten lassen.
Schließlich wird die Verwendung von Fractional Gates nicht unterstützt für:
- Pauli-Twirling - allerdings wird das Messungs-Twirling mit TREX unterstützt.
- Probabilistische Fehleraufhebung
- Null-Rausch-Extrapolation (mit probabilistischer Fehlerverstärkung)
Lesen Sie den Leitfaden zu den primitiven Optionen, um mehr über die Anpassung der Fehlerbegrenzungs- und -unterdrückungstechniken für eine bestimmte Quantenarbeitslast zu erfahren.
Welche Backends unterstützen fraktionierte Gates?
Nicht alle Backends unterstützen fraktionierte Gates. Lauf los, service.backends(use_fractional_gates=True) um diejenigen zu finden, die es tun. Mit der Veröffentlichung von „ v0.48qiskit-ibm-runtime “ können Sie außerdem den Befehl ausführen, um service.least_busy(fractional_gates=True) das am wenigsten ausgelastete Backend zu finden, das fraktionierte Gatter unterstützt. Ein simuliertes Backend unterstützt Bruchgates nur dann, wenn das zugehörige „echte“ Backend diese ebenfalls unterstützt.
Beachten Sie, dass gefälschte Backends standardmäßig keine Bruchgates unterstützen, da diese standardmäßig deaktiviert sind. Um Fractional Gates auf einem Fake-Backend zu aktivieren, das diese unterstützt, aktualisieren Sie dessen Konfiguration.
Beispiel:
service = QiskitRuntimeService()
fake_backend = FakeBoston()
fake_backend.refresh(service=service, use_fractional_gates=True)Nächste Schritte
- Weitere Informationen zur Transpilation finden Sie auf der Seite Einführung in die Transpilation.
- Lesen Sie über das Schreiben eines benutzerdefinierten Transpiler-Passes.
- Erfahren Sie, wie Sie die Fehlerbehebung konfigurieren.