Szybki start z Executor
Wersje pakietów
Kod na tej stronie został opracowany przy użyciu następujących wymagań. Zalecamy używanie tych lub nowszych wersji.
qiskit[all]~=2.4.0
qiskit-ibm-runtime~=0.46.1
samplomatic~=0.18.0
# Added by doQumentation — required packages for this notebook
!pip install -q qiskit qiskit-ibm-runtime samplomatic
Podobnie jak prymityw Sampler, Executor pobiera próbki z rejestrów wyjściowych wynikających z wykonania obwodów kwantowych, ale nie posiada żadnych wbudowanych mechanizmów tłumienia ani łagodzenia błędów. Zamiast tego jest częścią modelu ukierunkowanego wykonania, który dostarcza składniki do rejestrowania intencji projektowych po stronie klienta i przenosi kosztowne generowanie wariantów obwodów na stronę serwera. Executor wykonuje dyrektywy zawarte w adnotacjach obwodów i opcjach, generuje i wiąże wartości parametrów, wykonuje powiązane obwody na sprzęcie i zwraca wyniki wykonania oraz metadane. Nie podejmuje żadnych niejawnych decyzji i daje ci pełną kontrolę i przejrzystość.
Pakiet Qiskit nie ma jeszcze klasy bazowej dla prymitywu Executor.
Przed rozpoczęciem
Niektóre przykłady kodu na tej stronie używają samplex, który jest częścią pakietu Samplomatic. Dlatego przed uruchomieniem tych bloków kodu musisz zainstalować Samplomatic, jak pokazano w poniższym bloku kodu. Aby uzyskać więcej informacji, zobacz dokumentację Samplomatic.
pip install samplomatic
# For visualization support, include the visualization dependencies.
# pip install samplomatic[vis]
Kroki korzystania z prymitywu Executor
1. Inicjalizacja konta
Ponieważ Qiskit Runtime jest usługą zarządzaną, musisz najpierw zainicjować swoje konto. Następnie możesz wybrać QPU, którego chcesz użyć do obliczenia wartości oczekiwanej.
Jeśli nie masz jeszcze konta, postępuj zgodnie z krokami opisanymi w Konfiguracja konta IBM Cloud®.
from qiskit_ibm_runtime import QiskitRuntimeService, Executor
from qiskit_ibm_runtime.quantum_program import QuantumProgram
from qiskit.circuit import QuantumCircuit
from qiskit.transpiler import generate_preset_pass_manager
from samplomatic.transpiler import generate_boxing_pass_manager
from samplomatic import build
# Initialize the service and choose a backend
service = QiskitRuntimeService()
backend = service.least_busy(operational=True, simulator=False)
print(backend)
<IBMBackend('ibm_fez')>
2. Tworzenie i transpilacja obwodu
Do użycia prymitywu Executor potrzebujesz co najmniej jednego obwodu. Opcjonalnie może on zawierać parametry.
# Generate the circuit
circuit = QuantumCircuit(2)
circuit.h(0)
circuit.h(1)
circuit.cz(0, 1)
circuit.h(1)
# Using `measure_all` automatically creates the necessary
# classical registers.
circuit.measure_all()
Obwód musi zostać przekształcony tak, aby używał tylko instrukcji obsługiwanych przez QPU (określanych jako obwody architektury zestawu instrukcji (ISA)). Użyj Transpilatora, aby to zrobić.
# Transpile the circuit
preset_pass_manager = generate_preset_pass_manager(
backend=backend, optimization_level=0
)
isa_circuit = preset_pass_manager.run(circuit)
3. Inicjalizacja QuantumProgram
Zainicjuj QuantumProgram ze swoim obciążeniem roboczym. QuantumProgram składa się z QuantumProgramItems. Zazwyczaj każdy element składa się z obwodu, zestawu wartości parametrów i ewentualnie samplex do losowania zawartości obwodu. Aby uzyskać pełne szczegóły, zobacz Dane wejściowe i wyjściowe Executor.
Poniższa komórka inicjuje QuantumProgram i określa wykonanie 25 pomiarów. Następnie dołącza transpilowany obwód docelowy.
# Initialize an empty program
program = QuantumProgram(shots=25)
# Append the circuit to the program
program.append_circuit_item(isa_circuit)
4. Opcjonalnie: Grupowanie bramek i pomiarów w adnotowane bloki
Grupowanie instrukcji w bloki i ich adnotowanie to podstawowy sposób określania intencji. W poniższym przykładzie używamy generate_boxing_pass_manager i jego parametrów twirlingowych do grupowania dwukubitowych bramek i pomiarów w bloki oraz stosowania adnotacji twirlingowej.
# Generate a boxing pass manager to group gates
# and measurements into boxes and add
# a`Twirl` annotation.
boxes_pm = generate_boxing_pass_manager(
# Add gate twirling
enable_gates=True,
# Add measurement twirling
enable_measures=True,
)
boxed_circuit = boxes_pm.run(isa_circuit)
boxed_circuit.draw("mpl", idle_wires=False)
5. Opcjonalnie: Tworzenie obwodu szablonowego i samplex oraz dodanie ich do programu
Następnie użyj metody Samplomatic build, aby wygenerować parę obwodu szablonowego i samplex. Obwód szablonowy jest strukturalnie równoważny oryginalnemu obwodowi. Jednak jego jednokubitowe bramki są zastąpione przez bramki sparametryzowane w celu implementacji przepisanych adnotacji (twirling bramek i pomiarów w tym przykładzie). Samplex koduje wszystkie informacje wymagane do generowania losowych parametrów dla obwodu szablonowego.
Po wygenerowaniu pary obwodu szablonowego i samplex użyj metody append_samplex_item, aby dodać parę do programu.
Zobacz dokumentację API Samplomatic, aby uzyskać pełne szczegóły dotyczące samplomatic.samplex.Samplex i jego argumentów.
# Build the template circuit and the samplex
template_circuit, samplex = build(boxed_circuit)
# Append the template circuit and samplex as a `samplex_item`
program.append_samplex_item(
template_circuit,
samplex=samplex,
shape=(num_randomizations := 20,),
)
6. Wywołanie Executor i uzyskanie wyników
Uruchom QuantumProgram na backendzie IBM®, używając prymitywu Executor z domyślnymi opcjami. Zobacz Opcje Executor, aby dowiedzieć się o dostępnych opcjach.
# Initialize an Executor with the default options
executor = Executor(mode=backend)
# Submit the job
job = executor.run(program)
job
<RuntimeJobV2('d8286580bvlc73d1vmsg', 'executor')>
# Retrieve the result
result = job.result()
Wynik jest typu QuantumProgramResult. Zobacz Dane wejściowe i wyjściowe Executor, aby dowiedzieć się o obiekcie wynikowym.
Następne kroki
- Wypróbuj przykłady Executor.
- Zrozum dane wejściowe i wyjściowe Executor.
- Dowiedz się o semantyce rozgłaszania Executor.