Qiskit Aer primitiveによる完全シミュレーションとノイズありシミュレーション
Package versions
The code on this page was developed using the following requirements. We recommend using these versions or newer.
qiskit[all]~=2.3.0
qiskit-aer~=0.17
Qiskit primitiveによる完全シミュレーションでは、Qiskitに含まれるリファレンスprimitiveを使用して量子回路の完全シミュレーションを実行する方法を説明しています。現在の量子プロセッサーにはエラー(ノイズ)が存在するため、完全シミュレーションの結果が実際のハードウェア上で回路を実行したときに期待される結果と必ずしも一致するわけではありません。Qiskitのリファレンスprimitiveはノイズのモデリングをサポートしていませんが、Qiskit Aerにはノイズモデリングをサポートするprimitiveの実装が含まれています。Qiskit Aerは高性能な量子回路シミュレーターであり、より高いパフォーマンスと多くの機能を実現するためにリファレンスprimitiveの代わりに使用できます。Qiskit AerはQiskit Ecosystemの一部です。この記事では、完全シミュレーションとノイズありシミュレーションにおけるQiskit Aer primitiveの使用方法を説明します。
qiskit-aerv0.14以降が必要です。- Qiskit Aer primitiveはprimitive インターフェースを実装していますが、Qiskit Runtime primitiveと同じオプションを提供するわけではありません。たとえば、耐性レベル(Resilience level)はQiskit Aer primitiveでは利用できません。
- Aerがサポートするシミュレーション方式のオプションについては、AerSimulatorのドキュメントを参照してください。
完全シミュレーションとノイズありシミュレーションを試すために、8量子ビットのサンプル回路を作成します。
# Added by doQumentation — required packages for this notebook
!pip install -q qiskit qiskit-aer
from qiskit.circuit.library import efficient_su2
n_qubits = 8
circuit = efficient_su2(n_qubits)
circuit.draw("mpl")
この回路には、ゲートとゲートの回転角を表すパラメーターが含まれています。この回路をシミュレーションする際には、これらのパラメーターに具体的な値を指定する必要があります。次のセルでは、これらのパラメーターにいくつかの値を指定し、Qiskit AerのEstimator primitiveを使用して、観測量の厳密な期待値を計算します。
from qiskit.quantum_info import SparsePauliOp
from qiskit.transpiler import generate_preset_pass_manager
from qiskit_aer import AerSimulator
from qiskit_aer.primitives import EstimatorV2 as Estimator
observable = SparsePauliOp("Z" * n_qubits)
params = [0.1] * circuit.num_parameters
exact_estimator = Estimator()
# The circuit needs to be transpiled to the AerSimulator target
pass_manager = generate_preset_pass_manager(3, AerSimulator())
isa_circuit = pass_manager.run(circuit)
pub = (isa_circuit, observable, params)
job = exact_estimator.run([pub])
result = job.result()
pub_result = result[0]
exact_value = float(pub_result.data.evs)
exact_value
0.8870140234256602
次に、すべてのCXゲートに2%の脱分極エラー(depolarizing error)を含むノイズモデルを初期化します。実際には、ここでのCXゲートのような2量子ビットゲートから生じるエラーが、回路を実行する際の主要なエラーの原因です。Qiskit Aerでのノイズモデルの構築概要については、ノイズモデルの構築を参照してください。
次のセルでは、このノイズモデルを組み込んだEstimatorを構築し、観測量の期待値を計算します。
from qiskit_aer.noise import NoiseModel, depolarizing_error
noise_model = NoiseModel()
cx_depolarizing_prob = 0.02
noise_model.add_all_qubit_quantum_error(
depolarizing_error(cx_depolarizing_prob, 2), ["cx"]
)
noisy_estimator = Estimator(
options=dict(backend_options=dict(noise_model=noise_model))
)
job = noisy_estimator.run([pub])
result = job.result()
pub_result = result[0]
noisy_value = float(pub_result.data.evs)
noisy_value
0.7247404214143528
ご覧のとおり、ノイズが存在する場合の期待値は正しい値から大きくかけ離れています。実際には、ノイズの影響を軽減するためにさまざまなエラー軽減手法を使用できますが、これらの手法の説明はこの記事の範囲外となります。
ノイズが最終結果にどのような影響を与えるかをおおまかに把握するために、各CXゲートに2%の脱分極エラーを追加するノイズモデルを考えてみましょう。確率の脱分極エラーは、密度行列に対して次の作用を持つ量子チャンネルとして定義されます。
ここでは量子ビット数で、この場合は2です。つまり、確率で状態が完全混合状態に置き換えられ、確率で状態が保存されます。脱分極チャンネルを回適用した後、状態が保存される確率はとなります。したがって、シミュレーションの終了時に正しい状態を保持する確率は、回路内のCXゲートの数に対し て指数的に減少することが予想されます。
回路内のCXゲートの数を数えてを計算してみましょう。count_opsを呼び出してゲート名とカウントのマッピングを含む辞書を取得し、CXゲートのエントリーを取り出します。
cx_count = circuit.count_ops()["cx"]
(1 - cx_depolarizing_prob) ** cx_count
0.6542558123199923
この値(65%)は、最終状態が正しい確率の概算です。シミュレーションの初期状態を考慮していないため、これは保守的な推定値です。
次のコードセルは、Qiskit AerのSampler primitiveを使用してノイズありの回路からサンプリングする方法を示しています。Sampler primitiveで実行する前に、回路に測定を追加する必要があります。
from qiskit_aer.primitives import SamplerV2 as Sampler
measured_circuit = circuit.copy()
measured_circuit.measure_all()
noisy_sampler = Sampler(
options=dict(backend_options=dict(noise_model=noise_model))
)
# The circuit needs to be transpiled to the AerSimulator target
pass_manager = generate_preset_pass_manager(3, AerSimulator())
isa_circuit = pass_manager.run(measured_circuit)
pub = (isa_circuit, params, 100)
job = noisy_sampler.run([pub])
result = job.result()
pub_result = result[0]
pub_result.data.meas.get_counts()
{'00100000': 1,
'00000000': 65,
'10101000': 1,
'10000000': 5,
'00001000': 1,
'00000110': 2,
'11110010': 1,
'00000011': 3,
'01010000': 3,
'11000000': 3,
'01111000': 1,
'01000000': 2,
'00000010': 1,
'01100000': 1,
'00011000': 1,
'00111100': 1,
'00010100': 1,
'00001111': 1,
'00110000': 1,
'01100101': 1,
'00000100': 1,
'10100000': 1,
'00000001': 1,
'11010000': 1}
次のステップ
- 小規模でシンプルな回路をシミュレーションするには、Qiskit primitiveによる完全シミュレーションを参照してください。
- Qiskit Aerのドキュメントをご確認ください。