Membangun model noise
Versi paket
Kode di halaman ini dikembangkan menggunakan persyaratan berikut. Kami merekomendasikan penggunaan versi ini atau yang lebih baru.
qiskit[all]~=2.3.0
qiskit-ibm-runtime~=0.43.1
qiskit-aer~=0.17
Halaman ini menunjukkan cara menggunakan modul noise dari Qiskit Aer untuk membangun model noise guna mensimulasikan Circuit kuantum dengan adanya error. Ini berguna untuk mengemulasi prosesor kuantum yang berisik dan untuk mempelajari efek noise pada eksekusi algoritma kuantum.
# Added by doQumentation β required packages for this notebook
!pip install -q numpy qiskit qiskit-aer qiskit-ibm-runtime
import numpy as np
from qiskit import QuantumCircuit
from qiskit.quantum_info import Kraus, SuperOp
from qiskit.visualization import plot_histogram
from qiskit.transpiler import generate_preset_pass_manager
from qiskit_aer import AerSimulator
# Import from Qiskit Aer noise module
from qiskit_aer.noise import (
NoiseModel,
QuantumError,
ReadoutError,
depolarizing_error,
pauli_error,
thermal_relaxation_error,
)
Modul noise Qiskit Aerβ
Modul noise Qiskit Aer berisi kelas-kelas Python untuk membangun model noise yang dikustomisasi untuk simulasi. Ada tiga kelas utama:
-
Kelas
NoiseModelyang menyimpan model noise yang digunakan untuk simulasi berisik. -
Kelas
QuantumErroryang mendeskripsikan error Gate CPTP. Error ini dapat diterapkan:- Setelah instruksi gate atau reset
- Sebelum instruksi measure.
-
Kelas
ReadoutErroryang mendeskripsikan error readout klasik.
Menginisialisasi model noise dari Backendβ
Kamu bisa menginisialisasi model noise dengan parameter yang diatur dari data kalibrasi terbaru untuk Backend fisik:
from qiskit_ibm_runtime import QiskitRuntimeService
service = QiskitRuntimeService()
backend = service.backend("ibm_fez")
noise_model = NoiseModel.from_backend(backend)
Ini akan menghasilkan model noise yang kira-kira mendekati error yang akan ditemui saat menggunakan Backend tersebut. Jika kamu ingin kontrol lebih detail atas parameter model noise, maka kamu perlu membuat model noise sendiri, seperti yang dijelaskan di sisa halaman ini.
Error kuantumβ
Daripada berurusan langsung dengan objek QuantumError, banyak fungsi pembantu yang tersedia untuk menghasilkan secara otomatis tipe error kuantum berparameter tertentu. Fungsi-fungsi ini ada di modul noise dan mencakup fungsi untuk banyak tipe error umum yang digunakan dalam penelitian komputasi kuantum. Nama fungsi dan tipe error yang dikembalikannya adalah:
| Fungsi error standar | Detail |
|---|---|
kraus_error | saluran error CPTP n-Qubit umum yang diberikan sebagai daftar matriks Kraus . |
mixed_unitary_error | error uniter campuran n-Qubit yang diberikan sebagai daftar matriks uniter dan probabilitas . |
coherent_unitary_error | error uniter koheren n-Qubit yang diberikan sebagai matriks uniter tunggal . |
pauli_error | saluran error Pauli n-Qubit (uniter campuran) yang diberikan sebagai daftar Pauli dan probabilitas |
depolarizing_error | saluran error depolarisasi n-Qubit yang diparameterisasi oleh probabilitas depolarisasi . |
reset_error | error reset satu-Qubit yang diparameterisasi oleh probabilitas untuk reset ke keadaan , . |
thermal_relaxation_error | saluran relaksasi termal satu Qubit yang diparameterisasi oleh konstanta waktu relaksasi , , waktu Gate , dan populasi termal keadaan tereksitasi . |
phase_amplitude_damping_error | Saluran error redaman fase dan amplitudo gabungan umum satu-Qubit yang diberikan oleh parameter redaman amplitudo , parameter redaman fase , dan populasi termal keadaan tereksitasi . |
amplitude_damping_error | Saluran error redaman amplitudo umum satu-Qubit yang diberikan oleh parameter redaman amplitudo , dan populasi termal keadaan tereksitasi . |
phase_damping_error | Saluran error redaman fase satu-Qubit yang diberikan oleh parameter redaman fase . |
Menggabungkan error kuantumβ
Instance QuantumError dapat digabungkan menggunakan komposisi, produk tensor, dan perluasan tensor (produk tensor urutan terbalik) untuk menghasilkan QuantumError baru sebagai:
- Komposisi: sebagai
error = error1.compose(error2) - Produk tensor: sebagai
error = error1.tensor(error2) - Produk perluasan: sebagai
error = error1.expand(error2)
Contohβ
Untuk membuat error bit-flip satu-Qubit sebesar 5%:
# Construct a 1-qubit bit-flip and phase-flip errors
p_error = 0.05
bit_flip = pauli_error([("X", p_error), ("I", 1 - p_error)])
phase_flip = pauli_error([("Z", p_error), ("I", 1 - p_error)])
print(bit_flip)
print(phase_flip)
QuantumError on 1 qubits. Noise circuits:
P(0) = 0.05, Circuit =
βββββ
q: β€ X β
βββββ
P(1) = 0.95, Circuit =
βββββ
q: β€ I β
βββββ
QuantumError on 1 qubits. Noise circuits:
P(0) = 0.05, Circuit =
βββββ
q: β€ Z β
βββββ
P(1) = 0.95, Circuit =
βββββ
q: β€ I β
βββββ
# Compose two bit-flip and phase-flip errors
bitphase_flip = bit_flip.compose(phase_flip)
print(bitphase_flip)
QuantumError on 1 qubits. Noise circuits:
P(0) = 0.0025000000000000005, Circuit =
ββββββββββ
q: β€ X ββ€ Z β
ββββββββββ
P(1) = 0.0475, Circuit =
ββββββββββ
q: β€ X ββ€ I β
ββββββββββ
P(2) = 0.0475, Circuit =
ββββββββββ
q: β€ I ββ€ Z β
ββββββββββ
P(3) = 0.9025, Circuit =
ββββββββββ
q: β€ I ββ€ I β
ββββββββββ
# Tensor product two bit-flip and phase-flip errors with
# bit-flip on qubit-0, phase-flip on qubit-1
error2 = phase_flip.tensor(bit_flip)
print(error2)
QuantumError on 2 qubits. Noise circuits:
P(0) = 0.0025000000000000005, Circuit =
βββββ
q_0: β€ X β
βββββ€
q_1: β€ Z β
βββββ
P(1) = 0.0475, Circuit =
βββββ
q_0: β€ I β
βββββ€
q_1: β€ Z β
βββββ
P(2) = 0.0475, Circuit =
βββββ
q_0: β€ X β
βββββ€
q_1: β€ I β
βββββ
P(3) = 0.9025, Circuit =
βββββ
q_0: β€ I β
βββββ€
q_1: β€ I β
βββββ
Mengonversi ke dan dari operator QuantumChannelβ
Kita juga bisa mengonversi bolak-balik antara objek QuantumError di Qiskit Aer dan objek QuantumChannel di Qiskit.
# Convert to Kraus operator
bit_flip_kraus = Kraus(bit_flip)
print(bit_flip_kraus)
Kraus([[[-9.74679434e-01+0.j, 0.00000000e+00+0.j],
[ 0.00000000e+00+0.j, -9.74679434e-01+0.j]],
[[ 0.00000000e+00+0.j, 2.23606798e-01+0.j],
[ 2.23606798e-01+0.j, -4.96506831e-17+0.j]]],
input_dims=(2,), output_dims=(2,))
# Convert to Superoperator
phase_flip_sop = SuperOp(phase_flip)
print(phase_flip_sop)
SuperOp([[1. +0.j, 0. +0.j, 0. +0.j, 0. +0.j],
[0. +0.j, 0.9+0.j, 0. +0.j, 0. +0.j],
[0. +0.j, 0. +0.j, 0.9+0.j, 0. +0.j],
[0. +0.j, 0. +0.j, 0. +0.j, 1. +0.j]],
input_dims=(2,), output_dims=(2,))
# Convert back to a quantum error
print(QuantumError(bit_flip_kraus))
# Check conversion is equivalent to original error
QuantumError(bit_flip_kraus) == bit_flip
QuantumError on 1 qubits. Noise circuits:
P(0) = 1.0, Circuit =
βββββββββ
q: β€ kraus β
βββββββββ
True
Error readoutβ
Error readout klasik ditentukan oleh daftar vektor probabilitas penugasan :
- adalah nilai bit klasik yang dicatat
- adalah nilai bit sebenarnya yang dikembalikan dari pengukuran
Sebagai contoh, untuk satu Qubit: .
# Measurement misassignment probabilities
p0given1 = 0.1
p1given0 = 0.05
ReadoutError([[1 - p1given0, p1given0], [p0given1, 1 - p0given1]])
ReadoutError([[0.95 0.05]
[0.1 0.9 ]])
Error readout juga bisa digabungkan menggunakan compose, tensor, dan expand, seperti halnya error kuantum.
Menambahkan error ke noise modelβ
Saat menambahkan quantum error ke noise model, kita harus menentukan jenis instruksi yang diterapkan dan Qubit mana yang dikenai error tersebut. Ada dua jenis quantum error:
- Quantum error untuk semua Qubit
- Quantum error untuk Qubit tertentu
1. Quantum error untuk semua Qubitβ
Ini menerapkan error yang sama pada setiap kemunculan suatu instruksi, terlepas dari Qubit mana yang dikenainya.
Cara menambahkannya: noise_model.add_all_qubit_quantum_error(error, instructions):
# Create an empty noise model
noise_model = NoiseModel()
# Add depolarizing error to all single qubit u1, u2, u3 gates
error = depolarizing_error(0.05, 1)
noise_model.add_all_qubit_quantum_error(error, ["u1", "u2", "u3"])
# Print noise model info
print(noise_model)
NoiseModel:
Basis gates: ['cx', 'id', 'rz', 'sx', 'u1', 'u2', 'u3']
Instructions with noise: ['u3', 'u2', 'u1']
All-qubits errors: ['u1', 'u2', 'u3']
2. Quantum error untuk Qubit tertentuβ
Ini menerapkan error pada setiap kemunculan suatu instruksi yang bertindak pada daftar Qubit yang ditentukan. Perlu diperhatikan bahwa urutan Qubit penting: misalnya, error yang diterapkan pada Qubit [0, 1] untuk gate dua Qubit berbeda dengan yang diterapkan pada Qubit [1, 0].
Cara menambahkannya: noise_model.add_quantum_error(error, instructions, qubits):
# Create an empty noise model
noise_model = NoiseModel()
# Add depolarizing error to all single qubit u1, u2, u3 gates on qubit 0 only
error = depolarizing_error(0.05, 1)
noise_model.add_quantum_error(error, ["u1", "u2", "u3"], [0])
# Print noise model info
print(noise_model)
NoiseModel:
Basis gates: ['cx', 'id', 'rz', 'sx', 'u1', 'u2', 'u3']
Instructions with noise: ['u3', 'u2', 'u1']
Qubits with noise: [0]
Specific qubit errors: [('u1', (0,)), ('u2', (0,)), ('u3', (0,))]
Catatan tentang quantum error non-lokalβ
NoiseModel tidak mendukung penambahan quantum error non-lokal untuk Qubit. Error semacam ini harus ditangani di luar NoiseModel. Artinya, kamu perlu membuat transpiler pass sendiri (TransformationPass) dan menjalankan pass tersebut tepat sebelum menjalankan simulator jika ingin menyisipkan quantum error ke dalam Circuit sesuai kondisi yang kamu tentukan.
Menjalankan simulasi bersuara dengan noise modelβ
Perintah AerSimulator(noise_model=noise_model) mengembalikan simulator yang dikonfigurasi sesuai noise model yang diberikan. Selain mengatur noise model simulator, perintah ini juga mengganti basis gates simulator sesuai dengan gates dari noise model.
Contoh noise modelβ
Sekarang kita akan memberikan beberapa contoh noise model. Untuk demonstrasi ini, kita menggunakan Circuit uji sederhana yang menghasilkan GHZ state dengan n Qubit:
# System Specification
n_qubits = 4
circ = QuantumCircuit(n_qubits)
# Test Circuit
circ.h(0)
for qubit in range(n_qubits - 1):
circ.cx(qubit, qubit + 1)
circ.measure_all()
print(circ)
βββββ β βββ
q_0: β€ H ββββ ββββββββββββββββ€Mββββββββββ
ββββββββ΄ββ β ββ₯ββββ
q_1: ββββββ€ X ββββ ββββββββββββ«ββ€Mβββββββ
ββββββββ΄ββ β β ββ₯ββββ
q_2: βββββββββββ€ X ββββ βββββββ«βββ«ββ€Mββββ
ββββββββ΄ββ β β β ββ₯ββββ
q_3: ββββββββββββββββ€ X ββββββ«βββ«βββ«ββ€Mβ
βββββ β β β β ββ₯β
meas: 4/βββββββββββββββββββββββββ©βββ©βββ©βββ©β
0 1 2 3
Simulasi idealβ
# Ideal simulator and execution
sim_ideal = AerSimulator()
result_ideal = sim_ideal.run(circ).result()
plot_histogram(result_ideal.get_counts(0))
Contoh noise 1: Model noise error bit-flip dasarβ
Mari kita lihat contoh noise model mainan sederhana yang umum dalam penelitian teori informasi kuantum:
- Saat menerapkan gate satu Qubit, balikkan keadaan Qubit dengan probabilitas
p_gate1. - Saat menerapkan gate dua Qubit, terapkan error satu Qubit pada setiap Qubit.
- Saat mereset Qubit, reset ke 1 alih-alih 0 dengan probabilitas
p_reset. - Saat mengukur Qubit, balikkan keadaan Qubit dengan probabilitas
p_meas.
# Example error probabilities
p_reset = 0.03
p_meas = 0.1
p_gate1 = 0.05
# QuantumError objects
error_reset = pauli_error([("X", p_reset), ("I", 1 - p_reset)])
error_meas = pauli_error([("X", p_meas), ("I", 1 - p_meas)])
error_gate1 = pauli_error([("X", p_gate1), ("I", 1 - p_gate1)])
error_gate2 = error_gate1.tensor(error_gate1)
# Add errors to noise model
noise_bit_flip = NoiseModel()
noise_bit_flip.add_all_qubit_quantum_error(error_reset, "reset")
noise_bit_flip.add_all_qubit_quantum_error(error_meas, "measure")
noise_bit_flip.add_all_qubit_quantum_error(error_gate1, ["u1", "u2", "u3"])
noise_bit_flip.add_all_qubit_quantum_error(error_gate2, ["cx"])
print(noise_bit_flip)
NoiseModel:
Basis gates: ['cx', 'id', 'rz', 'sx', 'u1', 'u2', 'u3']
Instructions with noise: ['u3', 'u2', 'measure', 'cx', 'reset', 'u1']
All-qubits errors: ['reset', 'measure', 'u1', 'u2', 'u3', 'cx']
Menjalankan simulasi bersuaraβ
# Create noisy simulator backend
sim_noise = AerSimulator(noise_model=noise_bit_flip)
# Transpile circuit for noisy basis gates
passmanager = generate_preset_pass_manager(
optimization_level=3, backend=sim_noise
)
circ_tnoise = passmanager.run(circ)
# Run and get counts
result_bit_flip = sim_noise.run(circ_tnoise).result()
counts_bit_flip = result_bit_flip.get_counts(0)
# Plot noisy output
plot_histogram(counts_bit_flip)
Contoh 2: Relaksasi termal T1/T2β
Sekarang mari pertimbangkan model error yang lebih realistis berdasarkan relaksasi termal dengan lingkungan Qubit:
- Setiap Qubit diparameterisasi oleh konstanta waktu relaksasi termal dan konstanta waktu dephasing .
- Perlu diperhatikan bahwa kita harus memiliki .
- Tingkat error pada instruksi ditentukan oleh waktu gate dan nilai , Qubit.
# T1 and T2 values for qubits 0-3
T1s = np.random.normal(
50e3, 10e3, 4
) # Sampled from normal distribution mean 50 microsec
T2s = np.random.normal(
70e3, 10e3, 4
) # Sampled from normal distribution mean 50 microsec
# Truncate random T2s <= T1s
T2s = np.array([min(T2s[j], 2 * T1s[j]) for j in range(4)])
# Instruction times (in nanoseconds)
time_u1 = 0 # virtual gate
time_u2 = 50 # (single X90 pulse)
time_u3 = 100 # (two X90 pulses)
time_cx = 300
time_reset = 1000 # 1 microsecond
time_measure = 1000 # 1 microsecond
# QuantumError objects
errors_reset = [
thermal_relaxation_error(t1, t2, time_reset) for t1, t2 in zip(T1s, T2s)
]
errors_measure = [
thermal_relaxation_error(t1, t2, time_measure) for t1, t2 in zip(T1s, T2s)
]
errors_u1 = [
thermal_relaxation_error(t1, t2, time_u1) for t1, t2 in zip(T1s, T2s)
]
errors_u2 = [
thermal_relaxation_error(t1, t2, time_u2) for t1, t2 in zip(T1s, T2s)
]
errors_u3 = [
thermal_relaxation_error(t1, t2, time_u3) for t1, t2 in zip(T1s, T2s)
]
errors_cx = [
[
thermal_relaxation_error(t1a, t2a, time_cx).expand(
thermal_relaxation_error(t1b, t2b, time_cx)
)
for t1a, t2a in zip(T1s, T2s)
]
for t1b, t2b in zip(T1s, T2s)
]
# Add errors to noise model
noise_thermal = NoiseModel()
for j in range(4):
noise_thermal.add_quantum_error(errors_reset[j], "reset", [j])
noise_thermal.add_quantum_error(errors_measure[j], "measure", [j])
noise_thermal.add_quantum_error(errors_u1[j], "u1", [j])
noise_thermal.add_quantum_error(errors_u2[j], "u2", [j])
noise_thermal.add_quantum_error(errors_u3[j], "u3", [j])
for k in range(4):
noise_thermal.add_quantum_error(errors_cx[j][k], "cx", [j, k])
print(noise_thermal)
NoiseModel:
Basis gates: ['cx', 'id', 'rz', 'sx', 'u2', 'u3']
Instructions with noise: ['u3', 'u2', 'measure', 'cx', 'reset']
Qubits with noise: [0, 1, 2, 3]
Specific qubit errors: [('reset', (0,)), ('reset', (1,)), ('reset', (2,)), ('reset', (3,)), ('measure', (0,)), ('measure', (1,)), ('measure', (2,)), ('measure', (3,)), ('u2', (0,)), ('u2', (1,)), ('u2', (2,)), ('u2', (3,)), ('u3', (0,)), ('u3', (1,)), ('u3', (2,)), ('u3', (3,)), ('cx', (0, 0)), ('cx', (0, 1)), ('cx', (0, 2)), ('cx', (0, 3)), ('cx', (1, 0)), ('cx', (1, 1)), ('cx', (1, 2)), ('cx', (1, 3)), ('cx', (2, 0)), ('cx', (2, 1)), ('cx', (2, 2)), ('cx', (2, 3)), ('cx', (3, 0)), ('cx', (3, 1)), ('cx', (3, 2)), ('cx', (3, 3))]
Menjalankan simulasi bersuaraβ
# Run the noisy simulation
sim_thermal = AerSimulator(noise_model=noise_thermal)
# Transpile circuit for noisy basis gates
passmanager = generate_preset_pass_manager(
optimization_level=3, backend=sim_thermal
)
circ_tthermal = passmanager.run(circ)
# Run and get counts
result_thermal = sim_thermal.run(circ_tthermal).result()
counts_thermal = result_thermal.get_counts(0)
# Plot noisy output
plot_histogram(counts_thermal)
Langkah berikutnyaβ
- Untuk mensimulasikan Circuit bersuara, lihat Simulasi eksak dan bersuara dengan Qiskit Aer primitives.
- Tinjau referensi modul noise Qiskit Aer.