Langkau ke kandungan utama
Projek ini dalam fasa beta. Jumpa pepijat? Buat isu GitHub. Ada soalan atau idea? Tanya dalam Discussions — kami suka dengar maklum balas anda!
Bagaimana kualiti terjemahan pada halaman ini?

Permulaan Pantas


title: Mula pantas description: Panduan mula pantas untuk pakej addon Qiskit pauli-prop​

Dalam panduan ini kita menggunakan pakej pauli-prop untuk mensimulasikan secara klasik dinamik masa bagi model Ising berdenyut 10-qubit pada rantai spin 1D.

Sediakan input untuk perambatan Pauli​

Hamiltonian yang dipertimbangkan ialah:

H=−J∑⟨i,j⟩ZiZj+h∑iXiH = -J\sum\limits_{\langle i,j \rangle} Z_iZ_j + h\sum\limits_iX_i

dengan J>0J>0 menerangkan gandingan spin jiran terdekat, i<ji<j, dan hh ialah medan melintang global. Penguraian Trotter peringkat pertama bagi pengendali yang berevolusi masa akan dilaksanakan sebagai litar kuantum, UU, melebihi 2020 langkah Trotter. Pemalar gandingan, JJ, akan ditetapkan pada J=−π2J=-\frac{\pi}{2}, dan hh akan ditetapkan pada π6\frac{\pi}{6}. Interaksi ZZZZ akan dilaksanakan menggunakan gate Clifford (CXCX, SdgSdg, Y\sqrt{Y}).

Kita melaksanakan evolusi masa Trotter sebagai litar kuantum dan menggunakan π6\frac{\pi}{6} untuk putaran bukan Clifford pada paksi-x. Semakin jauh sudut ini daripada sudut Clifford (contohnya, θ=nπ2,n∈Z\theta=n\frac{\pi}{2}, n \in \mathbb{Z}), semakin sukar sistem itu untuk disimulasikan bagi kaedah perambatan Pauli.

Untuk pilihan observable, kita mempertimbangkan purata magnetisasi satu-tapak, 1N∑i=1N⟨zi⟩\frac{1}{N} \sum_{i=1}^{N} \langle z_i \rangle, dengan NN ialah bilangan spin.

# Added by doQumentation — installs the packages this notebook needs if they are missing
import importlib.util

_needed = {"matplotlib": "matplotlib", "numpy": "numpy", "pauli_prop": "pauli-prop", "qiskit": "qiskit", "qiskit_aer": "qiskit-aer"}
_missing = [pip for module, pip in _needed.items()
if importlib.util.find_spec(module) is None]
# One at a time, so a package that fails to install does not block the others
for _pip in _missing:
%pip install -q {_pip}
if not _missing:
print("\u2713 All required packages are installed")
import numpy as np
from qiskit import QuantumCircuit
from qiskit.quantum_info import SparsePauliOp
from qiskit.transpiler import CouplingMap

num_qubits = 10
coupling_map = CouplingMap.from_line(num_qubits, bidirectional=False)

# Num Trotter steps
num_steps = 20
theta_rx = np.pi / 6

# Average single-site magnetization
observable = (
SparsePauliOp(
[
"I" * iq + "Z" + "I" * (num_qubits - iq - 1)
for iq in range(num_qubits)
]
)
/ num_qubits
)

# Create the Trotter circuit
num_qubits = 10
num_steps = 20
theta_rx = np.pi / 6
circuit = QuantumCircuit(num_qubits)
edges = CouplingMap.from_line(num_qubits, bidirectional=False).get_edges()
for _ in range(num_steps):
circuit.rx(theta_rx, [i for i in range(num_qubits)])
for edge in edges:
circuit.sdg(edge)
circuit.ry(np.pi / 2, edge[1])
circuit.cx(edge[0], edge[1])
circuit.ry(-np.pi / 2, edge[1])
circuit.draw("mpl", fold=-1)

Output of the previous code cell

Simulasikan evolusi masa sistem dengan perambatan Pauli​

Setelah kita mempunyai litar, UU, dan observable, OO, kita boleh mensimulasikan sistem dengan mudah dalam beberapa langkah:

  • Asingkan UU kepada bahagian Clifford, CC, dan bahagian bukan Clifford, PP, supaya U=PCU=PC menggunakan evolve_through_cliffords

  • Rambatkan OO melalui PP, menghasilkan pengendali baharu, O′O^\prime, menggunakan pauli_prop.propagate_through_circuit

  • Evolusikan O′O^\prime melalui bahagian Clifford litar menggunakan sokongan evolusi Clifford yang terbina dalam Qiskit

  • Anggarkan nilai jangkaan sebagai ⟨0∣O′∣0⟩≈⟨0∣U†OU∣0⟩\langle0|O^\prime|0\rangle \approx \langle0|U^\dagger OU|0\rangle dengan menjumlahkan pekali dalam O′O^\prime yang dikaitkan dengan sebutan Pauli pepenjuru sepenuhnya (sebutan Pauli yang mengandungi I atau Z pada semua qubit). Ingat, ini ialah anggaran kerana kita memangkas sebutan daripada O′O^\prime semasa merambatkannya melalui bahagian bukan Clifford litar.

import time

from pauli_prop import evolve_through_cliffords, propagate_through_circuit

cliff, non_cliff = evolve_through_cliffords(circuit)

max_terms_list = [10**i for i in range(8)]
approx_evs = []
durations = []
for max_terms in max_terms_list:
st = time.perf_counter()
evolved_obs = propagate_through_circuit(
observable, non_cliff, max_terms=max_terms, atol=1e-12, frame="h"
)[0]
evolved_obs.paulis = evolved_obs.paulis.evolve(cliff, frame="h")
durations.append(time.perf_counter() - st)
approx_evs.append(
float(evolved_obs.coeffs[~evolved_obs.paulis.x.any(axis=1)].sum())
)

Apabila kita menjalankan pengiraan yang lebih besar, anggaran nilai jangkaan menjadi lebih tepat. Dalam contoh ini, kita menepukan ruang Pauli penuh pada sekitar 410≈1064^{10}\approx10^6, yang ditunjukkan oleh lengkung yang mendatar antara dua titik terakhir.

Walaupun plot di bawah menunjukkan penumpuan monotonik, simulasi perambatan Pauli secara amnya tidak menumpu secara monotonik. Adalah tidak luar biasa untuk melihat tingkah laku "berombak" dalam plot jenis ini.

import matplotlib.pyplot as plt
from qiskit_aer import AerSimulator

sim_circ = circuit.copy()
sim_circ.save_statevector()
backend = AerSimulator(method="statevector")
psi = backend.run(sim_circ).result().data()["statevector"]
exact_ev = psi.expectation_value(observable)

ax1 = plt.gca()
ax1.plot(max_terms_list, approx_evs, marker="o", label="Approximate")
ax1.axhline(exact_ev, linestyle="--", color="green", label="Exact")
ax1.set_xscale("log")
ax1.set_xlabel("# terms kept")
ax1.set_ylabel(r"$\frac{1}{N} \sum_{i=1}^{N} \langle z_i \rangle$")

ax2 = ax1.twinx()
ax2.plot(
max_terms_list, durations, marker=".", label="Runtime", color="orange"
)
ax2.set_ylabel("Runtime (s)", color="orange")
ax2.set_yscale("log")

handles1, labels1 = ax1.get_legend_handles_labels()
handles2, labels2 = ax2.get_legend_handles_labels()
ax1.legend(handles1 + handles2, labels1 + labels2, loc="lower right")

plt.title(f"Simulating {num_steps}-step 1D Ising Model")
Text(0.5, 1.0, 'Simulating 20-step 1D Ising Model')

Output of the previous code cell