So übermitteln Sie einen Schaltkreis mit Cirq an Azure Quantum

Erfahren Sie, wie Sie einen Cirq-Quantenkreis mithilfe des azure-quantumPython Pakets übermitteln. Sie können Cirq-Schaltkreise mithilfe des Azure Quantum-Notizbuchs azure-quantumPython , das über ein integriertes Paket oder über Ihren lokalen Computer verfügt, an Azure Quantum übermitteln.

Weitere Informationen finden Sie unter Quantenschaltungen.

Voraussetzungen

Installationsdetails finden Sie unter Installieren des QDK unter VS Code.

Erstellen eines neuen Jupyter Notebooks

  1. Wählen Sie in VS Code die Optionen Ansicht > Befehlspalette und dann Erstellen aus: Verwenden von Jupyter Notebook.
  2. In der oberen rechten Ecke erkennt und zeigt VS Code die Version und Python die virtuelle Python Umgebung an, die für das Notizbuch ausgewählt wurde. Wenn Sie über mehrere Python Umgebungen verfügen, müssen Sie möglicherweise einen Kernel mit der Kernelauswahl oben rechts auswählen. Wenn keine Umgebung erkannt wurde, finden Sie Informationen zum Einrichten unter Jupyter-Notizbücher in VS Code .

Laden der erforderlichen Importe

Führen Sie in der ersten Zelle Ihres Notizbuchs den folgenden Code aus, um die erforderlichen Importe zu laden:

import azure.quantum
from azure.quantum.cirq import AzureQuantumService

Herstellen einer Verbindung mit dem Azure Quantum-Dienst

Zum Herstellen einer Verbindung mit dem Azure Quantum-Dienst benötigt Ihr Programm die Ressourcen-ID und den Speicherort Ihres Azure Quantum Arbeitsbereichs.

  1. Melden Sie sich bei Ihrem Azure-Konto an, https://portal.azure.com

  2. Wählen Sie Ihren Azure Quantum-Arbeitsbereich aus, und navigieren Sie zu "Übersicht".

  3. Kopieren Sie die Parameter in den Feldern.

    Screenshot von Visual Studio Code, der zeigt, wie Sie den Übersichtsbereich Ihres Quantum Workspace erweitern.

Fügen Sie eine neue Zelle hinzu, und verwenden Sie Ihre Kontoinformationen, um eine Verbindung mit Ihrem Azure Quantum-Arbeitsbereich herzustellen und AzureQuantumService Objekte zu erstellenWorkspace.

workspace = Workspace(  
    resource_id = "", # Add the resourceID of your workspace
    location = "" # Add the location of your workspace (for example "westus")
    )

service = AzureQuantumService(workspace)

Alle auflisten targets

Verwenden Sie die targets()Methode, um alle targets in Ihrem Arbeitsbereich aufgeführten Arbeitsbereiche auflisten, die Ihren Schaltkreis ausführen können, einschließlich der aktuellen Warteschlangenzeit und Verfügbarkeit.

Hinweis

targets Alle in Ihrem Arbeitsbereich dürfen nicht aufgeführt werden - nur die, die targets einen Cirq- oder OpenQASM-Schaltkreis akzeptieren kann, werden hier aufgeführt.

print(service.targets())
[<Target name="quantinuum.qpu.h1-1", avg. queue time=0 s, Degraded>,
<Target name="quantinuum.sim.h1-1sc", avg. queue time=1 s, Available>,
<Target name="quantinuum.sim.h1-1e", avg. queue time=40 s, Available>,
<Target name="ionq.simulator", avg. queue time=3 s, Available>,
<Target name="ionq.qpu.aria-1", avg. queue time=1136774 s, Available>]

Erstellen eines einfachen Schaltkreises

Erstellen Sie als Nächstes eine einfache Cirq-Schaltung für die Ausführung. Diese Schaltung verwendet die Quadratwurzel des X-Gatters, was nativ für das IonQ-Hardwaresystem ist.

import cirq

q0, q1 = cirq.LineQubit.range(2)
circuit = cirq.Circuit(
    cirq.X(q0)**0.5,             # Square root of X
    cirq.CX(q0, q1),              # CNOT
    cirq.measure(q0, q1, key='b') # Measure both qubits
)
print(circuit)
0: ───X^0.5───@───M────────
              │   │
1: ───────────X───M────────

Wählen Sie ein target , um Ihr Programm auszuführen.

Auf IonQ-Simulator ausführen

Sie können das Programm jetzt über den Azure Quantum-Dienst ausführen und das Ergebnis abrufen. Die folgende Zelle übermittelt einen Auftrag (an den als Standard festgelegten IonQ-Simulator), der die Schaltung mit 100 Ausführungen abläuft, wartet, bis der Auftrag abgeschlossen ist, und die Ergebnisse zurückgibt.

result = service.run(program=circuit, repetitions=100, target="ionq.simulator")

Hierbei wird ein cirq.Result-Objekt zurückgegeben.

print(result)
    b=1001100101100001000011011101000011010100010111100011001000100100010000001110010010101110110000011010, 1001100101100001000011011101000011010100010111100011001000100100010000001110010010101110110000011010

Schätzen der Auftragskosten

Bevor Sie einen Auftrag auf der QPU ausführen, sollten Sie schätzen, wie viel die Ausführung kostet.

Die aktuellen Preisdetails finden Sie unter Preise. Suchen Sie alternativ nach Ihrem Arbeitsbereich, und zeigen Sie die Preisoptionen auf der Registerkarte „Anbieter“ Ihres Arbeitsbereichs über aka.ms/aq/myworkspaces an.

Ausführen auf der IonQ-QPU

Der vorherige Auftrag wurde im Standardsimulator "ionq.simulator" ausgeführt. Sie können ihn jedoch ebenfalls auf dem Hardwareprozessor von IonQ ausführen (einer Quantenprozessoreinheit (QPU)). Geben Sie zur Ausführung auf der IonQ-QPU "ionq.qpu.aria-1" als target-Argument an:

result = service.run(
    program=circuit,
    repetitions=100,
    target="ionq.qpu.aria-1",
    timeout_seconds=500 # Set timeout to accommodate queue time on QPU
)

Hierbei wird wiederum ein cirq.Result-Objekt zurückgegeben.

print(result)
b=0101011011011111100001011101101011011110100010000000011110111000100100110110101100110001001111101111, 0101011011011111100001011101101011011110100010000000011110111000100100110110101100110001001111101111

Asynchrones Modell mit Aufträgen

Bei Schaltungen mit langer Ausführungsdauer kann es sinnvoll sein, sie asynchron auszuführen. Die service.create_job-Methode gibt ein Job-Objekt zurück, das Sie verwenden können, um die Ergebnisse nach der erfolgreichen Ausführung des Auftrags abzurufen.

job = service.create_job(
    program=circuit,
    repetitions=100,
    target="ionq.simulator"
)

Verwenden Sie job.status(), um den Auftragsstatus zu überprüfen:

print(job.status())
'completed'

Wenn Sie auf den Abschluss des Auftrags warten und dann die Ergebnisse abrufen möchten, verwenden Sie den blockierenden Aufruf job.results():

result = job.results()
print(result)
00: 0.5
11: 0.5

Beachten Sie, dass hierbei kein cirq.Result-Objekt zurückgegeben wird. Stattdessen wird ein Ergebnisobjekt zurückgegeben, das für den IonQ-Simulator spezifisch ist und Zustandswahrscheinlichkeiten anstelle von Ausführungsdaten verwendet.

type(result)
cirq_ionq.results.SimulatorResult

Verwenden Sie result.to_cirq_result(), um dies in ein cirq.Result-Objekt zu konvertieren:

print(result.to_cirq_result())
b=1110101111111110111000011101011111001100010000001011011101001111001111001101100111010000001100011100, 1110101111111110111000011101011111001100010000001011011101001111001111001101100111010000001100011100

Voraussetzungen

  • Ein Azure-Konto mit einem aktiven Abonnement. Wenn Sie nicht über ein Azure-Konto verfügen, registrieren Sie sich kostenlos, und registrieren Sie sich für ein Kostenpflichtiges Abonnement.
  • Azure Quantum-Arbeitsbereich Weitere Informationen finden Sie unter Erstellen eines Azure Quantum-Arbeitsbereichs.

Erstellen eines neuen Notebooks in Ihrem Arbeitsbereich

  1. Melden Sie sich beim Azure-Portal an, und wählen Sie den Arbeitsbereich aus dem vorherigen Schritt aus.
  2. Wählen Sie auf dem linken Blatt Notebooks aus.
  3. Klicken Sie auf Meine Notebooks und dann auf Neu hinzufügen.
  4. Geben Sie einen Namen für die Datei ein, z. B. Cirq.ipynb, und klicken Sie auf Datei erstellen.

Wenn Ihr neues Notebook geöffnet wird, wird der Code für die erste Zelle automatisch auf der Grundlage Ihrer Abonnement- und Arbeitsbereichsinformationen erstellt.

from azure.quantum import Workspace
workspace = Workspace ( 
  resource_id = "", # Add your resource_id 
  location = ""  # Add your workspace location (for example, "westus") 
)

Hinweis

Sofern nicht anders angegeben, müssen Sie die einzelnen Zellen in der Reihenfolge ihrer Erstellung ausführen, um Kompilierungsprobleme zu vermeiden.

Klicken Sie links neben der Zelle auf das dreieckige Wiedergabesymbol, um den Code auszuführen.

Laden der erforderlichen Importe

Zunächst müssen Sie ein zusätzliches Modul importieren.

Klicken Sie auf + Code, um eine neue Zelle hinzuzufügen, fügen Sie dann den folgenden Code hinzu, und führen Sie ihn aus:

from azure.quantum.cirq import AzureQuantumService

Herstellen einer Verbindung mit dem Azure Quantum-Dienst

Erstellen Sie als Nächstes ein AzureQuantumService Objekt mithilfe des workspace Objekts aus der vorherigen Zelle, um eine Verbindung mit Ihrem Azure Quantum-Arbeitsbereich herzustellen. Fügen Sie eine neue Zelle mit dem folgenden Code hinzu:

provider = AzureQuantumService(workspace)

Definieren einer einfachen Schaltung

Erstellen Sie als Nächstes eine einfache Cirq-Schaltung für die Ausführung. Diese Schaltung verwendet die Quadratwurzel des X-Gatters, was nativ für das IonQ-Hardwaresystem ist.

import cirq

q0, q1 = cirq.LineQubit.range(2)
circuit = cirq.Circuit(
    cirq.X(q0)**0.5,             # Square root of X
    cirq.CX(q0, q1),              # CNOT
    cirq.measure(q0, q1, key='b') # Measure both qubits
)
print(circuit)
0: ───X^0.5───@───M────────
              │   │
1: ───────────X───M────────

Alle auflisten targets

Verwenden Sie die targets()Methode, um alle targets in Ihrem Arbeitsbereich aufgeführten Arbeitsbereiche auflisten, die Ihren Schaltkreis ausführen können, einschließlich der aktuellen Warteschlangenzeit und Verfügbarkeit.

Hinweis

targets Alle in Ihrem Arbeitsbereich dürfen nicht aufgeführt werden - nur die, die targets einen Cirq- oder OpenQASM-Schaltkreis akzeptieren kann, werden hier aufgeführt.

print("This workspace's targets:")
for target in service.targets():
     print(target)
This workspace's targets:
<Target name="quantinuum.qpu.h1-1", avg. queue time=0 s, Degraded>
<Target name="quantinuum.sim.h1-1sc", avg. queue time=1 s, Available>
<Target name="quantinuum.sim.h1-1e", avg. queue time=40 s, Available>
<Target name="ionq.simulator", avg. queue time=3 s, Available>
<Target name="ionq.qpu.aria-1", avg. queue time=1136774 s, Available>

Hinweis

Die vollständige Liste kann target für Ihren Arbeitsbereich unterschiedlich sein.

Wählen Sie ein target , um Ihr Programm auszuführen.

Ausführen im IonQ-Simulator

Um Ihre Schaltung zu überprüfen, bevor Sie sie auf der tatsächlichen Quantenhardware ausführen, können Sie den IonQ-Simulator ionq.simulator verwenden.

Die folgende Zelle übermittelt einen Auftrag, der die Schaltung mit 100 Ausführungen abläuft, wartet, bis der Auftrag abgeschlossen ist, und die Ergebnisse zurückgibt.

result = service.run(
    program=circuit,
    repetitions=100,
    target="ionq.simulator"
)

Hierbei wird ein cirq.Result-Objekt zurückgegeben.

print(result)
    b=1001100101100001000011011101000011010100010111100011001000100100010000001110010010101110110000011010, 1001100101100001000011011101000011010100010111100011001000100100010000001110010010101110110000011010

Sie können die Ergebnisse in einem Histogramm zeichnen:

import pylab as pl

pl.hist(result.data)
pl.ylabel("Counts")
pl.xlabel("Result")

Schätzen der Auftragskosten

Bevor Sie einen Auftrag auf der tatsächlichen Quantenhardware oder einer Quantenverarbeitungseinheit (Quantum Processing Unit , QPU) ausführen, sollten Sie abschätzen, wie viel die Ausführung kostet.

Die aktuellen Preisdetails finden Sie unter Preise, oder zeigen Sie die Preisoptionen auf dem Blatt Anbieter Ihres Arbeitsbereichs an. Wählen Sie Guthaben und Kontingente aus, um Ihren aktuellen Guthabenstatus und Ihre aktuelle Nutzung anzuzeigen.

Ausführen auf der IonQ-QPU

Der vorherige Auftrag wurde im Standardsimulator ionq.simulator ausgeführt. Sie können ihn jedoch ebenfalls auf dem Hardwareprozessor von IonQ oder einer Quantenprozessoreinheit (QPU) ausführen. Geben Sie zur Ausführung auf der IonQ-QPU ionq.qpu.aria-1 als target-Argument an:

result = service.run(
    program=circuit,
    repetitions=100,
    target="ionq.qpu.aria-1",
    timeout_seconds=500 # Set timeout to accommodate queue time on QPU
)

Hinweis

Die zum Ausführen einer Schaltung auf der QPU erforderliche Zeit hängt von den aktuellen Warteschlangenzeiten ab. Sie können die durchschnittliche Warteschlangenzeit für ein Objekt target anzeigen, indem Sie das Blatt "Anbieter " Ihres Arbeitsbereichs auswählen.

Hierbei wird wiederum ein cirq.Result-Objekt zurückgegeben.

print(result)
    b=1001100101100001000011011101000011010100010111100011001000100100010000001110010010101110110000011010, 1001100101100001000011011101000011010100010111100011001000100100010000001110010010101110110000011010

Asynchrones Modell mit Aufträgen

Bei Schaltungen mit langer Ausführungsdauer kann es sinnvoll sein, sie asynchron auszuführen. Die service.create_job-Methode gibt ein Job-Objekt zurück, das Sie verwenden können, um die Ergebnisse nach der erfolgreichen Ausführung des Auftrags abzurufen.

job = service.create_job(
    program=circuit,
    repetitions=100,
    target="ionq.simulator"
)

Verwenden Sie job.status(), um den Auftragsstatus zu überprüfen:

print(job.status())
'completed'

Wenn Sie auf den Abschluss des Auftrags warten und dann die Ergebnisse abrufen möchten, verwenden Sie den blockierenden Aufruf job.results():

result = job.results()
print(result)
00: 0.5
11: 0.5

Hinweis

Die Funktion job.results() gibt kein Objekt vom Typ cirq.Result zurück. Stattdessen wird ein Ergebnisobjekt zurückgegeben, das für den IonQ-Simulator spezifisch ist und Zustandswahrscheinlichkeiten anstelle von Ausführungsdaten verwendet.

type(result)
cirq_ionq.results.SimulatorResult

Verwenden Sie result.to_cirq_result(), um dies in ein cirq.Result-Objekt zu konvertieren:

print(result.to_cirq_result())
b=1110101111111110111000011101011111001100010000001011011101001111001111001101100111010000001100011100, 1110101111111110111000011101011111001100010000001011011101001111001111001101100111010000001100011100

Wichtig

Das Übermitteln mehrerer Schaltungen in einem einzelnen Auftrag wird derzeit nicht unterstützt. Sie können allerdings die Methode backend.run aufrufen, um die einzelnen Schaltungen asynchron zu übermitteln, und anschließend die Ergebnisse jedes Auftrags abrufen. Zum Beispiel:

jobs = []
for circuit in circuits:
    jobs.append(backend.run(circuit, shots=N))

results = []
for job in jobs:
    results.append(job.result())