Skip to main content
IBM Quantum Platform

Qiskit 0.39 Versionshinweise


0.39.5

Terra- 0.22.4

Vorspiel

Qiskit Terra 0.22.4 ist ein kleineres Bugfix-Release, das einige Fehler aus der 0.22 Serie behebt.

Fehlerkorrekturen

  • Ein Fehler wurde in BackendSampler der einen Fehler auslöste, wenn seine run() methode zwei Mal hintereinander aufgerufen wurde.

  • Es wurden zwei Fehler in der ComposedOp wo die ComposedOp.to_matrix() methode nicht die richtigen Ergebnisse für Zusammensetzungen mit StateFn und für Zusammensetzungen mit einem globalen Koeffizienten. Behoben #9283.

  • Es wurde das Problem behoben, bei dem Primitive, Sampler und Estimatornicht funktionierten, wenn eine Schaltung mit numpy.ndarray als Parameter übergeben wurde.

  • Es wurde ein Fehler in SamplingVQE behoben, bei dem das Argument aggregation keine Auswirkung hatte. Nun kann die Aggregationsfunktion und damit auch der CVaR Erwartungswert korrekt angegeben werden.

  • Ein Leistungsfehler wurde behoben, bei dem SamplingVQE die Energien von Eigenzuständen nur langsam auswertete.

  • Die automatische Bewertung der Beta-Parameter wurde in VQDkorrigiert, Unterstützung für SparsePauliOp eingaben, und die Energiebewertungsfunktion wurde korrigiert, um die asynchrone Ausführung von Primitiven zu nutzen, indem die Auftragsergebnisse erst abgerufen werden, nachdem beide Aufträge übermittelt wurden.

  • Es wurde ein Problem mit den Statevector.probabilities_dict() und DensityMatrix.probabilities_dict() methoden behoben, bei denen sie falsche Ergebnisse für Nicht-Qubit-Systeme lieferten, wenn das Argument qargs angegeben wurde. Behoben #9210

  • Die Behandlung einiger classmethods durch wrap_method() in Python 3.11. Zuvor wurde in Python 3.11, wrap_method die ungebundene Funktion, die mit classmethod verbunden ist, umhüllt und schlug dann beim Aufruf fehl, weil das Klassenobjekt, das normalerweise an classmethod gebunden ist, nicht an die Funktion übergeben wurde. Beginnend mit Python 3.11.1 betraf dieses Problem QiskitTestCase und verhinderte, dass es von anderem Testcode importiert werden konnte. Behoben #9291.

Aer- 0.11.2

Keine Änderung

IBM Q Anbieter 0.19.2

Keine Änderung


0.39.4

Terra- 0.22.3

Keine Änderung

Aer- 0.11.2

Neue Funktionen

  • Unterstützung für die Ausführung von Qiskit Aer mit Python 3.11 hinzugefügt.

Bekannte Probleme

  • Behebung von zwei Fehlern in AerStatevector. AerStatevector verwendet mc*-Anweisungen, die in der Methode matrix_product_state nicht aktiviert sind. Dieser Commit ändert AerStatevector so, dass MC* nicht mehr verwendet wird und H, X, Y, Z, U und CX verwendet werden. AerStatevector scheitert auch, wenn eine Anweisung in leere QuantumCircuit zerlegt wird. Diese Übergabe ermöglicht eine solche Anweisung.

Fehlerkorrekturen

  • In der Methode AerSimulator.from_backend() wurde die Unterstützung für die Instanziierung einer AerSimulator -Instanz aus einem a BackendV2 objekt. Zuvor hatte der Versuch, AerSimulator.from_backend() mit einem BackendV2 objekt zu verwenden, wurde eine AerError ausgegeben, die besagte, dass dies nicht unterstützt wurde.

  • Behebt einen Fehler, bei dem NoiseModel.from_backend() mit einem BackendV2 Objekt ein Rauschmodell mit übermäßigem QuantumError s auf Nicht-Gate-Befehlen erzeugen kann, während z.B. nur ReadoutError s für Maßnahmen ausreichend sein sollte. Diese Übergabe aktualisiert NoiseModel.from_backend() mit einem BackendV2 Objekt, so dass es das gleiche Rauschmodell zurückgibt wie das, das mit dem entsprechenden BackendV1 Objekt aufgerufen wird. Das heißt, das resultierende Rauschmodell enthält keine QuantumError s auf Maßnahmen und es kann nur thermische Relaxationsfehler auf andere Nicht-Gate-Befehle wie z. B. Rücksetzungen enthalten. Beachten Sie, dass sie immer noch ReadoutError s auf Maßnahmen enthält.

  • In NoiseModel.from_backend() wurde ein Fehler behoben, bei dem die Verwendung von temperature kwarg mit einem anderen als dem Standardwert die Population der angeregten Zustände für die angegebene Temperatur falsch berechnet hat. Zuvor gab es einen zusätzlichen Faktor 2 bei der Berechnung der Boltzman-Verteilung, der zu einem falschen kleineren Wert für die Population im angeregten Zustand führte.

  • Es wurde eine fehlerhafte Logik im Kontrollfluss-Compiler behoben, die dazu führen konnte, dass nicht verwandte Anweisungen während der Ausführung "innerhalb" von Kontrollflusskörpern erscheinen konnten, was zu falschen Ergebnissen führte. Zum Beispiel, früher:

    from qiskit import QuantumCircuit
    from qiskit_aer import AerSimulator
    
    backend = AerSimulator(method="statevector")
    
    circuit = QuantumCircuit(3, 3)
    circuit.measure(0, 0)
    circuit.measure(1, 1)
    
    with circuit.if_test((0, True)):
        with circuit.if_test((1, False)):
            circuit.x(2)
    
    with circuit.if_test((0, False)):
        with circuit.if_test((1, True)):
            circuit.x(2)
    
    circuit.measure(range(3), range(3))
    print(backend.run(circuit, method=method, shots=100).result())

    würde {'010': 100} ausgeben, da die verschachtelten Kontrollflussoperationen versehentlich über das erste X-Gatter auf Qubit 2 springen würden, das eigentlich hätte ausgeführt werden müssen.

  • Behebt einen Fehler, bei dem NoiseModel.from_backend() ausführliche Warnungen ausgibt, wenn ein Backend bereitgestellt wird, das unphysikalische Geräteparameter wie T2 > 2 * T1 aufgrund von statistischen Fehlern bei ihrer Schätzung meldet. Dieser Commit entfernt solche Warnungen, da sie für die Benutzer nicht handhabbar sind, in dem Sinne, dass es keine andere Möglichkeit gibt, als sie auf die theoretischen Grenzen abzuschneiden, wie es im noise.device Modul gemacht wird. Siehe Ausgabe 1631 für Details zu dem behobenen Fehler.

  • Dies ist eine Korrektur für den GPU-Zustandsvektor-Simulator. Die Chunk-Verteilung hat versucht, den gesamten freien Speicher auf der GPU zuzuweisen, was jedoch zu einem Fehler bei der Speicherzuweisung führt. Dieser Fix weist also 80 Prozent des freien Speichers zu. Dies legt auch die Größe des Matrixpuffers fest, wenn Rauschsampling angewendet wird.

  • Dies ist eine Korrektur von AerState, die mit Cache-Blockierung läuft. AerState falsch konfigurierter Transpiler von Aer für Cache-Blocking, und dann funktionierte sein Algorithmus zum Tauschen von Qubits falsch. Diese Korrektur korrigiert AerState, um diesen Transpiler zu verwenden. Genauer gesagt: Nach der Transpilierung wird eine vertauschte Qubit-Karte in die ursprüngliche Karte zurückverwandelt, wenn AerState verwendet wird. Dieser Fix ist notwendig für AerStatevector, um mehrere GPUs zu verwenden.

  • Dies ist die Lösung für AerStatevector. Es war nicht möglich, eine AerStatevector Instanz direkt aus dem Statevector von terra zu erstellen. Dieser Fix erlaubt einen Statevector als AerStatevector’s Eingabe.

  • SamplerResult.quasi_dists enthalten die Daten über die Anzahl der Qubits. QuasiDistribution.binary_probabilities() gibt Bitstrings mit der richtigen Länge zurück.

  • Zuvor wird die Saat in AerStatevector nicht initialisiert und die Ergebnisse der Stichproben sind immer gleich. Mit diesem Commit wird für jede Stichprobe ein Seed initialisiert und die Ergebnisse der Stichprobe können variieren.

IBM Q Anbieter 0.19.2

Keine Änderung


0.39.3

Terra- 0.22.3

Vorspiel

Qiskit Terra 0.22.3 ist ein kleineres Bugfix-Release, das einige weitere Fehler in der 0.22 Serie behebt.

Fehlerkorrekturen

  • AdaptVQE zeigt nun korrekt an, dass es Hilfsoperatoren unterstützt.

  • Die Schaltkreisschubladen (QuantumCircuit.draw() und circuit_drawer()) geben bei Verwendung der Standardargumente keine Warnung über den Parameter cregbundle mehr aus, wenn der Inhalt des Schaltkreises erfordert, dass alle Bits einzeln gezeichnet werden. Dies trat vor allem dann auf, wenn man versuchte, Schaltungen mit neuartigen Kontrollflussoperationen zu zeichnen.

  • Ein Fehler wurde behoben, der dazu führte, dass QNSPSA fehlschlug, wenn max_evals_grouped auf einen Wert größer als 1 gesetzt wurde.

  • Es wurde ein Problem mit dem SabreSwap durchgang, der dazu führte, dass die Ausgabe mehrerer Durchläufe des Durchgangs ohne Angabe des Arguments seed denselben Zufallszahlengenerator-Samen zwischen den Durchläufen wiederverwendete, anstatt verschiedene Samen zu verwenden. Dies führte bisher dazu, dass zwischen den Läufen identische Ergebnisse zurückgegeben wurden, auch wenn keine seed angegeben war.

  • Ein Problem mit den primitiven Klassen wurde behoben, BackendSampler und BackendEstimator, bei denen Instanzen nicht mit pickle serialisiert werden konnten. Im Allgemeinen ist nicht garantiert, dass diese Klassen serialisierbar sind, da BackendV2 und BackendV1 instanzen nicht serialisierbar sein müssen (und es oft auch nicht sind), aber die Klassendefinitionen von BackendSampler und BackendEstimator verhindern nicht mehr die Verwendung von pickle.

  • Die Methode pulse.Instruction.draw() wird nun wie zuvor erfolgreich sein. Diese Methode ist veraltet und wird nicht ersetzt, sollte aber für die Zeit der Veraltung noch funktionieren.

Aer- 0.11.1

Keine Änderung

IBM Q Anbieter 0.19.2

Keine Änderung


0.39.2

Terra- 0.22.2

Vorspiel

Qiskit Terra 0.22.2 ist eine kleinere Bugfix-Version und markiert die erste offizielle Unterstützung für Python 3.11.

Fehlerkorrekturen

  • Ein Problem mit den primitiven Klassen im Backend wurde behoben BackendSampler und BackendEstimator das die Ausführung mit einer BackendV1 instanz, die kein max_experiments Feld in ihrer BackendConfiguration.

  • Ein Fehler in der VF2PostLayout pass beim Transpilieren für Backends mit einem definierten Target, wo der Interaktionsgraph nicht korrekt erstellt wurde. Dies könnte zu übermäßigen Laufzeiten führen, da der Graph viel komplexer ist als nötig.

  • Der Pulse-Ausdrucksparser sollte nicht mehr regelmäßig hängen bleiben, wenn er von Jupyter-Notebooks aus aufgerufen wird. Dies wird dadurch erreicht, dass ein internes deepycopy eines rekursiven Objekts vermieden wird, dessen Auswertung für die Memoisierung besonders schwierig zu sein schien.

Aer- 0.11.1

Keine Änderung

IBM Q Anbieter 0.19.2

Keine Änderung


0.39.1

Terra- 0.22.1

Vorspiel

Qiskit Terra 0.22.1 ist eine Bugfix-Version, die einige kleinere Probleme behebt, die seit der Veröffentlichung von 0.22.0 festgestellt wurden.

Hinweise zu veralteten Versionen

  • Der pauli_list kwarg von pauli_basis() wurde veraltet, da pauli_basis() jetzt immer ein PauliList. Dieses Argument wurde vorzeitig aus Qiskit Terra 0.22.0 entfernt, wodurch die Kompatibilität für Benutzer, die pauli_list``argument. Now, the argument has been restored but will emit a ``DeprecationWarning verwenden, nicht mehr gegeben war. Wenn es verwendet wird, hat es keine Auswirkung, da Qiskit Terra 0.22.0 eine PauliList immer zurückgegeben wird.

Fehlerkorrekturen

  • Behebung des BarrierBeforeFinalMeasurements transpiler-Durchgang, wenn es Bedingungen auf losen Clbits unmittelbar vor der endgültigen Messschicht. Bisher scheiterte dies mit der Begründung, dass das Bit nicht in einer internen temporären Schaltung vorhanden war. Behoben #8923

  • Die Gleichheitsprüfungen für QuantumCircuit und DAGCircuit (mit Objekten desselben Typs) werden nun korrekt mit Bedingungen für einzelne Bits umgehen. Früher führten diese zu falsch negativen Ergebnissen bei Gleichheit, da die Bits "exakte" Gleichheitsprüfungen anstelle der "semantischen" Prüfungen verwendeten, die für die übrigen Eigenschaften von Schaltkreisanweisungen durchgeführt werden.

  • Feste Handhabung von klassischen Bits in StochasticSwap mit Kontrollfluss. Früher wurden Kontrollflussoperationen so erweitert, dass sie alle klassischen Bits in der äußeren Schaltung enthielten, und nicht wieder zusammengezogen, was zu einer Diskrepanz zwischen der Anzahl der vom Befehl als erforderlich gemeldeten Bits und der tatsächlichen Anzahl der ihm zugeführten Bits führte. Behoben #8903

  • Die Behandlung von global definierten Anweisungen für die Target klasse. Zuvor gab es zwei Methoden, operations_for_qargs() und operation_names_for_qargs() ignorierten/fälschlicherweise alle global definierten idealen Operationen, die im Ziel vorhanden waren. Zum Beispiel:

    from qiskit.transpiler import Target
    from qiskit.circuit.library import CXGate
    
    target = Target(num_qubits=5)
    target.add_instruction(CXGate())
    names = target.operation_names_for_qargs((1, 2))
    ops = target.operations_for_qargs((1, 2))

    gibt nun {"cx"} für names und [CXGate()] für ops zurück, anstatt KeyError oder einen leeren Rückgabewert zu erzeugen.

  • Es wurde ein Problem in der Target.add_instruction() methode behoben, bei der zuvor ein Argument mit einer ungültigen Anzahl von Qubits als Teil des properties Arguments akzeptiert wurde. Zum Beispiel:

    from qiskit.transpiler import Target
    from qiskit.circuit.library import CXGate
    
    target = Target()
    target.add_instruction(CXGate(), {(0, 1, 2): None})

    Dies wird nun korrekt eine TranspilerError auslösen, anstatt Laufzeitprobleme bei der Interaktion mit dem Ziel zu verursachen. Behoben #8914

  • Es wurde ein Problem mit der plot_state_hinton() visualisierungsfunktion behoben, die zu einer falsch platzierten Achse führte, die gegenüber der eigentlichen Darstellung versetzt war. Behoben #8446 <https://github.com/Qiskit/qiskit/issues/8446>

  • Die Ausgabe der Funktion plot_state_hinton() funktion korrigiert, so dass die Zustandsbezeichnungen richtig geordnet sind und das Bild mit der natürlichen Matrixanordnung übereinstimmt. Behoben #8324

  • Ein Problem mit den primitiven Klassen wurde behoben, BackendSampler und BackendEstimator bei der Ausführung auf Backends, die eine begrenzte Anzahl von Schaltkreisen in jedem Auftrag haben. Nicht alle Backends unterstützen eine unbegrenzte Stapelgröße (die meisten Hardware-Backends nicht), und früher hätten die primitiven Backend-Klassen möglicherweise fälschlicherweise mehr Schaltkreise gesendet, als das Backend unterstützte. Dies wurde dahingehend korrigiert, dass BackendSampler und BackendEstimator die Schaltkreise in mehrere Aufträge aufteilt, wenn das Backend eine begrenzte Anzahl von Schaltkreisen pro Auftrag hat.

  • Es wurde ein Problem mit der BackendEstimator klasse, bei dem das Setzen einer Laufoption namens monitor auf einen Wert, der als True ausgewertet wurde, fälschlicherweise einen Jobmonitor ausgelöst hat, der nur mit Backends aus dem Paket qiskit-ibmq-provider funktioniert hat. Dies wurde entfernt, so dass Sie bei Bedarf die Option monitor verwenden können, ohne dass es zu Problemen kommt.

  • Es wurde ein Problem mit der Target.build_coupling_map() methode, die fälschlicherweise None für ein Target objekt mit einer Mischung aus idealen, global verfügbaren Anweisungen und Anweisungen mit Qubit-Beschränkungen. In solchen Fällen wird die Target.build_coupling_map() eine Kopplungskarte für die eingeschränkte Anweisung zurück (es sei denn, es handelt sich um eine 2-Qubit-Operation, die None zurückgibt, da es global gesehen keine Konnektivitätsbeschränkung gibt). Behoben #8971

  • Es wurde ein Problem mit dem Target.qargs attribut, bei dem es fälschlicherweise None für ein Target objekt, das eine global verfügbare ideale Anweisung enthielt.

  • Das vorzeitige Entfernen des pauli_list Schlüsselwortarguments der pauli_basis() funktion, die bestehenden Code, der den pauli_list=True future compatibility path beim Upgrade auf Qiskit Terra 0.22.0 verwendete, beschädigte. Dieses Schlüsselwortargument wurde wieder in die Funktion aufgenommen und ist nun veraltet und wird in einer zukünftigen Version entfernt werden.

  • Ein Problem in der QPY-Serialisierung wurde behoben (dump()), wenn eine benutzerdefinierte ControlledGate unterklasse, die die Methode _define() überladen hat, um eine benutzerdefinierte Definition für die Operation bereitzustellen. Zuvor wurde dieser Vorgang nicht korrekt serialisiert, da die Verwendung der potenziellen Methode _define() zur Bereitstellung einer Definition nicht berücksichtigt wurde. Behebt #8794

  • Die QPY-Deserialisierung fügt nicht mehr zusätzliche Clbit instanzen zum Kreislauf hinzu, wenn sowohl lose Clbits in der Schaltung und mehr Qubits als Clbits.

  • Die QPY-Deserialisierung fügt keine Register mit den Namen q und c mehr hinzu, wenn die Eingangsschaltung nur lose Bits enthält.

  • Die Methode SparsePauliOp.dot() methode, wenn sie auf zwei Operatoren mit reellen Koeffizienten angewendet wird. Um dies zu beheben, wird der dtype, den SparsePauliOp annehmen kann, auf np.complex128 und object beschränkt. Behoben #8992

  • Es wurde ein Problem in der circuit_drawer() funktion und der Methode QuantumCircuit.draw() behoben, bei dem der einzige eingebaute Stil für die Ausgabe mpl , der verwendbar war, default war. Wenn ein anderer eingebauter Stil wie iqx verwendet würde, würde eine Warnung ausgegeben, dass der Stil nicht gefunden wurde, und die Schublade würde auf den Stil default zurückgreifen. Behoben #8991

  • Es wurde ein Problem mit dem transpile() wo es zuvor mit einem TypeError fehlschlug, wenn ein benutzerdefiniertes Target objekt über das Argument target übergeben wurde und für das Argument circuits eine Liste mit mehreren Schaltkreisen angegeben wurde.

  • Ein Problem wurde behoben mit transpile() beim Anvisieren einer Target (entweder direkt über das Argument target oder über eine BackendV2 instanz aus dem backend Argument), die eine ideale Measure anweisung enthielt (eine, für die keine Eigenschaften definiert waren). Zuvor wurde beim Versuch, das Ziel zu parsen, eine Ausnahme ausgelöst. Behoben #8969

  • Es wurde ein Problem mit dem VF2Layout pass, bei dem ein Fehler auftrat, wenn er mit einer Target die Anweisungen mit fehlenden Fehlerraten enthielt. Dies wurde korrigiert, so dass in solchen Fällen das Fehlen einer Fehlerquote als ideale Implementierung behandelt wird, und wenn keine Fehlerquoten vorhanden sind, wird einfach das erste passende Layout ausgewählt. Behoben #8970

  • Es wurde ein Problem mit dem VF2PostLayout passes behoben, bei dem ein Fehler auftrat, wenn er mit einer Target die fehlende Anweisungen enthielt. In solchen Fällen wird das Fehlen einer Fehlerquote als ideale Durchführung des Vorgangs gewertet.

  • Es wurde ein Problem mit der VQD klasse, wenn mehr als k=2 Eigenwerte berechnet wurden. Zuvor schlug dies aufgrund einer internen Typinkongruenz fehl, aber jetzt läuft es wie erwartet. Behoben #8982

  • Ein Leistungsfehler wurde behoben, bei dem die neuen primitiv-basierten Variationsalgorithmen minimum_eigensolvers.VQE, eigensolvers.VQD und SamplingVQE standardmäßig keine Energieauswertungen in Stapeln durchführten, was zu einer erheblichen Verlangsamung führte, wenn ein Hardware-Backend verwendet wurde.

  • Null-Operanden-Gatter und Anweisungen funktionieren jetzt mit circuit_to_gate(), QuantumCircuit.to_gate(), Gate.control()und der Konstruktion eines Operator aus einer QuantumCircuit mit Null-Operanden-Anweisungen. Dieser Grenzfall ist gelegentlich bei der Erstellung von Global-Phase-Gattern als Teil größerer zusammengesetzter Befehle nützlich, obwohl er für viele Anwendungen QuantumCircuit.global_phase geeigneter sein kann.

  • Behebt ein Problem, bei dem Statevector.evolve() und DensityMatrix.evolve() bei der Entwicklung von verschachtelten Subsystemen für Nicht-Qubit-Subsysteme eine Exception auslöste. Behebt Problem #8897

  • Behebt einen Fehler in Statevector.evolve() bei dem die Subsystem-Evolution in bestimmten Fällen den falschen Wert zurückgibt, wenn es 2 oder mehr als nicht-evolutionierte Subsysteme mit unterschiedlichen Subsystem-Dimensionen gibt. Behebt Problem #8899

Aer- 0.11.1

Fehlerkorrekturen

  • Ein möglicher Build-Fehler wurde behoben, wenn versucht wurde, CMake 3.18 oder neuer zu verwenden und qiskit-aer mit aktivierter GPU-Unterstützung zu bauen. Seit CMake 3.18 oder später muss beim Bauen mit CUDA die CMAKE_CUDA_ARCHITECTURES mit dem Architekturwert für die Ziel-GPU gesetzt werden. Dies wurde korrigiert, so dass die Einstellung AER_CUDA_ARCH verwendet wird, wenn diese nicht gesetzt wurde.

  • Behebt einen Fehler bei der Behandlung von Anweisungen mit Clbits in LocalNoisePass. Zuvor wurden versehentlich Clbits von Anweisungen (z. B. Maßnahmen) gelöscht, auf die das Rauschen im Fall von method="append" angewendet wird.

  • Der Leistungs-Overhead der Sampler-Klasse bei der Ausführung mit identischen Schaltkreisen in mehreren Ausführungen wurde behoben. Dies wurde dadurch erreicht, dass die Umsetzung dieser identischen Schaltungen bei nachfolgenden Ausführungen übersprungen/gespeichert wurde.

  • Die Kompatibilität der Sampler und Estimator primitiven Klassen mit qiskit-terra 0.22.0 Release. In qiskit-terra 0.22.0 wurden bahnbrechende API-Änderungen an der abstrakten Schnittstelle vorgenommen, wodurch die Kompatibilität mit diesen Klassen nicht mehr gegeben war; dies wurde behoben, so dass Sampler und Estimator jetzt mit qiskit-terra >= 0.22.0 verwendet werden können.

IBM Q Anbieter 0.19.2

Keine Änderung


0.39.0

Mit dieser Version wird auch das Qiskit Aer-Projekt als Teil des Qiskit-Metapakets offiziell abgeschafft. Dies bedeutet, dass in einer zukünftigen Version pip install qiskit nicht mehr qiskit-aer enthalten sein wird. Wenn Sie derzeit qiskit als Abhängigkeit installieren oder auflisten, um Aer zu erhalten, sollten Sie dies aktualisieren, um qiskit-aer ebenfalls explizit aufzulisten.

Das Projekt qiskit-aer ist immer noch aktiv und wird weiter gepflegt, aber für das Qiskit-Metapaket (d.h. das, was über pip install qiskit installiert wird) bewegt sich das Projekt in Richtung eines Modells, bei dem das Qiskit-Paket nur die gemeinsame Kernfunktionalität für den Aufbau und die Kompilierung von Quantenschaltungen, Programmen und Anwendungen enthält und Pakete, die darauf aufbauen oder Qiskit mit Hardware oder Simulatoren verbinden, separate Pakete sind.

Terra- 0.22.0

Vorspiel

Die Version von Qiskit Terra 0.22.0 ist eine große Funktionsversion, die eine Vielzahl von neuen Funktionen und Fehlerbehebungen enthält. Die Highlights dieser Veröffentlichung sind:

  • Hinzufügen einer anfänglichen Unterstützung des Transpilers für die Transpilierung von QuantumCircuit von Objekten, die Kontrollflussanweisungen enthalten, wie ForLoopOp und enthalten WhileLoopOp.
  • Deutlich verbesserte Skalierung und Leistung für die transpile() funktion bei einer großen Anzahl von Qubits, insbesondere wenn optimization_level=3 verwendet wird.
  • Externe Plugin-Schnittstelle für transpile() die es externen Paketen ermöglicht, Stufen für die Standard-Passmanager zu implementieren. Weitere Einzelheiten hierzu finden Sie unter qiskit.transpiler.preset_passmanagers.plugin. Zusätzlich, BackendV2 backends können nun optional benutzerdefinierte Standard-Plugins für die Planungs- und Übersetzungsphasen festlegen.
  • Aktualisierte Algorithmus-Implementierungen in qiskit.algorithms die sich die primitives klassen, die die BaseSampler und BaseEstimator.

Neue Funktionen

  • Hinzufügen von Unterstützung für die Darstellung einer Operation mit variabler Breite in der Target klasse. Zuvor musste ein Target objekt eine Instanz von Operation für jede im Ziel unterstützte Operation definiert werden. Dies wurde sowohl für die Validierung der Argumente als auch der Parameter der Operation verwendet. Bei Operationen mit variabler Breite war dies jedoch nicht möglich, da jede Instanz einer Klasse Operation nur eine feste Anzahl von Qubits haben kann. In Fällen, in denen ein Backend Operationen mit variabler Breite unterstützt, kann die Anweisung mit der Klasse der Operation anstelle einer Instanz hinzugefügt werden. In solchen Fällen wird die Operation als global auf allen Qubits unterstützt behandelt. Zum Beispiel, wenn Sie ein Ziel wie:

    from qiskit.circuit import Parameter, Measure, IfElseOp, ForLoopOp, WhileLoopOp
    from qiskit.circuit.library import IGate, RZGate, SXGate, XGate, CXGate
    from qiskit.transpiler import Target, InstructionProperties
    
    theta = Parameter("theta")
    
    ibm_target = Target()
    i_props = {
        (0,): InstructionProperties(duration=35.5e-9, error=0.000413),
        (1,): InstructionProperties(duration=35.5e-9, error=0.000502),
        (2,): InstructionProperties(duration=35.5e-9, error=0.0004003),
        (3,): InstructionProperties(duration=35.5e-9, error=0.000614),
        (4,): InstructionProperties(duration=35.5e-9, error=0.006149),
    }
    ibm_target.add_instruction(IGate(), i_props)
    rz_props = {
        (0,): InstructionProperties(duration=0, error=0),
        (1,): InstructionProperties(duration=0, error=0),
        (2,): InstructionProperties(duration=0, error=0),
        (3,): InstructionProperties(duration=0, error=0),
        (4,): InstructionProperties(duration=0, error=0),
    }
    ibm_target.add_instruction(RZGate(theta), rz_props)
    sx_props = {
        (0,): InstructionProperties(duration=35.5e-9, error=0.000413),
        (1,): InstructionProperties(duration=35.5e-9, error=0.000502),
        (2,): InstructionProperties(duration=35.5e-9, error=0.0004003),
        (3,): InstructionProperties(duration=35.5e-9, error=0.000614),
        (4,): InstructionProperties(duration=35.5e-9, error=0.006149),
    }
    ibm_target.add_instruction(SXGate(), sx_props)
    x_props = {
        (0,): InstructionProperties(duration=35.5e-9, error=0.000413),
        (1,): InstructionProperties(duration=35.5e-9, error=0.000502),
        (2,): InstructionProperties(duration=35.5e-9, error=0.0004003),
        (3,): InstructionProperties(duration=35.5e-9, error=0.000614),
        (4,): InstructionProperties(duration=35.5e-9, error=0.006149),
    }
    ibm_target.add_instruction(XGate(), x_props)
    cx_props = {
        (3, 4): InstructionProperties(duration=270.22e-9, error=0.00713),
        (4, 3): InstructionProperties(duration=305.77e-9, error=0.00713),
        (3, 1): InstructionProperties(duration=462.22e-9, error=0.00929),
        (1, 3): InstructionProperties(duration=497.77e-9, error=0.00929),
        (1, 2): InstructionProperties(duration=227.55e-9, error=0.00659),
        (2, 1): InstructionProperties(duration=263.11e-9, error=0.00659),
        (0, 1): InstructionProperties(duration=519.11e-9, error=0.01201),
        (1, 0): InstructionProperties(duration=554.66e-9, error=0.01201),
    }
    ibm_target.add_instruction(CXGate(), cx_props)
    measure_props = {
        (0,): InstructionProperties(duration=5.813e-6, error=0.0751),
        (1,): InstructionProperties(duration=5.813e-6, error=0.0225),
        (2,): InstructionProperties(duration=5.813e-6, error=0.0146),
        (3,): InstructionProperties(duration=5.813e-6, error=0.0215),
        (4,): InstructionProperties(duration=5.813e-6, error=0.0333),
    }
    ibm_target.add_instruction(Measure(), measure_props)
    ibm_target.add_instruction(IfElseOp, name="if_else")
    ibm_target.add_instruction(ForLoopOp, name="for_loop")
    ibm_target.add_instruction(WhileLoopOp, name="while_loop")

    Die IfElseOp, ForLoopOp, und WhileLoopOp werden global für jede Anzahl von Qubits unterstützt. Dies wird dann durch andere Aufrufe in der Target API wider, wie zum Beispiel instruction_supported():

    ibm_target.instruction_supported(operation_class=WhileLoopOp, qargs=(0, 2, 3, 4))
    ibm_target.instruction_supported('if_else', qargs=(0, 1))

    beide geben True zurück.

  • Neue primitive Implementierungen hinzugefügt, BackendSampler und BackendEstimatorzu qiskit.primitives. Diese neuen primitiven Klassenimplementierungen verpacken eine BackendV1 oder BackendV2 instanz als BaseSampler oder BaseEstimator um. Der beabsichtigte Anwendungsfall für diese primitiven Implementierungen ist die Überbrückung der Lücke zwischen Anbietern, die keine nativen primitiven Implementierungen haben, und der Verwendung des Backends dieses Anbieters mit APIs, die mit Primitiven arbeiten. Zum Beispiel, die SamplingVQE klasse benötigt eine BaseSampler instanz zur Funktion. Wenn Sie diese Klasse mit einem Backend von einem Anbieter ohne native primitive Implementierung ausführen möchten, können Sie eine BackendSampler um dies zu tun:

    from qiskit.algorithms.minimum_eigensolvers import SamplingVQE
    from qiskit.algorithms.optimizers import SLSQP
    from qiskit.circuit.library import TwoLocal
    from qiskit.primitives import BackendSampler
    from qiskit.providers.fake_provider import FakeHanoi
    from qiskit.opflow import PauliSumOp
    from qiskit.quantum_info import SparsePauliOp
    
    backend = FakeHanoi()
    sampler = BackendSampler(backend=backend)
    
    operator = PauliSumOp(SparsePauliOp(["ZZ", "IZ", "II"], coeffs=[1, -0.5, 0.12]))
    ansatz = TwoLocal(rotation_blocks=["ry", "rz"], entanglement_blocks="cz")
    optimizer = SLSQP()
    sampling_vqe = SamplingVQE(sampler, ansatz, optimizer)
    result = sampling_vqe.compute_minimum_eigenvalue(operator)
    eigenvalue = result.eigenvalue

    Wenn Sie einen Anbieter verwenden, der über native primitive Implementierungen verfügt (z. B. qiskit-ibm-runtime oder qiskit-aer), ist es immer eine bessere Wahl, diese native primitive Implementierung anstelle von BackendEstimator oder BackendSampler zu verwenden, da die nativen Implementierungen viel effizienter sind und/oder zusätzliche Vor- und Nachverarbeitungen vornehmen. BackendEstimator und BackendSampler sind so konzipiert, dass sie generisch sind und mit jedem Backend arbeiten können, das Counts in ihrem Results , was eine zusätzliche Optimierung ausschließt.

  • Eine neue Algorithmusklasse wurde hinzugefügt, AdaptVQE zu hinzugefügt qiskit.algorithms Dieser Algorithmus verwendet eine qiskit.algorithms.minimum_eigensolvers.VQE in Kombination mit einem Pool von Operatoren, aus dem er eine qiskit.circuit.library.EvolvedOperatorAnsatz adaptiv. Zum Beispiel:

    from qiskit.algorithms.minimum_eigensolvers import AdaptVQE, VQE
    from qiskit.algorithms.optimizers import SLSQP
    from qiskit.primitives import Estimator
    from qiskit.circuit.library import EvolvedOperatorAnsatz
    
    # get your Hamiltonian
    hamiltonian = ...
    
    # construct your ansatz
    ansatz = EvolvedOperatorAnsatz(...)
    
    vqe = VQE(Estimator(), ansatz, SLSQP())
    
    adapt_vqe = AdaptVQE(vqe)
    
    result = adapt_vqe.compute_minimum_eigenvalue(hamiltonian)
  • Die BackendV2 klasse unterstützt nun zwei neue optionale Hook-Points, die es Backends ermöglichen, benutzerdefinierte Kompilierungsschritte als Teil von transpile() und generate_preset_pass_manager(). Wenn eine BackendV2 implementierung die Methoden get_scheduling_stage_plugin() oder get_translation_stage_plugin() enthält, verwendet der Transpiler die zurückgegebene Zeichenkette als Standardwert für die Argumente scheduling_method und translation_method . Dies ermöglicht es Backends, zusätzliche benutzerdefinierte Transpilerdurchläufe auszuführen, wenn sie auf dieses Backend abzielen, indem sie die Transpiler Stage plugin schnittstelle. Für weitere Details zur Verwendung siehe: Benutzerdefinierte Transpiler-Pässe.

  • Ein neues Schlüsselwortargument, ignore_backend_supplied_default_methods, wurde zu der transpile() funktion hinzugefügt, das verwendet werden kann, um die benutzerdefinierte Auswahl einer Standardmethode durch ein Backend zu deaktivieren, wenn das Ziel-Backend get_scheduling_stage_plugin() oder get_translation_stage_plugin() definiert hat.

  • Hinzufügen eines label Parameters zum Barrier konstruktor der Klasse und der barrier() methode wurde ein Parameter hinzugefügt, der es dem Benutzer ermöglicht, einer Instanz der Barrier richtlinie zuzuweisen. Für Visualisierungen, die mit circuit_drawer() oder QuantumCircuit.draw() erzeugt wurden, wird diese Beschriftung am oberen Rand der barrier gedruckt.

    from qiskit import QuantumCircuit
    
    circuit = QuantumCircuit(2)
    circuit.h(0)
    circuit.h(1)
    circuit.barrier(label="After H")
    circuit.draw('mpl')
  • Neue Tore hinzufügen CCZGate, CSGate, und CSdgGate zu den Standardgattern in der Schaltkreisbibliothek (qiskit.circuit.library).

  • Hinzugefügt qiskit.algorithms.eigensolvers paket zur Aufnahme von Schnittstellen für primitiv-aktivierte Algorithmen. Dieses neue Modul wird schließlich das bisherige qiskit.algorithms.eigen_solvers ersetzen. Dieses neue Modul enthält eine alternative Implementierung des VQD die statt eines Backends oder QuantumInstance stattdessen eine Instanz von BaseEstimator, einschließlich Estimator, BackendEstimator, oder beliebige Provider-Implementierungen wie die in qiskit-ibm-runtime und qiskit-aer.

    Um zum Beispiel die neue Implementierung mit einer Instanz von Estimator klasse:

    from qiskit.algorithms.eigensolvers import VQD
    from qiskit.algorithms.optimizers import SLSQP
    from qiskit.circuit.library import TwoLocal
    from qiskit.primitives import Sampler, Estimator
    from qiskit.algorithms.state_fidelities import ComputeUncompute
    from qiskit.opflow import PauliSumOp
    from qiskit.quantum_info import SparsePauliOp
    
    h2_op = PauliSumOp(SparsePauliOp(
        ["II", "IZ", "ZI", "ZZ", "XX"],
        coeffs=[
            -1.052373245772859,
            0.39793742484318045,
            -0.39793742484318045,
            -0.01128010425623538,
            0.18093119978423156,
        ],
    ))
    
    estimator = Estimator()
    ansatz = TwoLocal(rotation_blocks=["ry", "rz"], entanglement_blocks="cz")
    optimizer = SLSQP()
    fidelity = ComputeUncompute(Sampler())
    
    vqd = VQD(estimator, fidelity, ansatz, optimizer, k=2)
    result = vqd.compute_eigenvalues(h2_op)
    eigenvalues = result.eigenvalues

    Man beachte, dass die ausgewerteten Hilfsoperatoren jetzt über das aux_operators_evaluated -Feld der Ergebnisse erhalten werden. Diese besteht aus einer Liste oder einem Diktat von Tupeln, die die Erwartungswerte für diese Operatoren sowie die Metadaten des primitiven Laufs enthalten. aux_operator_eigenvalues ist nicht länger ein gültiges Feld.

  • Neue Algorithmen zur Berechnung von Zustandstreue/Überlappung für Paare von Quantenschaltungen (die parametrisiert werden können). Neben der Basisklasse (BaseStateFidelity), die die Schnittstelle definiert, gibt es eine Implementierung der Methode compute-uncompute, die Instanzen der BaseSampler primitivs nutzt: qiskit.algorithms.state_fidelities.ComputeUncompute.

    Zum Beispiel:

    import numpy as np
    from qiskit.primitives import Sampler
    from qiskit.algorithms.state_fidelities import ComputeUncompute
    from qiskit.circuit.library import RealAmplitudes
    
    sampler = Sampler(...)
    fidelity = ComputeUncompute(sampler)
    circuit = RealAmplitudes(2)
    values = np.random.random(circuit.num_parameters)
    shift = np.ones_like(values) * 0.01
    
    job = fidelity.run([circuit], [circuit], [values], [values+shift])
    fidelities = job.result().fidelities
  • Ein neues Modul hinzugefügt qiskit.algorithms.gradients hinzugefügt, das Klassen enthält, die zur Berechnung von Gradienten unter Verwendung der primitiven Schnittstellen, die in qiskit.primitives. Es gibt 4 Arten von Gradientenklassen: Finite Difference, Parameter Shift, Linear Combination of Unitary, und SPSA mit Implementierungen, die entweder eine Instanz des BaseEstimator schnittstelle verwenden:

    oder eine Instanz der BaseSampler schnittstelle:

    Die schätzerbasierten Gradienten berechnen den Gradienten der Erwartungswerte, während die samplerbasierten Gradienten die Gradienten der Messergebnisse (auch als "Wahrscheinlichkeitsgradienten" bezeichnet) liefern.

    Zum Beispiel:

    estimator = Estimator(...)
    gradient = ParamShiftEstimatorGradient(estimator)
    job = gradient.run(circuits, observables, parameters)
    gradients = job.result().gradients
  • Die Klasse Grover klasse hat ein neues Schlüsselwortargument, sampler , das verwendet wird, um den Algorithmus mit einer Instanz der BaseSampler schnittstelle, um die Ergebnisse zu berechnen. Dieses neue Argument ersetzt das Argument quantum_instance und dementsprechend ist quantum_instance veraltet und wird in zukünftigen Versionen veraltet sein und entfernt werden.

    Beispiel:

    from qiskit import QuantumCircuit
    from qiskit.primitives import Sampler
    from qiskit.algorithms import Grover, AmplificationProblem
    
    sampler = Sampler()
    oracle = QuantumCircuit(2)
    oracle.cz(0, 1)
    problem = AmplificationProblem(oracle, is_good_state=["11"])
    grover = Grover(sampler=sampler)
    result = grover.amplify(problem)
  • Eine neue Option, "formatter.control.fill_waveform" , wurde zu den Stilvorlagen für die Impulsschublade (pulse_v2.draw() und Schedule.draw()) Stilvorlagen hinzugefügt. Diese Option kann verwendet werden, um die Gesichtsfarbe von Impulsen in der Ausgabevisualisierung zu entfernen, was es ermöglicht, Impulse nur mit Linien zu zeichnen.

    Zum Beispiel:

    from qiskit.visualization.pulse_v2 import IQXStandard
    
    my_style = IQXStandard(
        **{"formatter.control.fill_waveform": False, "formatter.line_width.fill_waveform": 2}
    )
    
    my_sched.draw(style=my_style)
  • Ein neuer Transpiler-Pass wurde hinzugefügt, ResetAfterMeasureSimplification, der verwendet wird, um eine Reset operation nach einer Measure durch eine bedingte XGate. Dieser Pass kann in Backends verwendet werden, in denen eine Reset operation durchgeführt wird, indem man eine Messung und dann ein bedingtes X-Gate durchführt, so dass dies die doppelte implizite Measure von der Reset operation entfernt. Zum Beispiel:

    from qiskit import QuantumCircuit
    from qiskit.transpiler.passes import ResetAfterMeasureSimplification
    
    qc = QuantumCircuit(1)
    qc.measure_all()
    qc.reset(0)
    qc.draw('mpl')
    result = ResetAfterMeasureSimplification()(qc)
    result.draw('mpl')
  • Es wurde ein neuer unterstützter Wert "reverse_linear" für das entanglement Schlüsselwortargument zum Konstruktor für die NLocal schaltkreis-Klasse. Für TwoLocal schaltungen (die eine Unterklasse von NLocal), wenn entanglement_blocks="cx" , dann liefert die Verwendung von entanglement="reverse_linear" eine äquivalente n-Qubit-Schaltung wie entanglement="full" , aber mit nur n−1n-1 CXGate gattern anstelle von n(n−1)2\frac{n(n-1)}{2}.

  • ScheduleBlock wurde so aktualisiert, dass es nicht zugewiesene Unterprogramme verwalten kann, d.h., dass es den "faulen" Aufruf anderer Programme ermöglicht. Dies ermöglicht zum Beispiel den folgenden Arbeitsablauf:

    from qiskit import pulse
    
    with pulse.build() as prog:
      pulse.reference("x", "q0")
    
    with pulse.build() as xq0:
      pulse.play(Gaussian(160, 0.1, 40), pulse.DriveChannel(0))
    
    prog.assign_references({("x", "q0"): xq0})

    Nun kann ein Benutzer prog erstellen, ohne die tatsächliche Implementierung der Referenz ("x", "q0") zu kennen, und sie zu einem späteren Zeitpunkt zur Ausführung zuweisen. Dies verbessert die Modularität von Impulsprogrammen, und so kann man leicht ein Musterimpulsprogramm schreiben, das auf anderen Kalibrierungen beruht.

    Um diese Funktion zu realisieren, wurde die neue Impulsanweisung (Compilerdirektive) Reference hinzugefügt worden. Diese Anweisung wird in den aktuellen Builder-Bereich injiziert, wenn der reference() befehl verwendet wird. Mit der Eigenschaft references können alle im aktuellen Pulsprogramm definierten Referenzen aufgelistet werden.

    Außerdem wird jede Referenz mit einem Bereich verwaltet, um die Parameterverwaltung zu erleichtern. scoped_parameters() und search_parameters() sind hinzugefügt worden zu ScheduleBlock. Weitere Einzelheiten finden Sie in der API-Dokumentation.

  • Hinzufügen einer neuen Methode SparsePauliOp.argsort()hinzugefügt, die die Zusammensetzung von Permutationen in der Reihenfolge der Sortierung nach Koeffizienten und der Sortierung nach Pauli zurückgibt. Mit dem Schlüsselwortargument weight für die Methode kann die Ausgabe zusätzlich nach der Anzahl der nicht-identischen Terme im Pauli sortiert werden, wobei die Menge aller Paulis eines bestimmten Gewichts weiterhin lexikografisch geordnet wird.

  • Hinzufügen einer neuen Methode SparsePauliOp.sort()hinzugefügt, die zuerst die Koeffizienten mit Hilfe von numpy's argsort() und dann nach Pauli sortiert, wobei die Pauli-Sortierung Vorrang hat. Wenn die Pauli-Sortierung dieselbe ist, wird sie nach Koeffizienten sortiert. Mit dem Schlüsselwortargument weight kann die Ausgabe zusätzlich nach der Anzahl der nicht-identischen Begriffe im Pauli sortiert werden, wobei die Menge aller Paulis eines bestimmten Gewichts weiterhin lexikographisch geordnet wird.

  • Ein neues Schlüsselwortargument, wire_order, wurde zu der circuit_drawer() funktion und QuantumCircuit.draw() methode hinzugefügt, die es erlaubt, sowohl die Quanten- als auch die klassischen Bits in der Ausgabevisualisierung beliebig umzuordnen. Zum Beispiel:

    from qiskit import QuantumCircuit, QuantumRegister, ClassicalRegister
    
    qr = QuantumRegister(4, "q")
    cr = ClassicalRegister(4, "c")
    cr2 = ClassicalRegister(2, "ca")
    circuit = QuantumCircuit(qr, cr, cr2)
    circuit.h(0)
    circuit.h(3)
    circuit.x(1)
    circuit.x(3).c_if(cr, 10)
    circuit.draw('mpl', cregbundle=False, wire_order=[2, 1, 3, 0, 6, 8, 9, 5, 4, 7])
  • Zusätzliche Unterstützung für die CSGate, CSdgGate und CCZGate klassen zum Konstruktor für die Operatorklasse CNOTDihedral. Die Eingangsschaltungen beim Erstellen eines CNOTDihedral operator werden nun Schaltungen unterstützt, die diese Gatter verwenden. Zum Beispiel:

    from qiskit import QuantumCircuit
    from qiskit.quantum_info import CNOTDihedral
    
    qc = QuantumCircuit(2)
    qc.t(0)
    qc.cs(0, 1)
    qc.tdg(0)
    operator = CNOTDihedral(qc)
  • Die Algorithmusklassen für die Amplitudenschätzung:

    Haben jetzt ein neues Schlüsselwortargument, sampler , für ihren Konstruktor, der eine Instanz eines Objekts annimmt, das die BaseSampler schnittstelle einschließlich BackendSampler, Sampler, oder beliebige Provider-Implementierungen, wie die in qiskit-ibm-runtime und qiskit-aer vorhandenen. Dies bietet eine Alternative zur Verwendung des Arguments quantum_instance , um das Ziel zu setzen Backend oder QuantumInstance für die Ausführung des Algorithmus. Die Verwendung von a QuantumInstance ist noch nicht veraltet und wird in einer zukünftigen Version veraltet sein.

  • Eine neue Klasse wurde hinzugefügt, BackendV2Converterhinzugefügt, die verwendet wird, um eine BackendV1 instanz in eine BackendV2 schnittstelle. Sie ermöglicht es Ihnen, eine BackendV2 instanz von jedem BackendV1. Dies ermöglicht die Standardisierung von Zugriffsmustern auf die neuere BackendV2 schnittstelle zu standardisieren, auch wenn Sie noch BackendV1.

  • Eine neue Funktion hinzugefügt convert_to_target() die verwendet wird, um eine BackendConfigurationund optional a BackendProperties und PulseDefaults nimmt und ein Target objekt erzeugt, das dem Inhalt dieser Objekte entspricht.

  • qiskit.quantum_info.BaseOperator unterklassen (wie z.B ScalarOp, SparsePauliOp und PauliList) können jetzt mit der eingebauten Funktion Python sum() verwendet werden.

  • Ein neuer Transpiler-Pass, ConvertConditionsToIfOps wurde hinzugefügt, der verwendet werden kann, um altmodische Instruction.c_if()-konditionierte Anweisungen in IfElseOp objekte umwandelt. Dies soll den Übergang vom alten Typ zum neuen Typ für Backends erleichtern. Für die meisten Benutzer besteht keine Notwendigkeit, diese Funktion zu ihren Pass-Managern hinzuzufügen, und sie ist auch nicht in den voreingestellten Pass-Managern enthalten.

  • Umstrukturierung der Kommutativitätsanalyse von Gattern in eine Klasse CommutationChecker. Mit dieser Klasse können Sie (auf der Grundlage der Matrixmultiplikation) prüfen, ob zwei Gatter kommutieren oder nicht kommutieren, und die Ergebnisse zwischenspeichern (so dass eine ähnliche Prüfung in Zukunft keine Matrixmultiplikation mehr erfordert).

    Zum Beispiel können wir jetzt tun:

    from qiskit.circuit import QuantumRegister, CommutationChecker
    
    comm_checker = CommutationChecker()
    qr = QuantumRegister(4)
    
    res = comm_checker.commute(CXGate(), [qr[1], qr[0]], [], CXGate(), [qr[1], qr[2]], [])

    Da sich die beiden CX-Gatter umkehren (das erste CX-Gatter ist über die Qubits qr[1] und qr[0], und das zweite CX-Gatter ist über die Qubits qr[1] und qr[2]), haben wir, dass res True ist.

    Diese Kommutativitätsprüfung ist bei bedingten und parametrisierten Gattern zu konservativ und kann False zurückgeben, selbst wenn solche Gatter kommutieren.

  • Hinzufügen eines neuen Transpiler-Passes CommutativeInverseCancellation hinzugefügt, der Paare von inversen Gattern unter Ausnutzung von Kommutationsbeziehungen zwischen Gattern aufhebt. Dieser Durchgang ist eine Verallgemeinerung des Transpiler-Durchgangs InverseCancellation da er eine größere Menge von inversen Gattern erkennt und die Kommutativität berücksichtigt. Der Durchgang vermeidet auch einige Probleme im Zusammenhang mit dem Transpiler-Durchgang CommutativeCancellation.

    Zum Beispiel:

    from qiskit.circuit import QuantumCircuit
    from qiskit.transpiler import PassManager
    from qiskit.transpiler.passes import CommutativeInverseCancellation
    
    circuit = QuantumCircuit(2)
    circuit.z(0)
    circuit.x(1)
    circuit.cx(0, 1)
    circuit.z(0)
    circuit.x(1)
    
    passmanager = PassManager(CommutativeInverseCancellation())
    new_circuit = passmanager.run(circuit)

    hebt das Paar der selbstinversen Z-Tore und das Paar der selbstinversen X-Tore auf (da die betreffenden Tore mit dem CX-Tor pendeln), so dass eine Schaltung entsteht, die aus einem einzigen CX-Tor besteht.

    Die umgekehrte Prüfung ist bei bedingten und parametrisierten Gattern zu konservativ und kann einige dieser Gatter nicht aufheben.

  • QuantumCircuit.compose() akzeptiert nun einen Operanden mit klassischen Bits, wenn die Basisschaltung selbst keine hat. Das Muster, einen Schaltkreis mit Messungen zu einem reinen Quantenschaltkreis zusammenzusetzen, ist nun gültig. Zum Beispiel:

    from qiskit import QuantumCircuit
    
    base = QuantumCircuit(3)
    terminus = QuantumCircuit(3, 3)
    terminus.measure_all()
    
    # This will now succeed, though it was previously a CircuitError.
    base.compose(terminus)
  • Die DAGCircuit methoden depth() und size() haben ein neues Schlüsselwortargument recurse zur Verwendung mit Schaltkreisen, die Kontrollflussoperationen enthalten (wie z. B IfElseOp, WhileLoopOp, und ForLoopOp). Standardmäßig ist dies False und löst einen Fehler aus, wenn Kontrollflussoperationen vorhanden sind, um schlecht definierte Ergebnisse zu vermeiden. Bei der Einstellung True wird ein Proxy-Wert zurückgegeben, der versucht, jeden Kontrollflussblock im Verhältnis zu seinem Zustand gerecht zu gewichten, auch wenn die Tiefe oder Größe eines konkreten Laufs im Allgemeinen nicht bekannt ist. Wie sich die einzelnen Kontrollflussoperationen auf die Ausgabe auswirken, finden Sie in der Dokumentation der jeweiligen Methode.

  • DAGCircuit.count_ops() ein recurse -Schlüsselwortargument für die Rekursion in Kontrollflussblöcke gewonnen. Standardmäßig ist dies True, und alle Operationen in allen Blöcken werden zurückgegeben, ebenso wie die Kontrollflussoperationen selbst.

  • Hinzufügen eines Arguments create_preds_and_succs zu den Funktionen circuit_to_dagdependency() und dag_to_dagdependency() die von QuantumCircuit und DAGCircuitjeweils in DAGDependency. Wenn der Wert von create_preds_and_succs False ist, werden die transitiven Vorgänger und Nachfolger für Knoten in DAGDependency nicht konstruiert, wodurch die Konvertierungen schneller und deutlich weniger speicherintensiv werden. Die direkten Vorgänger und Nachfolger der Knoten in DAGDependency werden wie üblich konstruiert.

    Zum Beispiel:

    from qiskit.converters import circuit_to_dagdependency
    from qiskit import QuantumRegister, ClassicalRegister, QuantumCircuit
    
    circuit_in = QuantumCircuit(2)
    circuit_in.h(qr[0])
    circuit_in.h(qr[1])
    
    dag_dependency = circuit_to_dagdependency(circuit_in, create_preds_and_succs=False)
  • Neue Attribute hinzugefügt Clifford.symplectic_matrix, Clifford.tableau, Clifford.z, Clifford.x, Clifford.phase, Clifford.stab, Clifford.stab_z, Clifford.stab_x, Clifford.stab_phase, Clifford.destab, Clifford.destab_z, Clifford.destab_x, Clifford.destab_phase zur Clifford klasse. Diese können anstelle von Clifford.table verwendet werden, das in Zukunft veraltet sein wird. StabilizerTable und PauliTable sind veraltet und werden in der nächsten Version veraltet sein und danach entfernt werden.

  • Der Commuting2qGateRouter konstruktor hat jetzt ein neues Schlüsselwortargument, edge_coloring. Dieses Argument wird verwendet, um eine Kantenfärbung der Kopplungskarte zu erstellen, um die Reihenfolge zu bestimmen, in der die commuting gates angewendet werden.

  • Hinzufügen einer neuen Algorithmus-Schnittstelle zur Erstellung von Zeitentwicklungsalgorithmen unter Verwendung der Primitive BaseSampler und BaseEstimator. Diese neue Schnittstelle besteht aus:

    Diese neue Schnittstelle ist eine Alternative zu der bereits bestehenden Schnittstelle für Zeitentwicklungsalgorithmen, die mit EvolutionProblem, EvolutionResult, RealEvolver, und ImaginaryEvolver die mit einem QuantumInstance objekt anstelle von Primitiven arbeitete. Diese neue Schnittstelle ersetzt die frühere Schnittstelle, die veraltet ist und in zukünftigen Versionen entfernt werden wird.

  • Neue Backend-Klassen zugefügt qiskit.providers.fake_provider:

    Diese neuen Klassen implementieren die BackendV2 schnittstelle und werden unter Verwendung gespeicherter Snapshots der Backend-Informationen aus den Systemen IBM Quantum ibm_auckland, ibm_oslo, ibm_geneva bzw. ibm_perth erstellt.

  • Die Klasse Z2Symmetries klasse hat zwei neue Methoden, convert_clifford() und taper_clifford(). Diese beiden Methoden sind die beiden Operationen, die notwendig sind, um einen Operator auf der Grundlage der Z2 Symmetrien im Objekt zu verjüngen und wurden zuvor intern über die taper() methode durchgeführt. Diese Methoden sind nun jedoch öffentliche Methoden der Klasse, die bei Bedarf einzeln aufgerufen werden können.

  • Die Laufzeitleistung für die Konjugation eines langen PauliList objekts durch eine Clifford unter Verwendung der PauliList.evolve() hat sich deutlich verbessert. Er läuft jetzt deutlich schneller als zuvor.

  • Hinzufügen einer neuen abstrakten Klasse ClassicalIOChannel zum qiskit.pulse.channels modul hinzugefügt. Diese Klasse wird verwendet, um klassische E/A-Kanäle darzustellen und diese Kanäle von anderen Unterklassen von Channel. Diese neue Klasse ist die Basisklasse für die MemorySlot, RegisterSlot, und SnapshotChannel klassen. Dementsprechend ist die pad() kanonisierungsimpulstransformation in qiskit.pulse.transforms keine Verzögerungen bei den Instanzen von ClassicalIOChannel

  • Der SabreSwap transpilerpass hat ein neues Schlüsselwortargument in seinem Konstruktor, trials. Das Argument trials wird verwendet, um die Anzahl der zu versuchenden Zufallsversuche anzugeben. Die Ausgabe des SABRE-Algorithmus kann sich je nach dem für die Zufallszahl verwendeten Seed stark unterscheiden. SabreSwap führt nun den Algorithmus mit trials Anzahl von Zufallsseeds aus und wählt den besten aus (mit den wenigsten eingefügten Swaps). Wenn trials nicht angegeben wird, verwendet der Durchlauf standardmäßig die Anzahl der physischen CPUs auf dem lokalen System.

  • Der SabreLayout transpilerpass hat ein neues Schlüsselwortargument in seinem Konstruktor, swap_trials. Das Argument swap_trials wird verwendet, um anzugeben, wie viele Zufallsversuche für den SabreSwap intern durchlaufen werden sollen. Sie entspricht dem trials arugment auf dem SabreSwap pass. Wenn diese Option gesetzt ist, wird jede Iteration von SabreSwap intern swap_trials mal durchlaufen werden. Wenn swap_trials nicht angegeben wird, wird standardmäßig die Anzahl der physischen CPUs auf dem lokalen System verwendet.

  • Eine neue Funktion wurde hinzugefügt, estimate_observables() die eine Implementierung der BaseEstimator schnittstelle (z.B. Estimator, BackendEstimator, oder beliebige Provider-Implementierungen wie die in qiskit-ibm-runtime und qiskit-aer) verwendet, um die Erwartungswerte, ihre Mittelwerte und Standardabweichungen aus einer Liste oder einem Wörterbuch von Beobachtungswerten zu berechnen. Dies dient einem ähnlichen Zweck wie die bereits vorhandene Funktion eval_observables() die die Berechnung mit einem QuantumInstance objekts durchführte und die durch diese neue Funktion ersetzt wurde (und in zukünftigen Versionen veraltet sein und entfernt werden wird).

  • Hinzufügen einer neuen Operation basisklasse hinzugefügt, die eine leichtgewichtige abstrakte Schnittstelle für Objekte bietet, die auf QuantumCircuit. Dies ermöglicht es, "übergeordnete" Objekte direkt auf einer Schaltung zu speichern (z.B., Clifford objekte), solche Objekte direkt zu kombinieren (z. B. mehrere aufeinanderfolgende Clifford objekte über dieselben Qubits zusammenzusetzen) und solche Objekte zur Laufzeit zu synthetisieren (z.B. um Clifford in einer Weise zu synthetisieren, die die Tiefe optimiert und/oder die Konnektivität der Geräte ausnutzt). Zuvor konnten nur Unterklassen von qiskit.circuit.Instruction auf QuantumCircuitzugeordnet werden, aber diese Schnittstelle ist unhandlich geworden und enthält zu viele Methoden und Attribute für Allzweckobjekte.

    Die neue Operation schnittstelle umfasst name, num_qubits und num_clbits (in Zukunft kann dies leicht angepasst werden), aber vor allem umfasst sie nicht definition (und bindet somit die Synthese nicht an das Objekt), sie umfasst nicht condition (dies sollte Teil eines separaten klassischen Kontrollflusses sein) und sie umfasst nicht duration und unit (da dies Eigenschaften der Ausgabe des Transpilers sind).

    Ab sofort, Operation umfasst Gate, Reset, Barrier, Measureund "höherwertige" Objekte wie Clifford. Diese Liste der "übergeordneten" Objekte wird in Zukunft noch erweitert werden.

  • A Clifford wird nun zu einer Quantenschaltung als Operationhinzugefügt, ohne zuvor eine Teilschaltung zu synthetisieren, die diese Clifford-Schaltung implementiert. Die eigentliche Synthese wird auf einen späteren HighLevelSynthesis transpilierungsdurchgang verschoben.

    Zum Beispiel der folgende Code:

    from qiskit import QuantumCircuit
    from qiskit.quantum_info import random_clifford
    
    qc = QuantumCircuit(3)
    cliff = random_clifford(2)
    qc.append(cliff, [0, 1])

    konvertiert cliff nicht mehr in qiskit.circuit.Instructionum, was die Synthese des Clifford in eine Schaltung einschließt, wenn sie an qc angehängt wird.

  • Ein neuer Transpiler-Pass wurde hinzugefügt OptimizeCliffords der Blöcke von aufeinanderfolgenden Clifford objekten in einer Schaltung sammelt und jeden Block durch einen einzelnen Clifford.

    Zum Beispiel der folgende Code:

    from qiskit import QuantumCircuit
    from qiskit.quantum_info import random_clifford
    from qiskit.transpiler.passes import OptimizeCliffords
    from qiskit.transpiler import PassManager
    
    qc = QuantumCircuit(3)
    cliff1 = random_clifford(2)
    cliff2 = random_clifford(2)
    qc.append(cliff1, [2, 1])
    qc.append(cliff2, [2, 1])
    qc_optimized = PassManager(OptimizeCliffords()).run(qc)

    speichert zunächst die beiden Cliffords cliff1 und cliff2 auf qc als "übergeordnete" Objekte, und dann optimiert der Transpiler-Pass OptimizeCliffords optimiert die Schaltung, indem er diese beiden Cliffords zu einem einzigen Clifford zusammensetzt. Beachten Sie, dass die resultierende Clifford-Datei immer noch auf qc als übergeordnetes Objekt gespeichert wird. Dieser Pass ist noch nicht in einem der voreingestellten Passmanager enthalten.

  • Hinzufügen eines neuen Transpiler-Passes HighLevelSynthesis der Objekte auf höherer Ebene synthetisiert (zum Beispiel, Clifford objekte).

    Zum Beispiel der folgende Code:

    from qiskit import QuantumCircuit
    from qiskit.quantum_info import random_clifford
    from qiskit.transpiler import PassManager
    from qiskit.transpiler.passes import HighLevelSynthesis
    
    qc = QuantumCircuit(3)
    qc.h(0)
    cliff = random_clifford(2)
    qc.append(cliff, [0, 1])
    
    qc_synthesized = PassManager(HighLevelSynthesis()).run(qc)

    synthetisiert den in qc gespeicherten Clifford-Satz höherer Ebene unter Verwendung der Standardfunktion decompose_clifford() .

    Dieser neue Transpiler-Pass HighLevelSynthesis ist in die voreingestellten Passmanager integriert und läuft direkt nach UnitarySynthesis pass. Daher, transpile() alle in der Schaltung vorhandenen Cliffords höherer Ebene synthetisieren.

    Es ist wichtig zu beachten, dass die Arbeit, die für die Speicherung von Clifford objekte als "higher-level" Objekte zu speichern und diese Objekte mit HighLevelSynthesis pass völlig transparent sein sollte und keine Codeänderungen erforderlich sind.

  • SparsePauliOps können nun mit Koeffizientenarrays konstruiert werden, die allgemeine Python Objekte sind. Dies ist für die Verwendung mit ParameterExpression objekten gedacht; andere Objekte können funktionieren, haben aber keine erstklassige Unterstützung. Einige SparsePauliOp methoden (wie z.B. die Konvertierung in andere Klassendarstellungen) funktionieren bei der Verwendung von object Arrays möglicherweise nicht, wenn das gewünschte Ziel diese allgemeinen Arrays nicht darstellen kann.

    Zum Beispiel, ein ParameterExpression SparsePauliOp könnte konstruiert werden durch:

    import numpy as np
    from qiskit.circuit import Parameter
    from qiskit.quantum_info import SparsePauliOp
    
    print(SparsePauliOp(["II", "XZ"], np.array([Parameter("a"), Parameter("b")])))

    das ergibt

    SparsePauliOp(['II', 'XZ'],
          coeffs=[ParameterExpression(1.0*a), ParameterExpression(1.0*b)])
  • Eine neue Funktion wurde hinzugefügt plot_distribution() zum Plotten von Verteilungen über Quasi-Wahrscheinlichkeiten hinzugefügt. Diese ist geeignet für Counts, QuasiDistribution und ProbDistribution. Rohdiktat kann auch weitergegeben werden. Zum Beispiel:

    from qiskit.visualization import plot_distribution
    
    quasi_dist = {'0': .98, '1': -.01}
    plot_distribution(quasi_dist)
  • Es wurde eine neue High-Level-Synthese-Plugin-Schnittstelle eingeführt, die es ermöglicht, alternative Synthesetechniken, die in externen Paketen enthalten sind, nahtlos mit dem HighLevelSynthesis transpiler-Durchlauf. Diese alternativen Synthesetechniken können für beliebige "übergeordnete" Objekte vom Typ Operationspezifiziert werden, wie zum Beispiel für Clifford und LinearFunction objekte. Diese Plugin-Schnittstelle ähnelt derjenigen für die unitäre Synthese. Im letzteren Fall finden Sie die Einzelheiten zum Schreiben eines neuen Plugins in der qiskit.transpiler.passes.synthesis.plugin modul-Dokumentation.

  • Einführung einer neuen Klasse HLSConfig , die verwendet werden kann, um alternative Synthesealgorithmen für "übergeordnete" Objekte vom Typ Operation. Für jedes übergeordnete Objekt von Interesse gibt ein Objekt HLSConfig eine Liste von Synthesemethoden und deren Argumente an. Dieses Objekt kann an HighLevelSynthesis transpiler pass übergeben oder als Parameter angegeben werden hls_config in transpile().

    Nehmen wir als Beispiel an, dass op_a und op_b die Namen von zwei übergeordneten Objekten sind, dass op_a-Objekte zwei Synthesemethoden default haben, die keine zusätzlichen Parameter erfordern, und other mit zwei optionalen ganzzahligen Parametern option_1 und option_2, dass op_b-Objekte eine einzige Synthesemethode default haben und qc ein Quantenschaltkreis ist, der op_a und op_b Objekte enthält. Der folgende Codeschnipsel:

    hls_config = HLSConfig(op_b=[("other", {"option_1": 7, "option_2": 4})])
    pm = PassManager([HighLevelSynthesis(hls_config=hls_config)])
    transpiled_qc = pm.run(qc)

    zeigt, wie die alternative Synthesemethode other für op_b-Objekte ausgeführt wird, während für alle anderen High-Level-Objekte, einschließlich op_a-Objekte, die Methoden default verwendet werden.

  • Neue Methoden zur Ausführung von Primitiven hinzugefügt: BaseSampler.run() und BaseEstimator.run(). Diese Methoden werden asynchron ausgeführt und geben JobV1 objekte zurück, die ein Handle für die Ausnahmen bereitstellen. Diese neuen Laufmethoden können übergeben werden QuantumCircuit objekte (und Observables für BaseEstimator) übergeben werden, die nicht im Konstruktor registriert sind. Zum Beispiel:

    estimator = Estimator()
    result = estimator.run(circuits, observables, parameter_values).result()

    Dies bietet eine Alternative zum früheren Ausführungsmodell (das jetzt veraltet ist) für die BaseSampler und BaseEstimator primitive, die alle Eingaben über den Konstruktor entgegennehmen und das primitive Objekt mit der Kombination dieser Eingabeparameter aufrufen, die bei der Ausführung verwendet werden soll.

  • Option shots für Referenzimplementierungen von Primitiven hinzugefügt. Zufallszahlen können durch die Angabe seed_primitive festgelegt werden. Zum Beispiel:

    from qiskit.primitives import Sampler
    from qiskit import QuantumCircuit
    
    bell = QuantumCircuit(2)
    bell.h(0)
    bell.cx(0, 1)
    bell.measure_all()
    
    with Sampler(circuits=[bell]) as sampler:
        result = sampler(circuits=[0], shots=1024, seed_primitive=15)
        print([q.binary_probabilities() for q in result.quasi_dists])
  • Die Konstruktoren für die BaseSampler und BaseEstimator haben ein neues optionales Schlüsselwortargument, options , das verwendet wird, um die Standardwerte für die Optionen festzulegen, die über das options attribut.

  • Hinzufügen der PVQD klasse zu dem Zeitentwicklungs-Framework in qiskit.algorithms. Diese Klasse implementiert den projizierten Variational Quantum Dynamics (p-VQD) Algorithmus von Barison et al.

    In jedem Zeitschritt berechnet dieser Algorithmus den nächsten Zustand mit einer Trotter-Formel und projiziert ihn auf eine Variationsform. Die Projektion wird durch die Maximierung der Genauigkeit des von Trotter entwickelten Zustands und des Ansatzes unter Verwendung einer klassischen Optimierungsroutine bestimmt.

    import numpy as np
    
    from qiskit.algorithms.state_fidelities import ComputeUncompute
    from qiskit.algorithms.evolvers import EvolutionProblem
    from qiskit.algorithms.time_evolvers.pvqd import PVQD
    from qiskit.primitives import Estimator, Sampler
    from qiskit import BasicAer
    from qiskit.circuit.library import EfficientSU2
    from qiskit.quantum_info import Pauli, SparsePauliOp
    from qiskit.algorithms.optimizers import L_BFGS_B
    
    sampler = Sampler()
    fidelity = ComputeUncompute(sampler)
    estimator = Estimator()
    hamiltonian = 0.1 * SparsePauliOp([Pauli("ZZ"), Pauli("IX"), Pauli("XI")])
    observable = Pauli("ZZ")
    ansatz = EfficientSU2(2, reps=1)
    initial_parameters = np.zeros(ansatz.num_parameters)
    
    time = 1
    optimizer = L_BFGS_B()
    
    # setup the algorithm
    pvqd = PVQD(
        fidelity,
        ansatz,
        initial_parameters,
        estimator,
        num_timesteps=100,
        optimizer=optimizer,
    )
    
    # specify the evolution problem
    problem = EvolutionProblem(
        hamiltonian, time, aux_operators=[hamiltonian, observable]
    )
    
    # and evolve!
    result = pvqd.evolve(problem)
  • Die Methode QNSPSA.get_fidelity() statische Methode unterstützt nun ein optionales sampler Argument, das verwendet wird, um eine Implementierung der BaseSampler schnittstelle (z.B Sampler, BackendSampler, oder beliebige Provider-Implementierungen wie die in qiskit-ibm-runtime und qiskit-aer) zur Berechnung der Treue eines QuantumCircuit. Zum Beispiel:

    from qiskit.primitives import Sampler
    from qiskit.algorithms.optimizers import QNSPSA
    
    fidelity = QNSPSA.get_fidelity(my_circuit, Sampler())
  • Ein neues Schlüsselwortargument sampler wurde zu den Konstruktoren der Phasenschätzungsklassen hinzugefügt:

    Dieses Argument wird verwendet, um eine Implementierung der BaseSampler schnittstelle wie Sampler, BackendSampleroder beliebige Provider-Implementierungen, wie sie in qiskit-ibm-runtime und qiskit-aer zu finden sind.

    Zum Beispiel:

    from qiskit.primitives import Sampler
    from qiskit.algorithms.phase_estimators import HamiltonianPhaseEstimation
    from qiskit.synthesis import MatrixExponential
    from qiskit.quantum_info import SparsePauliOp
    from qiskit.opflow import PauliSumOp
    
    
    sampler = Sampler()
    num_evaluation_qubits = 6
    phase_est = HamiltonianPhaseEstimation(
        num_evaluation_qubits=num_evaluation_qubits, sampler=sampler
    )
    
    hamiltonian = PauliSumOp(SparsePauliOp.from_list([("X", 0.5), ("Y", 0.6), ("I", 0.7)]))
    result = phase_est.estimate(
        hamiltonian=hamiltonian,
        state_preparation=None,
        evolution=MatrixExponential(),
        bound=1.05,
    )
  • Der SabreSwap transpiler-Pass hat die Laufzeitleistung durch eine Neuformulierung des Algorithmus in Rust erheblich verbessert.

  • Symbolische Impuls-Unterklassen Gaussian, GaussianSquare, Drag und Constant wurden dahingehend aktualisiert, dass sie SymbolicPulse und nicht die Unterklasse selbst instanziieren. Alle parametrischen Impulsobjekte in Impulsprogrammen müssen symbolische Impulsinstanzen sein, da eine Unterklassifizierung nicht mehr erforderlich ist. Beachten Sie, dass SymbolicPulse einen bestimmten Umschlag mit dem in SymbolicPulse.envelope definierten symbolischen Ausdrucksobjekt eindeutig identifizieren kann.

  • Eine neue Funktion wurde hinzugefügt, sampled_expectation_value(), die die Berechnung von Erwartungswerten für Diagonaloperatoren aus Verteilungen wie Counts und QuasiDistribution. Gültige Operatoren für die Verwendung mit dieser Funktion sind: str, Pauli, PauliOp, PauliSumOp, und SparsePauliOp.

  • A SamplingVQE klasse wird eingeführt, die für diagonale Hamiltonianer optimiert ist und ein sampler Primitiv nutzt. A QAOA klasse hinzugefügt, die die Unterklasse SamplingVQE ist.

    Um die neue SamplingVQE mit einem Referenzprimitiv zu verwenden, kann man z.B. Folgendes tun:

    from qiskit.algorithms.minimum_eigensolvers import SamplingVQE
    from qiskit.algorithms.optimizers import SLSQP
    from qiskit.circuit.library import TwoLocal
    from qiskit.primitives import Sampler
    from qiskit.opflow import PauliSumOp
    from qiskit.quantum_info import SparsePauliOp
    
    operator = PauliSumOp(SparsePauliOp(["ZZ", "IZ", "II"], coeffs=[1, -0.5, 0.12]))
    
    sampler = Sampler()
    ansatz = TwoLocal(rotation_blocks=["ry", "rz"], entanglement_blocks="cz")
    optimizer = SLSQP()
    
    sampling_vqe = SamplingVQE(sampler, ansatz, optimizer)
    result = sampling_vqe.compute_minimum_eigenvalue(operator)
    eigenvalue = result.eigenvalue

    Man beachte, dass die ausgewerteten Hilfsoperatoren jetzt über das aux_operators_evaluated -Feld der Ergebnisse erhalten werden. Diese besteht aus einer Liste oder einem Diktat von Tupeln, die die Erwartungswerte für diese Operatoren sowie die Metadaten des primitiven Laufs enthalten. aux_operator_eigenvalues ist nicht länger ein gültiges Feld.

  • Ein neues atol Schlüsselwortargument wurde der SparsePauliOp.equiv() methode hinzugefügt, um die Toleranz der Äquivalenzprüfung anzupassen,

  • Es wurde eine neue Plugin-Schnittstelle für Transpiler-Stufen eingeführt, die dazu dient, alternative PassManager objekte aus einem externen Paket in einer bestimmten Stufe als Teil von transpile() oder der StagedPassManager ausgabe von generate_preset_pass_manager(), level_0_pass_manager(), level_1_pass_manager(), level_2_pass_manager(), und level_3_pass_manager(). Benutzer können ein Plugin für eine Transpiler-Stufe mit den Schlüsselwortargumenten init_method, layout_method, routing_method, translation_method, optimization_method, und scheduling_method auf transpile() und generate_preset_pass_manager(). Eine vollständige Liste der derzeit installierten Plugin-Namen finden Sie mit der list_stage_plugins() funktion. Für die Erstellung von Plugins lesen Sie bitte die qiskit.transpiler.preset_passmanagers.plugin modul-Dokumentation, die einen Leitfaden für die Erstellung von Bühnen-Plugins enthält.

  • Das Programm transpile() hat zwei neue Schlüsselwortargumente, init_method und optimization_method , die zur Angabe alternativer Plugins für die Stufen init bzw. optimization verwendet werden.

  • Die Klasse PassManagerConfig klasse hat 2 neue Attribute, init_method und optimization_method , zusammen mit passenden Schlüsselwortargumenten für die Konstruktormethoden. Diese stellen die vom Benutzer angegebenen init und optimization Plugins dar, die für die Kompilierung verwendet werden sollen.

  • Die SteppableOptimizer klasse wird hinzugefügt. Sie ermöglicht es, klassische Optimierungen Schritt für Schritt mit der step() methode. Diese Optimierer implementieren die "ask and tell"-Schnittstelle, die es (optional) ermöglicht, die erforderlichen Funktions- oder Gradientenauswertungen manuell zu berechnen und in den Optimierer zurückzuspeisen. Weitere Informationen über diese Schnittstelle finden Sie unter: ask and tell interface. Ein sehr einfacher Anwendungsfall, bei dem der Benutzer die Optimierung Schritt für Schritt durchführen möchte, ist das Auslesen:

    import random
    import numpy as np
    from qiskit.algorithms.optimizers import GradientDescent
    
    def objective(x):
          return (np.linalg.norm(x) - 1) ** 2
    
    def grad(x):
          return 2 * (np.linalg.norm(x) - 1) * x / np.linalg.norm(x)
    
    
    initial_point = np.random.normal(0, 1, size=(100,))
    
    optimizer = GradientDescent(maxiter=20)
    optimizer.start(x0=initial_point, fun=objective, jac=grad)
    
    for _ in range(maxiter):
        state = optimizer.state
        # Here you can manually read out anything from the optimizer state.
        optimizer.step()
    
    result = optimizer.create_result()

    Ein komplexerer Fall wäre die Fehlerbehandlung. Stellen Sie sich vor, dass die Funktion, die Sie auswerten, eine zufällige Fehlerwahrscheinlichkeit hat. In diesem Fall können Sie den Fehler abfangen und die Funktion erneut ausführen, bis sie das gewünschte Ergebnis liefert, bevor Sie den Optimierungsprozess fortsetzen. In diesem Fall würde man die "ask and tell"-Schnittstelle verwenden.

    import random
    import numpy as np
    from qiskit.algorithms.optimizers import GradientDescent
    
    def objective(x):
        if random.choice([True, False]):
            return None
        else:
            return (np.linalg.norm(x) - 1) ** 2
    
    def grad(x):
        if random.choice([True, False]):
            return None
        else:
            return 2 * (np.linalg.norm(x) - 1) * x / np.linalg.norm(x)
    
    
    initial_point = np.random.normal(0, 1, size=(100,))
    
    optimizer = GradientDescent(maxiter=20)
    optimizer.start(x0=initial_point, fun=objective, jac=grad)
    
    while optimizer.continue_condition():
        ask_data = optimizer.ask()
        evaluated_gradient = None
    
        while evaluated_gradient is None:
            evaluated_gradient = grad(ask_data.x_center)
            optimizer.state.njev += 1
    
        optmizer.state.nit += 1
    
        cf  = TellData(eval_jac=evaluated_gradient)
        optimizer.tell(ask_data=ask_data, tell_data=tell_data)
    
    result = optimizer.create_result()

    Übergang von GradientDescent zu einer Unterklasse von SteppableOptimizer.

  • Die Methode subset_fitter wird der Klasse TensoredMeasFitter klasse hinzugefügt. Die Implementierung ist auf Entschärfungsmuster beschränkt, bei denen jedes Qubit einzeln entschärft wird, z.B. [[0], [1], [2]]. Dies ist jedoch der am häufigsten verwendete Fall. Es ermöglicht die TensoredMeasFitter in Fällen verwendet werden, in denen die numerische Reihenfolge der physikalischen Qubits nicht mit dem Index des klassischen Bits übereinstimmt.

  • Kontrollflussoperationen werden nun durch den Transpiler auf den Optimierungsstufen 0 und 1 unterstützt (z.B. Aufruf von transpile() oder generate_preset_pass_manager() mit dem Schlüsselwortargument optimization_level=1). Man kann nun eine Schaltung wie folgt konstruieren

    from qiskit import QuantumCircuit
    
    qc = QuantumCircuit(2, 1)
    qc.h(0)
    qc.measure(0, 0)
    with qc.if_test((0, True)) as else_:
      qc.x(1)
    with else_:
      qc.y(1)

    und dies erfolgreich umsetzen, z. B. durch:

    from qiskit import transpile
    from qiskit_aer import AerSimulator
    
    backend = AerSimulator(method="statevector")
    transpiled = transpile(qc, backend)

    Die verfügbaren Werte für das Schlüsselwortargument layout_method sind "trivial" und "dicht". Für routing_method stehen die Optionen "stochastisch" und "keine" zur Verfügung. Die Übersetzung (translation_method) kann mit "translator" oder "unroller" vorgenommen werden. Die Optimierungsebenen 2 und 3 werden noch nicht mit Kontrollfluss unterstützt, ebenso wenig wie das Circuit Scheduling (d.h. die Bereitstellung eines Wertes für scheduling_method), obwohl wir beabsichtigen, die Unterstützung für diese und die anderen Layout-, Routing- und Übersetzungsmethoden in späteren Versionen von Qiskit Terra zu erweitern.

    Damit die Transpilierung mit Kontrollflussoperationen mit einem Backend erfolgreich sein kann, muss das Backend die erforderlichen Kontrollflussoperationen in seiner angegebenen Basis haben. Qiskit Aer, zum Beispiel, tut dies. Wenn Sie solche Transpilierungen einfach nur ausprobieren wollen, sollten Sie das Argument basis_gates überschreiben transpile().

  • Die folgenden Transpilerdurchläufe wurden alle unterrichtet, um Kontrollflusskonstrukte in Form von ControlFlowOp anweisungen in einer Schaltung:


    Layoutbezogen


    Routing-bezogen


    Übersetzungsbezogen


    Optimierungsbezogen

    Diese Pässe werden am häufigsten über die voreingestellten Passmanager verwendet (die intern von transpile() und generate_preset_pass_manager()), aber sie sind auch für andere Zwecke verfügbar. Diese Durchläufe werden nun gegebenenfalls in Kontrollflussoperationen zurückgeführt, wobei die internen Blöcke aktualisiert oder analysiert werden.

  • Hinzufügen einer neuen TrotterQRTE klasse hinzugefügt, die die RealTimeEvolver schnittstelle implementiert, die eine qiskit.primitives.BaseEstimator um die Berechnung durchzuführen. Diese neue Klasse ersetzt die bisher verfügbare qiskit.algorithms.TrotterQRTE klasse (die veraltet ist und in zukünftigen Versionen entfernt werden wird), die eine Backend oder QuantumInstance für die Berechnung verwendete.

  • DAGCircuit.substitute_node_with_dag() nimmt jetzt propagate_condition als Schlüsselwortargument. Die Standardeinstellung ist True, was das vorherige Verhalten war, und kopiert jede Bedingung des zu ersetzenden Knotens auf jeden Operationsknoten in der Ersetzung. Bei False wird die Bedingung nicht kopiert, so dass ein bedingter Knoten durch einen Unter-DAG ersetzt werden kann, der die Bedingung bereits korrekt implementiert.

  • DAGCircuit.substitute_node_with_dag() kann jetzt sowohl eine Abbildung für den Parameter wires als auch eine Sequenz annehmen. Das Mapping sollte Bits in der Ersatz-DAG auf die Bits in der DAG, in die sie eingefügt wird, abbilden. Dies ermöglicht eine einfachere Konstruktion für den Aufrufer, wenn der Eingabeknoten sowohl klassische Bits als auch eine Bedingung hat und die Ersatz-DAG diese in ungeordneter Reihenfolge verwenden kann.

  • Hinzufügen des qiskit.algorithms.minimum_eigensolvers paket, um Schnittstellen für primitiv-aktivierte Algorithmen aufzunehmen. VQE wurde in dieser Implementierung umgestaltet, um Primitive zu nutzen.

    Um die neue Implementierung mit einem Referenzprimitiv zu verwenden, kann man z. B. Folgendes tun

    from qiskit.algorithms.minimum_eigensolvers import VQE
    from qiskit.algorithms.optimizers import SLSQP
    from qiskit.circuit.library import TwoLocal
    from qiskit.primitives import Estimator
    from qiskit.quantum_info import SparsePauliOp
    
    h2_op = SparsePauliOp(
        ["II", "IZ", "ZI", "ZZ", "XX"],
        coeffs=[
            -1.052373245772859,
            0.39793742484318045,
            -0.39793742484318045,
            -0.01128010425623538,
            0.18093119978423156,
        ],
    )
    
    estimator = Estimator()
    ansatz = TwoLocal(rotation_blocks=["ry", "rz"], entanglement_blocks="cz")
    optimizer = SLSQP()
    
    vqe = VQE(estimator, ansatz, optimizer)
    result = vqe.compute_minimum_eigenvalue(h2_op)
    eigenvalue = result.eigenvalue

    Man beachte, dass die ausgewerteten Hilfsoperatoren jetzt über das aux_operators_evaluated -Feld der Ergebnisse erhalten werden. Diese besteht aus einer Liste oder einem Diktat von Tupeln, die die Erwartungswerte für diese Operatoren sowie die Metadaten des primitiven Laufs enthalten. aux_operator_eigenvalues ist nicht länger ein gültiges Feld.

Anmerkungen zu Upgrades

  • Für Target objekten, die nur global definierte 2-Qubit-Operationen ohne jegliche Konnektivitätskonstanten enthalten, wird die Rückgabe der Target.build_coupling_map() methode nun None zurück, anstatt ein CouplingMap objekts, das num_qubits Knoten und keine Kanten enthält. Diese Änderung wurde vorgenommen, um die tatsächlichen Konnektivitätseinschränkungen des Systems besser widerzuspiegeln Target widerzuspiegeln, denn in diesem Fall gibt es keine Konnektivitätseinschränkungen für das Backend, das durch die Targetmodelliert wird, und nicht ein Mangel an Konnektivität. Wenn Sie aus irgendeinem Grund das frühere Verhalten wünschen, können Sie es reproduzieren, indem Sie z. B. nach einer None -Rückgabe suchen und manuell eine Kopplungskarte erstellen:

    from qiskit.transpiler import Target, CouplingMap
    from qiskit.circuit.library import CXGate
    
    target = Target(num_qubits=3)
    target.add_instruction(CXGate())
    cmap = target.build_coupling_map()
    if cmap is None:
        cmap = CouplingMap()
        for i in range(target.num_qubits):
            cmap.add_physical_qubit(i)
  • Der Standardwert für das Schlüsselwortargument entanglement im Konstruktor für die RealAmplitudes und EfficientSU2 klassen wurde von "full" auf "reverse_linear" geändert. Diese Änderung wurde vorgenommen, weil die Ausgangsschaltung äquivalent ist, aber nur n−1n-1 anstelle von n(n−1)2\frac{n(n-1)}{2} verwendet CXGate gatter. Wenn Sie die frühere Standardeinstellung wünschen, können Sie beim Aufruf eines der beiden Konstruktoren explizit entanglement="full" angeben.

  • Eine Validierungsprüfung wurde zu BaseSampler.run(). Es wird ein Fehler ausgegeben, wenn es kein klassisches Bit gibt.

  • Das Verhalten der call() pulse builder Funktion wurde verbessert. Wenn eine ScheduleBlock instanz von dieser Methode aufgerufen wird, erzeugt sie intern eine Reference im aktuellen Kontext und ordnet das aufgerufene Programm sofort der Referenz zu. Daher wird der Call anweisung nicht mehr erzeugt. Zusammen mit dieser Änderung ist es verboten, verschiedene Blöcke mit demselben name Argument aufzurufen. Ein solcher Vorgang führt zu einem Fehler.

  • Für die meisten Architekturen, beginnend mit der nächsten Version von Qiskit Terra, 0.23, wird das tweedledum Paket zu einer optionalen Abhängigkeit, statt zu einer Voraussetzung. Dies wird derzeit von einigen klassischen Phasenorakelfunktionen verwendet. Wenn Ihre Anwendung oder Bibliothek diese Funktionalität benötigt, sollten Sie sich vorbereiten, indem Sie tweedledum sofort zu den Abhängigkeiten Ihres Pakets hinzufügen.

    tweedledum ist ab sofort in Qiskit Terra 0.22 keine Voraussetzung mehr auf macOS arm64 ( M1 ). Das liegt daran, dass die mitgelieferten Räder für diese Plattform kaputt sind und die Erstellung aus der sdist für die meisten Leute nicht zuverlässig ist. Wenn Sie eine funktionierende Version von tweedledum manuell installieren, werden alle abhängigen Funktionen weiterhin funktionieren.

  • Das Attribut ._layout des Objekts QuantumCircuit objekts wurde von der Speicherung eines Layout objekt zu einer Datenklasse mit 2 Attributen, initial_layout , die ein Layout objekt für das anfängliche Layout, das während der Kompilierung festgelegt wurde, und input_qubit_mapping , das ein Wörterbuch enthält, das die Qubits den Positionsindizes in der ursprünglichen Schaltung zuordnet. Diese Änderung war notwendig, um alle Informationen bereitzustellen, damit ein nachgeschalteter Schaltkreis in der Lage ist, die durch die ursprüngliche Anordnung verursachte Permutation in allen Situationen vollständig umzukehren. Dieses Attribut ist zwar privat und sollte nicht extern verwendet werden, aber es ist die einzige Möglichkeit, das ursprüngliche Layout durch transpile() zu verfolgen, daher wird die Änderung dokumentiert, falls Sie sich darauf verlassen. Wenn Sie einen Anwendungsfall für das Attribut _layout haben, der von der Qiskit-API nicht abgedeckt wird, öffnen Sie bitte ein Problem, damit wir diese Funktionslücke schließen können.

  • Die Konstruktoren für die SetPhase, ShiftPhase, SetFrequency, und ShiftFrequency klassen lösen nun eine PulseError wenn der über das Argument channel übergebene Wert keine Instanz von PulseChannel ist. Diese Änderung wurde vorgenommen, um sicherzustellen, dass die Eingaben in die Konstruktoren gültig sind, da die Anweisungen nur für Impulskanäle und nicht für andere Arten von Kanälen gültig sind.

  • Die Funktion plot_histogram() funktion wurde so geändert, dass sie ein tatsächliches Histogramm mit diskreten, gebündelten Werten zurückgibt. Das bisherige Verhalten der Funktion bestand darin, trotz des Namens tatsächlich eine Visualisierung der Verteilung der Eingaben zu erzeugen. Aufgrund dieser Diskrepanz zwischen dem Namen der Funktion und dem Verhalten wurde das Verhalten der Funktion geändert, so dass sie jetzt tatsächlich ein richtiges Histogramm diskreter Daten erzeugt. Wenn Sie das bisherige Verhalten der Darstellung einer Wahrscheinlichkeitsverteilung der Zähldaten beibehalten möchten, können Sie die Funktion plot_distribution() verwenden, um ein entsprechendes Diagramm zu erstellen. Zum Beispiel kann das frühere Verhalten von plot_histogram({'00': 512, '11': 500}) mit wiederhergestellt werden:

    from qiskit.visualization import plot_distribution
    import matplotlib.pyplot as plt
    
    ax = plt.subplot()
    plot_distribution({'00': 512, '11': 500}, ax=ax)
    ax.set_ylabel('Probabilities')
  • Die Kontexte qiskit.pulse.builder inline und pad wurden entfernt. Diese wurden erstmals in Terra 0.18.0 (Juli 2021) veraltet. Es gibt keinen Ersatz für inline; man kann die Impulse einfach in das enthaltende Scope schreiben. Der Kontextmanager pad hat keine Auswirkungen mehr, da er veraltet ist.

  • Die Ausgabe des SabreSwap'sabre' transpiler-Durchlaufs (auch wenn optimization_level=3 oder routing_method oder layout_method beim Aufruf von transpile()) mit einem festen Seed-Wert kann sich gegenüber früheren Versionen ändern. Dies ist auf die Verwendung eines neuen Zufallszahlengenerators zurückzuführen, der im Rahmen der Neuschreibung des SabreSwap passes in Rust verwendet wird, der die Leistung erheblich verbessert hat. Wenn Sie auf eine konsistente Ausgabe angewiesen sind, können Sie den Durchlauf in einer früheren Version von Qiskit durchführen und die Funktion qiskit.qpy verwenden, um den Schaltkreis zu speichern und ihn dann mit der aktuellen Version zu laden.

  • Das Layout.add() verhalten, wenn keine physical_bit angegeben wird, hat sich gegenüber früheren Versionen geändert. In früheren Versionen wurde je nach Länge des Objekts ein neues physisches Bit hinzugefügt Layout objekts. Wenn Sie zum Beispiel eine Layout mit den physikalischen Bits 1 und 3 haben, würden aufeinanderfolgende Aufrufe von add() würden die physikalischen Bits 2, 4, 5, 6 usw. hinzugefügt. Wären die physischen Bits 2 und 3, würden die aufeinander folgenden Aufrufe 4, 5, 6, 7 usw. ergeben. Dies wurde so geändert, dass stattdessen Layout.add() zunächst alle fehlenden physikalischen Bits zwischen 0 und dem maximalen physikalischen Bit in der Layout. Für das Beispiel 1 und 3 werden also 0, 2, 4, 5 und für das Beispiel 2 und 3 werden 0, 1, 4, 5 zu den Layout. Diese Änderung wurde vorgenommen, um die Vorhersagbarkeit des Ergebnisses zu erhöhen und um eine Reihe von Fehlern zu beheben, die durch das unerwartete Verhalten verursacht wurden. Da physikalische Bits auf einem Backend immer zusammenhängende Sequenzen von 0 bis nn sind, könnte das Hinzufügen neuer Bits, wenn noch ungenutzte physikalische Bits vorhanden sind, dazu führen, dass das Layout mehr Bits verwendet als auf dem Backend verfügbar sind. Wenn Sie das vorherige Verhalten wünschen, können Sie das gewünschte physikalische Bit manuell beim Aufruf von Layout.add().

  • Das veraltete Attribut Methode SparsePauliOp.table wurde entfernt. Ursprünglich war sie in Qiskit Terra 0.19 veraltet. Stattdessen sollte die Methode paulis() verwendet werden.

  • Die Unterstützung für die Rückgabe einer PauliTable aus der pauli_basis() funktion wurde entfernt. In ähnlicher Weise wird das Argument pauli_list der Funktion pauli_basis() funktion, das verwendet wurde, um zu einem PauliList (jetzt der einzige Rückgabetyp) wurde entfernt. Diese Funktion wurde in der Version Qiskit Terra 0.19 veraltet.

  • Die gefälschten Backend-Objekte FakeJohannesburg, FakeJohannesburgV2, FakeAlmaden, FakeAlmadenV2, FakeSingapore, und FakeSingaporeV2 enthalten nicht mehr die Impuls-Standardnutzlasten. Dies bedeutet für die BackendV1 basierten Klassen die Methode BackendV1.defaults() und die Impulssimulation über BackendV1.run() nicht mehr verfügbar ist. Für BackendV2 basierten Klassen wird die Eigenschaft calibration für Anweisungen in der Target nicht mehr aufgefüllt. Diese Änderung wurde vorgenommen, weil diese Systeme aufgrund der Verwendung von abgetasteten Wellenformen anstelle von parametrischen Impulsdefinitionen übermäßig große Impulsvorgaben hatten (insgesamt ~50MB ). Diese drei Nutzdateien beanspruchten mehr als 50 % des für die Installation von qiskit-terra benötigten Speicherplatzes. Wenn man den potenziellen Wert der Kompilierung mit Impulsbewusstsein oder der Impulssimulation dieser ausgemusterten Geräte gegeneinander abwägt, ist die Dateigröße die Kosten nicht wert. Wenn Sie diese Eigenschaften nutzen möchten, können Sie eine ältere Version von Qiskit verwenden und mit Hilfe von qpy verwenden, um Schaltkreise aus älteren Versionen von Qiskit in die aktuelle Version zu übertragen.

  • isinstance mit Pulsklassen prüfen Gaussian, GaussianSquare, Drag und Constant wird für ungültig erklärt, da diese Puls-Unterklassen nicht mehr instanziiert werden. Sie funktionieren noch in Terra 0.22, aber Sie sollten sofort mit der Umstellung beginnen. Anstelle von Typinformationen sollte SymbolicPulse.pulse_type verwendet werden. Es wird davon ausgegangen, dass dies ein eindeutiger String-Identifikator für Impulshüllkurven ist, und wir können String-Gleichheit verwenden, um die Impulstypen zu untersuchen. Beispiel:

    from qiskit.pulse.library import Gaussian
    
    pulse = Gaussian(160, 0.1, 40)
    
    if isinstance(pulse, Gaussian):
      print("This is Gaussian pulse.")

    Dieser Code sollte aktualisiert werden zu

    from qiskit.pulse.library import Gaussian
    
    pulse = Gaussian(160, 0.1, 40)
    
    if pulse.pulse_type == "Gaussian":
      print("This is Gaussian pulse.")

    Aus demselben Grund sollte auf die Klassenattribute wie pulse.__class__.__name__ nicht zugegriffen werden, um Informationen über den Impulstyp zu erhalten.

  • Die Ausnahme qiskit.exceptions.QiskitIndexError wurde entfernt und existiert nicht mehr, wie in der Deprecation Notice von qiskit-terra 0.18.0 (veröffentlicht am 12. Juli 2021) beschrieben.

  • Die veralteten Argumente epsilon und factr für den Konstruktor der L_BFGS_B optimizer-Klasse wurden entfernt. Diese Argumente wurden ursprünglich als Teil der 0.18.0 Version (veröffentlicht am 12. Juli 2021) veraltet. Stattdessen sollte das Argument ftol verwendet werden. Nähere Informationen über die Beziehung zwischen diesen Argumenten finden Sie in der Scipy-Dokumentation über den Optimierer.

  • Die voreingestellten Passmanager für die Ebenen 1 und 2, die verwendet werden, wenn optimization_level=1 oder optimization_level=2 mit transpile() oder generate_preset_pass_manager() und der Ausgabe von level_1_pass_manager() und level_2_pass_manager()ausgegeben werden, verwenden nun SabreLayout und SabreSwap standardmäßig anstelle der bisherigen Voreinstellungen DenseLayout und StochasticSwap. Diese Änderung wurde vorgenommen, um die Ausgabequalität des Transpilers zu verbessern; die SabreLayout und SabreSwap Kombination führt in der Regel dazu, dass weniger SwapGate objekte in die Ausgabeschaltung eingefügt werden. Wenn Sie die vorherigen Standardpässe verwenden möchten, können Sie layout_method='dense' und routing_method='stochastic' auf transpile() oder generate_preset_pass_manager() zur Nutzung von DenseLayout und StochasticSwap setzen.

  • Die implizite Verwendung von approximation_degree!=1.0 als Standard in der transpile() funktion, wenn optimization_level=3 gesetzt ist, wurde deaktiviert. Der Transpiler sollte standardmäßig die Einheitlichkeit der Eingabe bis zu bekannten Transformationen wie einseitigen Permutationen und Ähnlichkeitstransformationen erhalten. Dies wurde durch die frühere Verwendung von approximation_degree=None unterbrochen, was in Fällen wie der trotterisierten Evolution mit vielen Zeitschritten zu falschen Ergebnissen führte, bei denen die Unitarien übermäßig angenähert wurden, was zu falschen Ergebnissen führte. Es wurde beschlossen, dass Transformationen, die die unitäre Äquivalenz aufheben, vom Benutzer explizit aktiviert werden sollten. Wenn Sie das frühere Standardverhalten wünschen, bei dem synthetisierte UnitaryGate Anweisungen bis zu den Fehlerraten der nativen Anweisungen des Ziel-Backends angenähert werden, können Sie explizit approximation_degree=None setzen, wenn Sie transpile() mit optimization_level=3 zum Beispiel:

    transpile(circuit, backend, approximation_degree=None, optimization_level=3)
  • Ändern Sie den Standardwert für die maximale Anzahl zulässiger Funktionsbewertungen (maxfun) in L_BFGS_B von 1000 auf 15000, um der Vorgabe von SciPy zu entsprechen. Diese Zahl entspricht auch der Standardzahl der Iterationen (maxiter).

  • Aktualisiert ProbDistribution und QuasiDistribution um die Information über die Anzahl der Bits zu speichern, wenn Bitstrings ohne Präfix “0b” angegeben werden. ProbDistribution.binary_probabilities() und QuasiDistribution.binary_probabilities() die gespeicherte Anzahl der Bits als Standardwert für die Anzahl der Bits verwenden.

  • RZXCalibrationBuilder und RZXCalibrationBuilderNoEcho wurden aufgerüstet, um die Streckung von CX-Gattern zu überspringen, die durch eine nicht-echoisierte Kreuzresonanzsequenz (ECR) implementiert wurden, um einen Abbruch des Durchgangs mit unerwarteten Fehlern zu vermeiden. Diese Übergänge nehmen ein neues Argument verbose , das steuert, ob die Übergänge warnen, wenn dies geschieht. Wenn verbose=True gesetzt ist, gibt der Pass eine Benutzerwarnung aus, wenn er eine Nicht-ECR-Sequenz entdeckt.

  • Das Visualisierungsmodul qiskit.visualization wurde intern etwas umstrukturiert. Dies sollte keine Auswirkungen auf die öffentliche Schnittstelle haben, aber wenn Sie auf interne Daten der Schaltkreisschubladen zugreifen, befinden sich diese nun möglicherweise an anderen Stellen. Die einzigen Teile des Visualisierungsmoduls, die als öffentlich gelten, sind die Komponenten, die in dieser Online-Dokumentation dokumentiert sind.

Hinweise zu veralteten Versionen

  • Der Import der Namen Int1, Int2, classical_function und BooleanExpression direkt aus qiskit.circuit ist veraltet. Dies ist Teil der Entwicklung, tweedledum zu einer optionalen Abhängigkeit zu machen, anstatt eine vollständige Voraussetzung zu sein. Stattdessen sollten Sie diese Namen aus qiskit.circuit.classicalfunction.

  • Die Module qiskit.algorithms.factorizers und qiskit.algorithms.linear_solvers sind veraltet und werden in einer zukünftigen Version entfernt. Sie werden durch Tutorials im Qiskit-Lehrbuch ersetzt: Schor HHL

  • Die random_stabilizer_table() ist veraltet und wird in einer zukünftigen Version entfernt werden. Stattdessen sollte die random_pauli_list() funktion verwendet werden.

  • Die Pulsmodul-Funktion qiskit.pulse.utils.deprecated_functionality ist veraltet und wird in einer zukünftigen Version entfernt werden. Dies war eine hauptsächlich interne Funktion. Die gleiche Funktionalität wird von qiskit.utils.deprecate_function bereitgestellt, das stattdessen verwendet werden sollte.

  • Die Methode zur Ausführung von Primitiven wurde geändert. Die Methoden BaseSampler.__call__() und BaseEstimator.__call__() wurden veraltet. Zum Beispiel:

    estimator = Estimator(...)
    result = estimator(circuits, observables, parameters)
    
    sampler = Sampler(...)
    result = sampler(circuits, observables, parameters)

    sollte umgeschrieben werden als

    estimator = Estimator()
    result = estimator.run(circuits, observables, parameter_values).result()
    
    sampler = Sampler()
    result = sampler.run(circuits, parameter_values).result()

    Die Verwendung von Primitiven als Kontextmanager ist veraltet. Nicht alle Primitive verfügen über einen Kontextmanager. Wenn verfügbar (z. B. in qiskit-ibm-runtime), bietet der Kontextmanager der Sitzung eine gleichwertige Funktionalität.

    circuits, observables, und parameters im Konstruktor wurde veraltet. circuits und observables können von run Methoden übergeben werden. run methoden unterstützen nicht parameters. Die Benutzer müssen die Parameterwerte selbst umstellen.

  • Das unbenutzte Argument qubit_channel_mapping in den RZXCalibrationBuilder und RZXCalibrationBuilderNoEcho wurde veraltet und wird in einer zukünftigen Version entfernt werden. Dieses Argument wird nicht mehr verwendet und hat keine Auswirkungen auf die Funktionsweise der Pässe.

Fehlerkorrekturen

  • Ein Problem wurde behoben, bei dem Pauli.evolve() und PauliList.evolve() einen dtype-Fehler auslöste, wenn es durch bestimmte Clifford-Gatter, die die Pauli-Phase modifizierten, entwickelt wurde. Behoben #8438

  • Ein Fehler wurde behoben in QuantumCircuit.initialize() und QuantumCircuit.prepare_state() behoben, der dazu führte, dass sie bei der Initialisierung kein einzelnes Qubit als Argument akzeptierten.

  • Die Methode QuantumCircuit.while_loop() löst nun klassische Bitreferenzen in ihrer Bedingung auf die gleiche Weise auf wie QuantumCircuit.if_test() und InstructionSet.c_if() tun.

  • Die DAGCircuit methoden depth(), size() und DAGCircuit.count_ops() gaben bisher Ergebnisse zurück, die wenig bis gar keine Bedeutung hatten, wenn ein Kontrollfluss in der Schaltung vorhanden war. Die depth() und size() methoden werfen in diesen Fällen nun korrekt einen Fehler, haben aber ein neues recurse Schlüsselwortargument, um die Berechnung eines Proxy-Wertes zu ermöglichen, während count_ops() standardmäßig in den Blöcken rekursiert und die Operationen innerhalb dieser Blöcke zählt.

  • Es wurde ein Problem im DenseLayout transpiler-Durchgang, bei dem alle losen Qubit objekte (d.h. nicht Teil einer QuantumRegister), die Teil einer QuantumCircuit waren, nicht in die Ausgabe Layout die von dem Durchgang erzeugt wurde.

  • Die Operator.from_circuit() konstruktor-Methode wurde aktualisiert, so dass sie mit der Layout-Ausgabe von transpile() verarbeitet und die durch das Layout verursachte Qubit-Permutation in allen Fällen korrekt umkehrt. Wenn Ihre transpilierte Schaltung bisher lose Objekte verwendete Qubit objekte, mehrere QuantumRegister objekte oder ein einzelnes QuantumRegister mit einem anderen Namen als "q" verwendet hat, konnte der Konstruktor keine Operator aus der Schaltung zu erstellen. Behoben #8800.

  • Ein Fehler wurde behoben, bei dem die Zerlegung einer Anweisung mit einem Qubit und einem klassischen Bit, die ein einzelnes Quantengatter enthält, fehlschlug. Nun zerlegt sich das Folgende wie erwartet:

    block = QuantumCircuit(1, 1)
    block.h(0)
    
    circuit = QuantumCircuit(1, 1)
    circuit.append(block, [0], [0])
    
    decomposed = circuit.decompose()
  • Fixierte Initialisierung der leeren symplektischen Matrix in from_symplectic() in PauliList klasse Zum Beispiel:

    from qiskit.quantum_info.operators import PauliList
    
    x = np.array([], dtype=bool).reshape((1,0))
    z = np.array([], dtype=bool).reshape((1,0))
    pauli_list = PauliList.from_symplectic(x, z)
  • Behebung eines Problems in der GateDirection transpilerpass für die CZGate. Das CZ-Tor ist symmetrisch, so dass die Umkehrung der Qubit-Argumente erlaubt ist, um die gerichtete Kopplungskarte zu erfüllen.

  • Probleme mit der Methode DerivativeBase.gradient_wrapper() bei der Wiederverwendung eines Circuit Samplers zwischen den Aufrufen und der Bindung verschachtelter Parameter wurden behoben.

  • Ein Problem in den Schaltkreisschubladen mpl und latex wurde behoben, bei dem das Setzen der Option idle_wires auf False bei Vorhandensein eines barrier im Schaltkreis zu einem Ausfall der Schubladen führte. Behoben #8313

  • Ein Problem wurde behoben in circuit_drawer() und QuantumCircuit.draw() mit der Methode latex , bei der auf Systemen, deren temporäre Verzeichnisse (z.B. /tmp) in einem anderen Dateisystem liegen als das Arbeitsverzeichnis, ein OSError ausgelöst wurde. Behebt #8542

  • Verschachtelung einer FlowController innerhalb eines anderen in einer PassManager konnte früher dazu führen, dass einige Transpilerdurchläufe während der Transpilierung "vergessen" wurden, wenn die Durchläufe ein neues DAGCircuit zurückgaben, anstatt ihre Eingabe zu verändern. Verschachtelte FlowControllers wirken sich nun korrekt auf die Transpilierung aus.

  • Vergleich von QuantumCircuit und DAGCircuits auf Gleichheit war bisher nicht deterministisch, wenn die Schaltkreise mehr als ein Register desselben Typs enthielten (z. B. zwei oder mehr QuantumRegisters) und ergab manchmal False , selbst wenn die Register identisch waren. Schaltungen mit mehreren Registern werden nun korrekt verglichen.

  • Der OpenQASM 2-Exporter (QuantumCircuit.qasm()) definiert nun korrekt die Qubit-Parameter für UnitaryGate operationen, die nicht alle Qubits betreffen, für die sie definiert sind. Behoben #8224.

  • Es gab zwei Fehler in der text Schaltkreisschublade, die behoben wurden. Diese erschienen, wenn vertical_compression auf medium eingestellt war, was die Standardeinstellung ist. Im ersten Fall konnte es vorkommen, dass Text andere Texte oder Gatter überschrieb, und im zweiten Fall konnte es vorkommen, dass die Verbindungen zwischen einem Gatter und seinen Steuerungen unterbrochen wurden. Siehe #8588.

  • Es wurde ein Problem mit dem UnitarySynthesis pass, bei dem eine Schaltung mit 1-Qubit-Gattern und einem Target eingang manchmal fehlschlug, anstatt die Schaltung wie erwartet zu verarbeiten.

  • Der GateDirection transpiler-Durchlauf beachtet nun die verfügbaren Werte für Gatterparameter, wenn er parametrisierte Gatter mit einer Target.

  • Es wurde ein Problem in der SNOBFIT optimizer-Klasse, wo ein interner Fehler während der Ausführung der minimize() methode einen internen Fehler auslöste, wenn keine Eingabegrenzen angegeben wurden. Dies wird nun zum Zeitpunkt des Aufrufs überprüft, um schnell eine ValueError zu erstellen, wenn die erforderlichen Grenzen für den Aufruf fehlen minimize() aufruf fehlen. Behebt #8580

  • Es wurde ein Problem in der aufrufbaren Ausgabe der get_energy_evaluation() methode der VQD klasse ruft nun korrekt die angegebene callback auf, wenn sie ausgeführt wird. Zuvor wurde der Rückruf in diesem Fall fälschlicherweise nicht verwendet. Behoben #8575

  • Ein Problem wurde behoben, das bei der Verwendung von circuit_drawer() mit reverse_bits=True in einem Schaltkreis ohne klassische Bits zu einer möglicherweise verwirrenden Warnung über cregbundle führte. Behoben #8690

  • Der OpenQASM 3-Exporter (qiskit.qasm3) wird nun korrekt mit OpenQASM built-ins (wie reset und measure) umgehen, die eine klassische Bedingung haben, die von c_if(). Zuvor wäre die Bedingung ignoriert worden.

  • Es wurde ein Problem mit der SPSA klasse behoben, bei dem intern versucht wurde, Aufträge in gleichgroße Stapel aufzuteilen, was eine Ausnahme auslöste, wenn die Erstellung gleichgroßer Stapel nicht möglich war. Dieses Problem wurde behoben, so dass die Stapelverarbeitung immer erfolgreich ist, auch wenn die Größe der Aufträge nicht gleichmäßig ist.

  • Das Verhalten von Layout.add() das möglicherweise dazu führte, dass die Ausgabe von transpile() ungültig war und mehr Qubits enthielt, als auf dem Ziel-Backend verfügbar waren. Behoben: #8667

  • Ein Problem mit der Funktion state_to_latex() wurde behoben: Die Übergabe einer Latex-Zeichenkette an das optionale Argument prefix der Funktion führte zu einem Fehler. Behoben #8460

  • Die Funktion state_to_latex() erzeugte nicht gültige LaTeX bei Vorhandensein von Werten nahe Null, was zu Fehlern führte, wenn state_drawer() aufgerufen wurde. Behoben #8169.

  • GradientDescent zählt nun korrekt die Anzahl der Iterationen, Funktions- und Gradientenauswertungen. Außerdem wird in der Dokumentation nun korrekt angegeben, dass der Gradient durch eine Vorwärts-Finite-Differenzen-Methode approximiert wird.

  • Behebung von Verwerfungswarnungen in NaturalGradientdie nun StandardScaler verwendet, um die Daten vor der Anpassung des Modells zu skalieren, wenn der Parameter normalize auf True gesetzt ist.

Aer- 0.11.0

Keine Änderung

IBM Q Anbieter 0.19.2

Keine Änderung

War diese Seite hilfreich?
Melden Sie auf GitHub einen Fehler, einen Tippfehler oder fordern Sie Inhalte an.