メインコンテンツへスキップ
このプロジェクトはベータ版です。バグを見つけましたか?GitHub Issueを開く。質問やアイデアがありますか?Discussionsで質問する — フィードバックをお待ちしています!
このページの翻訳品質はいかがですか?

QESEM: QedmaによるQiskit Function

API リファレンス を参照してください

パッケージのバージョン

このページのコードは、以下の要件を使用して開発されました。 これらのバージョン以降を使用することをお勧めします。

qiskit[all]~=2.5.0
qiskit-ibm-runtime~=0.47.0
注記

Qiskit Functionsは、IBM Quantum® Premiumプラン、Flexプラン、およびOn-Prem(IBM Quantum Platform API経由)プランのユーザーのみが利用できる実験的な機能です。プレビューリリースの状態であり、変更される場合があります。

概要​

近年、量子処理ユニット(QPU)は大幅に改善されていますが、既存のハードウェアにおけるノイズや不完全性によるエラーは、量子アルゴリズム開発者にとって依然として中心的な課題です。この分野が古典的に検証できないユーティリティスケールの量子計算に近づくにつれて、精度を保証しながらノイズをキャンセルするソリューションがますます重要になっています。この課題を克服するため、QedmaはQuantum Error Mitigation(QESEM)を開発しました。これはQiskit Functionとして、IBM Quantum Platformにシームレスに統合されています。

QESEMを使用することで、ユーザーはノイズの多いQPU上で量子回路を実行し、基本的な限界に近い非常に効率的なQPU時間オーバーヘッドで、高精度なエラーのない結果を得ることができます。これを実現するために、QESEMはQedmaが開発した独自の手法のスイートを活用して、エラーの特性評価と低減を行っています。エラー低減技術には、ゲート最適化、ノイズを考慮したトランスパイレーション、エラー抑制(ES)、および不偏エラー緩和(EM)が含まれます。これらの特性評価に基づく手法を組み合わせることで、ユーザーは汎用的な大規模(高ボリューム)量子回路に対して信頼性の高いエラーのない結果を達成でき、それ以外では実現できないアプリケーションを解き放ちます。

基礎となるコンポーネントの詳細な説明とユーティリティスケールのデモについては、論文Reliable high-accuracy error mitigation for utility-scale quantum circuitsを参照してください。

説明​

QedmaのQESEM functionを使用することで、エラー抑制と緩和を適用した回路の見積もりと実行を簡単に行い、より大きな回路容量とより高い精度を達成できます。QESEMを使用するには、量子回路、測定するオブザーバブルのセット、各オブザーバブルの目標統計精度、および選択したQPUを指定します。目標精度まで回路を実行する前に、回路の実行を必要としない解析的計算に基づいて必要なQPU時間を見積もることができます。QPU時間の見積もりに納得したら、QESEMで回路を実行できます。

回路を実行すると、QESEMはお使いの回路に合わせたデバイス特性評価プロトコルを実行し、回路内で発生するエラーの信頼性の高いノイズモデルを生成します。この特性評価に基づいて、QESEMはまずノイズを考慮したトランスパイレーションを実装し、入力回路を物理量子ビットとゲートのセットにマッピングして、目標オブザーバブルに影響するノイズを最小化します。これには、ネイティブで使用可能なゲート(IBM®デバイスのCX/CZ)と、QESEMによって最適化された追加のゲートが含まれ、QESEMの拡張ゲートセットを形成しています。次に、QESEMはQPU上で特性評価に基づくESおよびEM回路のセットを実行し、その測定結果を収集します。これらは古典的な後処理によって、要求された精度に対応する各オブザーバブルの不偏期待値とエラーバーを提供します。

Qedma QESEM overview QESEMは、さまざまな量子アプリケーションに対して高精度な結果を提供し、現在達成可能な最大の回路容量での実証がなされています。QESEMは以下のユーザー向け機能を提供しており、以下のベンチマークセクションで実証されています:

  • 精度の保証: QESEMはオブザーバブルの期待値に対する不偏推定を出力します。そのEM手法は理論的な保証を備えており、Qedmaの最先端の特性評価と組み合わせることで、緩和がユーザー指定の精度までノイズのない回路出力に収束することを保証します。系統的なエラーや偏りが生じやすい多くのヒューリスティックなEM手法とは対照的に、QESEMの精度保証は、汎用的な量子回路とオブザーバブルにおいて信頼性の高い結果を確保するために不可欠です。
  • 大規模QPUへのスケーラビリティ: QESEMのQPU時間は回路容量に依存しますが、それ以外は量子ビット数に依存しません。Qedmaは、IBM Quantum 127量子ビットEagleおよび133量子ビットHeronデバイスを含む、現在利用可能な最大の量子デバイスでQESEMを実証しています。
  • アプリケーション非依存: QESEMは、ハミルトニアンシミュレーション、VQE、QAOA、振幅推定など、さまざまなアプリケーションで実証されています。ユーザーは任意の量子回路と測定するオブザーバブルを入力し、正確なエラーのない結果を得ることができます。唯一の制限は、アクセス可能な回路容量と出力精度を決定するハードウェア仕様と割り当てられたQPU時間によって決まります。対照的に、多くのエラー低減ソリューションはアプリケーション固有であるか、制御されていないヒューリスティックを含んでおり、汎用的な量子回路とアプリケーションには適用できません。
  • 拡張ゲートセット: QESEMは分数角度ゲートをサポートし、IBM Quantum HeronおよびEagleデバイスでQedma最適化の分数角度Rzz(θ)Rzz(\theta)ゲートを提供します。この拡張ゲートセットにより、より効率的なコンパイルが可能になり、デフォルトのCX/CZコンパイルと比較して最大2倍の回路容量が利用可能になります。
  • マルチベースオブザーバブル: QESEMは、汎用的なハミルトニアンなど、多くの非可換Pauli文字列で構成された入力オブザーバブルをサポートします。測定ベースの選択とQPUリソース配分(ショットと回路)の最適化は、要求された精度に必要なQPU時間を最小化するためにQESEMによって自動的に実行されます。ハードウェアの忠実度と実行レートを考慮したこの最適化により、より深い回路を実行してより高い精度を得ることができます。

ベンチマーク​

QESEMは、さまざまなユースケースとアプリケーションでテストされています。以下の例は、QESEMで実行できるワークロードの種類を評価するのに役立ちます。

所与の回路とオブザーバブルに対して、エラー緩和と古典的シミュレーションの両方の難しさを定量化するための主要な評価指標はアクティブボリュームです:回路内でオブザーバブルに影響するCNOTゲートの数です。アクティブボリュームは、回路の深さと幅、オブザーバブルの重み、およびオブザーバブルのライトコーンを決定する回路構造に依存します。詳細については、2024 IBM Quantum Summitのトークを参照してください。QESEMは高ボリュームの領域で特に大きな価値を提供し、汎用的な回路とオブザーバブルに対して信頼性の高い結果をもたらします。

Active volume

アプリケーション量子ビット数デバイス回路の説明精度合計時間ランタイム使用量
VQE回路8Eagle (r3)21層合計、9測定ベース、1Dチェーン98%35分14分
Kicked Ising28Eagle (r3)3ユニーク層 × 3ステップ、2D heavy-hexトポロジー97%22分4分
Kicked Ising28Eagle (r3)3ユニーク層 × 8ステップ、2D heavy-hexトポロジー97%116分23分
トロッタライズドハミルトニアンシミュレーション40Eagle (r3)2ユニーク層 × 10トロッターステップ、1Dチェーン97%3時間25分
トロッタライズドハミルトニアンシミュレーション119Eagle (r3)3ユニーク層 × 9トロッターステップ、2D heavy-hexトポロジー95%6.5時間45分
Kicked Ising136Heron (r2)3ユニーク層 × 15ステップ、2D heavy-hexトポロジー99%52分9分

ここでの精度はオブザーバブルの理想値に対して相対的に測定されています:⟨O⟩ideal−ϵ⟨O⟩ideal\frac{\langle O \rangle_{ideal} - \epsilon}{\langle O \rangle_{ideal}}。ここで「ϵ\epsilon」は緩和の絶対精度(ユーザー入力で設定)であり、⟨O⟩ideal\langle O \rangle_{ideal}はノイズのない回路でのオブザーバブルです。 「ランタイム使用量」は batch mode でのベンチマークの使用量を測定します(個々のジョブの使用量の合計)。一方、「合計時間」は session mode での使用量を測定します(実験のウォール時間)。これには追加の古典的処理と通信時間が含まれます。QESEMは両方のモードでの実行が可能であり、ユーザーは利用可能なリソースを最大限に活用できます。

28量子ビットのKicked Ising回路は、ibm_kawasakiの3つの連結ループ上で、Shinjo et al.が研究した離散時間準結晶(arXiv 2403.16718およびQ2B24 Tokyoを参照)をシミュレートします。ここで使用した回路パラメータは(θx,θz)=(0.9π,0)(\theta_x, \theta_z) = (0.9 \pi, 0)で、強磁性初期状態∣ψ0⟩=∣0⟩⊗n| \psi_0 \rangle = | 0 \rangle ^{\otimes n}を用いています。測定されたオブザーバブルは磁化の絶対値M=∣128∑i=027⟨Zi⟩∣M = |\frac{1}{28} \sum_{i=0}^{27} \langle Z_i \rangle|です。ユーティリティスケールのKicked Ising実験はibm_fezの最良の136量子ビット上で実行されました。この特定のベンチマークはClifford角(θx,θz)=(π,0)(\theta_x, \theta_z) = (\pi, 0)で実行されました。この角度では、アクティブボリュームが回路深さとともにゆっくりと増加するため、高いデバイス忠実度と合わせて、短いランタイムで高精度が実現できます。

トロッタライズドハミルトニアンシミュレーション回路は、分数角度での横断磁場Isingモデル用のものです:(θzz,θx)=(π/4,π/8)(\theta_{zz}, \theta_x) = (\pi / 4, \pi /8)および(θzz,θx)=(π/6,π/8)(\theta_{zz}, \theta_x) = (\pi / 6, \pi / 8)(Q2B24 Tokyoを参照)。ユーティリティスケールの回路はibm_brisbaneの最良の119量子ビット上で実行され、40量子ビットの実験は利用可能な最良のチェーン上で実行されました。精度は磁化について報告されており、より高い重みのオブザーバブルについても高精度な結果が得られています。

VQE回路は、Deutsches Elektronen-Synchrotron(DESY)の量子技術・応用センターの研究者と共同で開発されました。ここでの目標オブザーバブルは、多数の非可換Pauli文字列からなるハミルトニアンであり、マルチベースオブザーバブルに対するQESEMの最適化されたパフォーマンスを強調しています。緩和は古典的に最適化されたansatzに適用されました。これらの結果はまだ未発表ですが、同様の構造的特性を持つ異なる回路についても同等の品質の結果が得られます。

はじめに​

IBM Quantum Platform APIキーを使用して認証し、以下のようにQESEM Qiskit Functionを選択します。(このスニペットは、すでにアカウントを保存済みであることを前提としています。)

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

_needed = {"qiskit": "qiskit", "qiskit_ibm_catalog": "qiskit-ibm-catalog", "qiskit_ibm_runtime": "qiskit-ibm-runtime"}
_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 qiskit
from qiskit_ibm_catalog import QiskitFunctionsCatalog

catalog = QiskitFunctionsCatalog(channel="ibm_quantum_platform")

# verify that you have access to the function
catalog.list()
# load the function
qesem_function = catalog.load("qedma/qesem")

例​

時間推定ジョブの例​

時間推定ジョブは、特定の pub と backend_name に必要な QPU 時間を推定するのに役立ちます。backend_name には、任意のシミュレーター backend(たとえば fake_fez)を設定することもできます。

QESEM は、準確率的な、特性評価ベースの EM 手法を使用します。この手法には、おおよそ次のようにスケールする QPU 時間のオーバーヘッドがあります。

TQPU=aeαIF⋅Vaϵ2+bT_{QPU} = a \frac{e^{\alpha IF\cdot V_a}}{\epsilon^2} + b

ここで、VaV_a は Circuit のアクティブボリューム、ϵ\epsilon は目標精度、IFIF はネイティブゲートの infidelity です。

"estimate_time_only": "empirical"を使用すると、ジョブに必要な時間を見積もるためにQPU時間を数分使用することに注意してください(バックエンドが実機の場合。シミュレーターの場合はQPU時間は使用されません)。これには通常約5分かかりますが、10分を超えることはありません。ゲートの不忠実度(infidelity)が経験的な時間見積もりジョブとミティゲーションジョブの間で大きく変化する場合、QPU時間も大きく変化します。

はじめに、所与のpubについてQESEMを実行するために必要なQPU時間を見積もる基本的な例を試してみましょう:

# This cell is hidden from users
from qiskit_ibm_runtime import QiskitRuntimeService

service = QiskitRuntimeService()
backend_name = service.least_busy().name
backend_name = "fake_fez"

circ = qiskit.QuantumCircuit(5)
circ.cx(0, 1)
circ.cx(2, 3)
circ.cx(1, 2)
circ.cx(3, 4)

avg_magnetization = qiskit.quantum_info.SparsePauliOp.from_sparse_list(
[("Z", [q], 1 / 5) for q in range(5)], num_qubits=5
)
other_observable = qiskit.quantum_info.SparsePauliOp.from_sparse_list(
[("ZZ", [0, 1], 1.0), ("XZ", [1, 4], 0.5)], num_qubits=5
)

time_estimation_job = qesem_function.run(
pubs=[(circ, [avg_magnetization, other_observable])],
options={
"estimate_time_only": "empirical",
},
backend_name=backend_name, # example: "fake_fez", "ibm_fez"
)
time_estimate_result = (
time_estimation_job.result()
) # a list of results per pub (circuit)

以下のコードスニペットは、時間見積もりジョブから異なる実行メトリクスを取得する方法を示しています(estimate_time_onlyが設定されている場合):

pub_result = time_estimate_result[0]

print(
f"The estimated QPU time for mitigation for this PUB is: {pub_result.metadata['time_estimation_sec']}"
)
print(
f"The QPU time that this time estimation job took is (here it is 0 because we used fake_fez): {pub_result.metadata['total_qpu_time']}"
)
print(
f"Gates fidelity measured during the experiment: {pub_result.metadata['gate_fidelities']}"
)
print(f"Total shots: {pub_result.metadata['total_shots']}")
print(f"Resource usage breakdown: {pub_result.metadata['resource_usage']}")
The estimated QPU time for mitigation for this PUB is: 300
The QPU time that this time estimation job took is (here it is 0 because we used fake_fez): 0
Gates fidelity measured during the experiment: {'CZ': 0.9951354916722668, 'ID1Q': 0.9991246627329172}
Total shots: 220000
Resource usage breakdown: {'RUNNING: MAPPING': {'CPU_TIME': 33.6066133165732, 'GPU_TIME': 0.0, 'QPU_TIME': 0.0}, 'RUNNING: OPTIMIZING_FOR_HARDWARE': {'CPU_TIME': 184.53575124032795, 'GPU_TIME': 0.0, 'QPU_TIME': 0.0}, 'RUNNING: WAITING_FOR_QPU': {'CPU_TIME': 0.0, 'GPU_TIME': 0.0, 'QPU_TIME': 0.0}, 'RUNNING: EXECUTING_QPU': {'CPU_TIME': 0.0, 'GPU_TIME': 0.0, 'QPU_TIME': 0.0}, 'RUNNING: POST_PROCESSING': {'CPU_TIME': 0.0, 'GPU_TIME': 0.0, 'QPU_TIME': 0.0}}

経験的な時間見積もりが有効になっている場合、QESEMはより正確なQPU時間見積もりを提供するために少数の回路を実行します。これらの回路からのミティゲーション結果は、ジョブのempirical_estimation_mitigation_resultsフィールドで利用できます。

これらの結果は限られた回路サンプルから導出されているため、完全なQESEMミティゲーションジョブから得られる最終結果よりも大幅に精度が低くなります。ただし、回路が小さい場合や目標精度が低い場合、経験的な時間見積もり中に実行されるミティゲーションで目的の精度に達するのに十分な場合があり、完全なミティゲーションジョブが不要になることもあります。

empirical_estimation_mitigation_resultsフィールドは、入力パラメーターごとのPrimitiveResultオブジェクトのリストです。回路がパラメータ化されていない場合、リストの長さは1になります。

empirical_estimation_mitigation_results = time_estimate_result[0].metadata[
"empirical_estimation_mitigation_results"
][0] # a list per parameter
print("Partial results for the observables:")

print(
f" Mitigated expectation values: {empirical_estimation_mitigation_results.data.evs}"
)
print(
f" Mitigated error bars: {empirical_estimation_mitigation_results.data.stds}"
)
print(
f" Number of shots used for mitigation: {empirical_estimation_mitigation_results.metadata['mitigation_shots']}"
)
transpiled_circ = empirical_estimation_mitigation_results.metadata[
"transpiled_circ"
]
print(f" Qubit mapping: {transpiled_circ['qubit_maps']}")
print(
f" Number of measurement bases: {transpiled_circ['num_measurement_bases']}\n"
)

# results per obs
emp_obs_results = empirical_estimation_mitigation_results.metadata["results"][
0
]
# print(f"Results for each observable: {results}")
print("Results for each observable:")

for i, (obs_array, result_dict) in enumerate(emp_obs_results):
# obs_array, result_dict = results
print(f"Observable {i+1}: {obs_array}")
print(
f" QESEM mitigated value: {result_dict['qesem']['value']} \u00b1 {result_dict['qesem']['error_bar']}"
)
Partial results for the observables:
Mitigated expectation values: [1.00347302 1.00693905]
Mitigated error bars: [0.00304061 0.00714276]
Number of shots used for mitigation: 180000
Qubit mapping: [[[0, 136], [1, 143], [2, 142], [3, 141], [4, 140]]]
Number of measurement bases: 2

Results for each observable:
Observable 1: ObservablesArray({'IIIIZ': 0.2, 'IIIZI': 0.2, 'IIZII': 0.2, 'IZIII': 0.2, 'ZIIII': 0.2}, shape=())
QESEM mitigated value: 1.003473015776871 ± 0.0030406128032204015
Observable 2: ObservablesArray({'IIIZZ': 1.0, 'ZIIXI': 0.5}, shape=())
QESEM mitigated value: 1.0069390542613554 ± 0.0071427606736885925

QESEMミティゲーションジョブの例​

以下の例はQESEMジョブを実行します:

sample_job = qesem_function.run(
pubs=[(circ, [avg_magnetization, other_observable])],
backend_name=backend_name, # example: "ibm_fez"
# options = {
# "estimate_time_only": "empirical",
# "default_precision": 0.2, # Default precision is applied to all pubs that don't have a precision specified, see API reference for more details
# "max_execution_time": 3600, # You can specify a maximum QPU time in seconds, see API reference for more details
# "transpilation_level": "standard", # "minimal_with_layout_opt" for minimal transpilation, see API reference for more details
# "parallel_execution": True, # True for parallel execution, see API reference for more details
# },
)

各入力フィールドとオプションの詳細な説明については、QESEM APIリファレンスを参照してください。 使い慣れたQiskit Serverless APIを使用して、Qiskit Functionワークロードのステータスを確認したり、結果を返したりすることができます:

# Print the ID so you can use it later, if necessary
print(sample_job.job_id)
print(sample_job.status())
sample_result = sample_job.result()
3ac6b2df-15b0-4dc0-8f48-cf14bd20a1c8
DONE

以下のコードスニペットは、ミティゲーション結果と実行メトリクスを取得する方法を示しています。これらには、さまざまなパラメータがQESEM実行にどのように影響するかをより深く理解するための重要なデータが含まれています。研究に基づいて論文を書く際にも関連する可能性があります。

for pub_idx, pub_result in enumerate(
sample_result
): # each element in the list is a result for a different pub, here we sent only one pub
print(f"\nPUB {pub_idx}:")
print(
f" The QPU time that this job took is (here it is 0 because we used fake_fez): {pub_result.metadata['total_qpu_time']}"
)
print(
f" Gates fidelity measured during the experiment: {pub_result.metadata['gate_fidelities']}"
)
print(f" Total shots: {pub_result.metadata['total_shots']}")
print(
f" Number of shots used for mitigation: {pub_result.metadata['mitigation_shots']}"
)
print(
f" Resource usage breakdown: {pub_result.metadata['resource_usage']}"
)
PUB 0:
The QPU time that this job took is (here it is 0 because we used fake_fez): 0.0
Gates fidelity measured during the experiment: {'CZ': 0.9953704216147041, 'ID1Q': 0.9991834123567518}
Total shots: 446000
Number of shots used for mitigation: 194000
Resource usage breakdown: {'RUNNING: MAPPING': {'CPU_TIME': 32.52745003718883, 'GPU_TIME': 0.0, 'QPU_TIME': 0.0}, 'RUNNING: OPTIMIZING_FOR_HARDWARE': {'CPU_TIME': 257.850521848537, 'GPU_TIME': 0.0, 'QPU_TIME': 0.0}, 'RUNNING: WAITING_FOR_QPU': {'CPU_TIME': 0.0, 'GPU_TIME': 0.0, 'QPU_TIME': 0.0}, 'RUNNING: EXECUTING_QPU': {'CPU_TIME': 0.0, 'GPU_TIME': 0.0, 'QPU_TIME': 0.0}, 'RUNNING: POST_PROCESSING': {'CPU_TIME': 0.0, 'GPU_TIME': 0.0, 'QPU_TIME': 0.0}}

metadata["results"]では、結果はまず回路インスタンスごとに、次にオブザーバブルごとにグループ化されます。

print("Full QESEM mitigation results:")

for pub_idx, pub_result in enumerate(sample_result):
print(f"\nPUB {pub_idx}:")

print(f" Mitigated expectation values: {pub_result.data.evs}")
print(f" Mitigated error bars: {pub_result.data.stds}")
noisy_results = pub_result.metadata.get("noisy_results")
print(f" Unmitigated expectation values: {noisy_results.evs}")
print(f" Unmitigated error bars: {noisy_results.stds}")

print(" Transpiled circuits:")
for circ_idx, transpiled_circ in enumerate(
pub_result.metadata["transpiled_circs"]
):
print(f" Circuit {circ_idx}:")
# print(f" Circuit: \n {transpiled_circ['circuit']}") # not printing it because it's long but you can see the transpiled circuit itself
print(f" Qubit mapping: {transpiled_circ['qubit_maps']}")
print(
f" Measurement bases: {transpiled_circ['num_measurement_bases']}"
)

print(" Results for each observable:")
for circ_idx, circ_results in enumerate(pub_result.metadata["results"]):
print(f" Circuit {circ_idx}:")
for obs_idx, (obs_array, result_dict) in enumerate(circ_results):
print(f" Observable {obs_idx}: {obs_array}")
print(
f" QESEM mitigated value: {result_dict['qesem']['value']} ± {result_dict['qesem']['error_bar']}"
)
print(
f" Unmitigated value: {result_dict['unmitigated']['value']} ± {result_dict['unmitigated']['error_bar']}"
)
Full QESEM mitigation results:

PUB 0:
Mitigated expectation values: [1.00648343 1.00636289]
Mitigated error bars: [0.00253812 0.00693586]
Unmitigated expectation values: [0.98031429 0.96357143]
Unmitigated error bars: [0.00124128 0.00578812]
Transpiled circuits:
Circuit 0:
Qubit mapping: [[[0, 140], [1, 141], [2, 142], [3, 143], [4, 136]]]
Measurement bases: 2
Results for each observable:
Circuit 0:
Observable 0: ObservablesArray({'IIIIZ': 0.2, 'IIIZI': 0.2, 'IIZII': 0.2, 'IZIII': 0.2, 'ZIIII': 0.2}, shape=())
QESEM mitigated value: 1.0064834305181962 ± 0.002538119914534849
Unmitigated value: 0.9803142857142859 ± 0.0012412835813609938
Observable 1: ObservablesArray({'IIIZZ': 1.0, 'ZIIXI': 0.5}, shape=())
QESEM mitigated value: 1.0063628870614818 ± 0.006935859820870656
Unmitigated value: 0.9635714285714285 ± 0.005788121870526659

主な結果の内訳:

  • mitigated:完全にミティゲートされたQESEM期待値。
  • unmitigated:エラーミティゲーションを適用していない生の物理ノイズ結果。

QESEMヒューリスティック外挿結果​

単一のprecision浮動小数点数を使用する標準的なQESEM実行では、結果にはQESEMヒューリスティックに使用される自動的に利用可能なノイズスケーリングポイントも含まれます。これらのポイントは追加のQPUリソースなしで計算されます。

スケール1.0は読み出しミティゲーション(REM)を伴う物理デバイスのノイズレベルを表し、スケール2.0は同じくREMを伴う補完的なノイズ増幅ポイントです。これらのポイントはqesem_heuristic結果を生成するために使用されます。

  • qesem_heuristic:利用可能なノイズスケーリングされたデータから計算されたZNEスタイルの推定値。現在、これは指数外挿を使用しています。

  • noise_scaling.results_with_REM:異なるノイズスケールでの期待値で、すべて読み出しミティゲーション(REM)を伴います。

微妙ですが重要な詳細として、スケール1.0の結果はunmitigatedの結果と同じではありません。どちらも物理デバイスのノイズレベルに対応していますが、スケール1.0のポイントは読み出しミティゲーションを含んでいるのに対し、unmitigatedは含んでいません。

print("QESEM heuristic results:")

for pub_idx, pub_result in enumerate(sample_result):
print(f"\nPUB {pub_idx}:")
for circ_idx, circ_results in enumerate(pub_result.metadata["results"]):
print(f" Circuit {circ_idx}:")
for obs_idx, (obs_array, result_dict) in enumerate(circ_results):
print(f" Observable {obs_idx}: {obs_array}")
qesem_heuristic = result_dict["qesem_heuristic"][0]
print(" QESEM heuristic:")
print(
f" Value: {qesem_heuristic['value']} ± {qesem_heuristic['error_bar']}"
)
print(
f" Extrapolation: {qesem_heuristic['extrapolation']}"
)
print(
f" Scale factors: {qesem_heuristic['scale_factors']}"
)
noise_scaling = result_dict["noise_scaling"]
print(" Noise scaling results:")
print(
f" Scaling method: {noise_scaling['scaling_method']}"
)
print(" Results with Readout mitigation (REM):")
for rem_result in sorted(
(
item
for item in noise_scaling["results_with_REM"]
if item["scale"] != 0.0
),
key=lambda item: item["scale"],
):
print(
f" Scale factor {rem_result['scale']}: {rem_result['value']} ± {rem_result['error_bar']}"
)
QESEM heuristic results:

PUB 0:
Circuit 0:
Observable 0: ObservablesArray({'IIIIZ': 0.2, 'IIIZI': 0.2, 'IIZII': 0.2, 'IZIII': 0.2, 'ZIIII': 0.2}, shape=())
QESEM heuristic:
Value: 1.0008161638888535 ± 0.0038859458884403964
Extrapolation: exponential
Scale factors: [1.0, 2.0]
Noise scaling results:
Scaling method: QESEM
Results with Readout mitigation (REM):
Scale factor 1.0: 0.9918395459270772 ± 0.0012565417579355634
Scale factor 2.0: 0.982943441922748 ± 0.0028919278067695018
Observable 1: ObservablesArray({'IIIZZ': 1.0, 'ZIIXI': 0.5}, shape=())
QESEM heuristic:
Value: 0.9960853148925298 ± 0.013811635038961175
Extrapolation: exponential
Scale factors: [1.0, 2.0]
Noise scaling results:
Scaling method: QESEM
Results with Readout mitigation (REM):
Scale factor 1.0: 0.9902860583785115 ± 0.005921236914723409
Scale factor 2.0: 0.984520565414274 ± 0.006909522262347639
備考

以下の例は機能固有の入力と結果に焦点を当てているため、毎回完全な実行メトリクスは出力しません。前述したトップレベルのメタデータ(total_qpu_time、gate_fidelities、total_shots、mitigation_shots、resource_usageなど)は、これらのジョブでも利用できます。

前の例からの一部の変数(バックエンド、オブザーバブル、基本回路パラメーターを含む)は、簡潔にするために以下で再利用されます。

備考

以下の例はすべて、経験的時間推定を用いても実行できます。これを有効にするには、ファンクションオプションで"estimate_time_only": "empirical"を渡してください。

パラメータ化された回路の例​

多くのアルゴリズムは、同じ回路を複数のパラメーター値で評価します。パラメータ化された回路を1つのQESEMジョブとして送信することで、QESEMは回路インスタンス間でキャラクタリゼーションとキャリブレーションを共有でき、個別のジョブを実行する場合と比較してQPU時間のオーバーヘッドを削減できます。

パラメータ化された回路を送信するには、"minimal_with_layout_opt"トランスパイルレベルを使用する必要があります。 このレベルで送信される回路は、バックエンドに応じて、すでにバックエンドの基底ゲートを使用して表現されている必要があります。このレベルでは、QESEMは送信された構造を可能な限り入力回路に近い状態に保ち、レイヤー化(並列2量子ビットゲートのレイヤーへの操作のグループ化)中にバリアを尊重し、高忠実度量子ビットとデバイス接続性へのハードウェアマッピングを自動的に処理し続けます。

実際には、これは、送信前に回路をターゲットバックエンドの基底ゲートにトランスパイルする必要があることを意味します。基本的な基底ゲートトランスパイルの例を以下に示します。

QESEMは現在、パラメーターセットごとに1つのオブザーバブルのみをサポートしています。以下の2つのパラメーター行は、2つのオブザーバブルとzipされます。1行目はavg_magnetizationで測定され、2行目はother_observableで測定されます。

# Transpile to the backend basis gates only. With minimal_with_layout_opt, QESEM handles hardware mapping/connectivity and observable layout internally.
from qiskit_ibm_runtime.fake_provider import FakeFez

backend = FakeFez()
basis = backend.operation_names
print(basis)

param0 = qiskit.circuit.Parameter("param0")
param1 = qiskit.circuit.Parameter("param1")
parametrized_circ = qiskit.QuantumCircuit(5)
parametrized_circ.rx(param0, 0)
parametrized_circ.rx(param1, 1)
parametrized_circ.cx(0, 1)
parametrized_circ.cx(2, 3)
parametrized_circ.cx(1, 2)
parametrized_circ.cx(3, 4)

parametrized_circ = qiskit.transpile(
parametrized_circ, basis_gates=basis, optimization_level=1
)
parametrized_parameter_values = [[0.5, 0.1], [0.0, 0.6]]
parametrized_observables = [avg_magnetization, other_observable]

parametrized_job = qesem_function.run(
pubs=[
(
parametrized_circ,
parametrized_observables,
parametrized_parameter_values,
0.1,
)
],
backend_name=backend_name,
options={
"max_execution_time": 300,
"transpilation_level": "minimal_with_layout_opt",
},
)
print(parametrized_job.job_id)
print(parametrized_job.status())
d1b0e29b-196c-4896-aec6-44a268ebd874
DONE
parametrized_result = parametrized_job.result()
print("Parameterized circuit QESEM results:")

for pub_idx, pub_result in enumerate(parametrized_result):
print(f"\nPUB {pub_idx}:")
print(f" Mitigated expectation values: {pub_result.data.evs}")
print(f" Mitigated error bars: {pub_result.data.stds}")
noisy_results = pub_result.metadata["noisy_results"]
print(f" Unmitigated expectation values: {noisy_results.evs}")
print(f" Unmitigated error bars: {noisy_results.stds}")
print(" Results for each parameter value:")
for param_idx, param_results in enumerate(pub_result.metadata["results"]):
print(
f" Parameter set {param_idx}: {parametrized_parameter_values[param_idx]}"
)
for obs_idx, (obs_array, result_dict) in enumerate(param_results):
print(f" Observable {obs_idx}: {obs_array}")
print(
f" QESEM mitigated value: {result_dict['qesem']['value']} ± {result_dict['qesem']['error_bar']}"
)
print(
f" Unmitigated value: {result_dict['unmitigated']['value']} ± {result_dict['unmitigated']['error_bar']}"
)
Parameterized circuit QESEM results:

PUB 0:
Mitigated expectation values: [0.92392021 0.82517653]
Mitigated error bars: [0.00565281 0.00616016]
Unmitigated expectation values: [0.9028 0.78771429]
Unmitigated error bars: [0.00335142 0.00925413]
Results for each parameter value:
Parameter set 0: [0.5, 0.1]
Observable 0: ObservablesArray({'IIIIZ': 0.2, 'IIIZI': 0.2, 'IIZII': 0.2, 'IZIII': 0.2, 'ZIIII': 0.2}, shape=())
QESEM mitigated value: 0.923920210615709 ± 0.005652811570890183
Unmitigated value: 0.9028 ± 0.0033514176105045447
Parameter set 1: [0.0, 0.6]
Observable 0: ObservablesArray({'IIIZZ': 1.0, 'ZIIXI': 0.5}, shape=())
QESEM mitigated value: 0.8251765289285893 ± 0.006160161743353999
Unmitigated value: 0.7877142857142858 ± 0.009254130564027902

マルチPUBの例​

マルチPUB実行は、1つのQESEMジョブで複数の関連する回路を実行したい場合に便利です。パラメータ化実行と同様に、QESEMは個別のジョブで繰り返す代わりに回路インスタンス間でキャラクタリゼーションとキャリブレーションを共有できるため、オーバーヘッドを削減できます。

これは、異なる回路が同じ固有のレイヤーを再利用するトロッター型ワークロードなど、共有レイヤー構造を持つ回路に特に有用です。この場合、それらを一緒に実行することで、独立したQESEMジョブと比較してキャラクタリゼーションのコストを削減できます。

マルチPUBジョブには"transpilation_level": "minimal_with_layout_opt"が必要です。パラメータ化の例と同様に、回路は送信前にターゲットバックエンドの基底ゲートにトランスパイルする必要があります。その後、QESEMはデバイス接続性、レイアウト、高忠実度量子ビットへのマッピングを内部で処理します。

以下の各PUBには1つの回路と、このノートブックで先に使用したのと同じ2つのオブザーバブルが含まれているため、返されるPrimitiveResultには入力回路ごとに1つのPubResultが含まれます。

以下の例では、同じレイヤーパターンを持つ2つの単純なトロッター回路を使用しています。circ_aは1つのトロッターレイヤーを持ち、circ_bは同じレイヤーパターンを2回繰り返します。これにより、共有構造が明確になります。

def make_trotter_circuit(num_qubits, num_layers, zz_angle=0.2, x_angle=0.1):
trotter_circ = qiskit.QuantumCircuit(num_qubits)
for _ in range(num_layers):
for q in range(num_qubits):
trotter_circ.rx(x_angle, q)
trotter_circ.barrier()
for q in range(0, num_qubits - 1, 2):
trotter_circ.rzz(zz_angle, q, q + 1)
trotter_circ.barrier()
for q in range(1, num_qubits - 1, 2):
trotter_circ.rzz(zz_angle, q, q + 1)
trotter_circ.barrier()
return trotter_circ

circ_a = make_trotter_circuit(num_qubits=5, num_layers=1)
circ_b = make_trotter_circuit(num_qubits=5, num_layers=2)
multi_pubs = [
(
qiskit.transpile(qci, basis_gates=basis, optimization_level=1),
[avg_magnetization, other_observable],
)
for qci in [circ_a, circ_b]
]

multi_circ_job = qesem_function.run(
pubs=multi_pubs,
backend_name=backend_name,
options={
"max_execution_time": 300,
"transpilation_level": "minimal_with_layout_opt",
"default_precision": 0.1,
},
)
print(multi_circ_job.job_id)
print(multi_circ_job.status())
e34565b8-7262-4133-a120-de42ce624a99
DONE
multi_circ_result = multi_circ_job.result()
print("Multi-pub QESEM results:")

for pub_idx, pub_result in enumerate(multi_circ_result):
print(f"\nPUB {pub_idx}:")
print(f" Mitigated expectation values: {pub_result.data.evs}")
print(f" Mitigated error bars: {pub_result.data.stds}")
noisy_results = pub_result.metadata["noisy_results"]
print(f" Unmitigated expectation values: {noisy_results.evs}")
print(f" Unmitigated error bars: {noisy_results.stds}")
print(" Results for each observable:")
for circ_idx, circ_results in enumerate(pub_result.metadata["results"]):
print(f" Circuit {circ_idx}:")
for obs_idx, (obs_array, result_dict) in enumerate(circ_results):
print(f" Observable {obs_idx}: {obs_array}")
print(
f" QESEM mitigated value: {result_dict['qesem']['value']} ± {result_dict['qesem']['error_bar']}"
)
print(
f" Unmitigated value: {result_dict['unmitigated']['value']} ± {result_dict['unmitigated']['error_bar']}"
)
Multi-pub QESEM results:

PUB 0:
Mitigated expectation values: [0.99502406 1.02209332]
Mitigated error bars: [0.00483819 0.00707488]
Unmitigated expectation values: [0.96934286 0.97271429]
Unmitigated error bars: [0.00124855 0.00617294]
Results for each observable:
Circuit 0:
Observable 0: ObservablesArray({'IIIIZ': 0.2, 'IIIZI': 0.2, 'IIZII': 0.2, 'IZIII': 0.2, 'ZIIII': 0.2}, shape=())
QESEM mitigated value: 0.9950240647925642 ± 0.004838188086259301
Unmitigated value: 0.9693428571428573 ± 0.0012485470362492692
Observable 1: ObservablesArray({'IIIZZ': 1.0, 'ZIIXI': 0.5}, shape=())
QESEM mitigated value: 1.0220933230604674 ± 0.007074884384355636
Unmitigated value: 0.9727142857142859 ± 0.006172939375512439

PUB 1:
Mitigated expectation values: [0.98850017 1.02555188]
Mitigated error bars: [0.0077912 0.01672652]
Unmitigated expectation values: [0.93682857 0.95371429]
Unmitigated error bars: [0.00156245 0.00665735]
Results for each observable:
Circuit 0:
Observable 0: ObservablesArray({'IIIIZ': 0.2, 'IIIZI': 0.2, 'IIZII': 0.2, 'IZIII': 0.2, 'ZIIII': 0.2}, shape=())
QESEM mitigated value: 0.988500171577252 ± 0.007791203181151346
Unmitigated value: 0.9368285714285716 ± 0.001562451883089579
Observable 1: ObservablesArray({'IIIZZ': 1.0, 'ZIIXI': 0.5}, shape=())
QESEM mitigated value: 1.02555188098689 ± 0.016726524388086233
Unmitigated value: 0.9537142857142858 ± 0.006657345655544263

準確率的エラーチューニング(QET)の例​

準確率的エラーチューニング(QET)は、選択したノイズスケールファクターでの期待値を要求します。これはカスタムノイズスケーリング研究とゼロノイズ外挿ワークフローに有用です。スケール1.0は物理ノイズレベルであり、0.0から1.0の間の値はノイズを部分的に低減し、1.0を超える値はノイズを増幅します。

Qiskit FunctionでQETを使用するには、辞書をPUBの精度として渡します。この辞書は、要求された各ノイズスケールを目標精度にマッピングします。返されるスケールファクターの結果はnoise_scaling.results_with_REMに格納され、読み出しミティゲーションを含みます。したがって、スケール1.0のポイントは、1.0が読み出しミティゲーションを含むのに対しunmitigatedは含まないため、非ミティゲート値と同一ではありません。

スケールが要求されると、QESEMは追加のQPU使用なしで1.0周辺の補完的なスケールも返します。例えば、0.5を要求すると1.5も返されることがあり、1.3を要求すると0.7も返されることがあります。補完的なスケールでの精度は保証されません。

noise_scale_precision = {0.5: 0.15, 1.3: 0.2}

qet_job = qesem_function.run(
pubs=[
(
circ,
[avg_magnetization, other_observable],
None,
noise_scale_precision,
)
],
backend_name=backend_name,
options={"max_execution_time": 300},
)
print(qet_job.job_id)
print(qet_job.status())
8195fa58-f037-4651-8715-36ce1cdc5521
DONE
qet_result = qet_job.result()
print("QET noise-scaling results:")

for pub_idx, pub_result in enumerate(qet_result):
print(f"\nPUB {pub_idx}:")
noisy_results = pub_result.metadata["noisy_results"]
print(f" Unmitigated expectation values: {noisy_results.evs}")
print(f" Unmitigated error bars: {noisy_results.stds}")
print(" Results for each observable:")
for circ_idx, circ_results in enumerate(pub_result.metadata["results"]):
print(f" Circuit {circ_idx}:")
for obs_idx, (obs_array, result_dict) in enumerate(circ_results):
print(f" Observable {obs_idx}: {obs_array}")
noise_scaling = result_dict["noise_scaling"]
print(
f" Scaling method: {noise_scaling['scaling_method']}"
)
print(" Results with Readout mitigation (REM):")
for rem_result in sorted(
(
item
for item in noise_scaling["results_with_REM"]
if item["scale"] != 0.0
),
key=lambda item: item["scale"],
):
print(
f" Scale factor {rem_result['scale']}: {rem_result['value']} ± {rem_result['error_bar']}"
)
QET noise-scaling results:

PUB 0:
Unmitigated expectation values: [0.97822857 0.96171429]
Unmitigated error bars: [0.00123812 0.00672958]
Results for each observable:
Circuit 0:
Observable 0: ObservablesArray({'IIIIZ': 0.2, 'IIIZI': 0.2, 'IIZII': 0.2, 'IZIII': 0.2, 'ZIIII': 0.2}, shape=())
Scaling method: QESEM
Results with Readout mitigation (REM):
Scale factor 0.5: 0.9938730340199383 ± 0.0032116907357568275
Scale factor 0.7: 0.9963976191853445 ± 0.00036300258869586616
Scale factor 1.0: 0.9898115079506586 ± 0.0012525947426560995
Scale factor 1.3: 0.9864667065580341 ± 0.002633221613518526
Scale factor 1.5: 0.9838755527197551 ± 0.002948417797996015
Observable 1: ObservablesArray({'IIIZZ': 1.0, 'ZIIXI': 0.5}, shape=())
Scaling method: QESEM
Results with Readout mitigation (REM):
Scale factor 0.5: 1.0006538544450332 ± 0.002121742014777343
Scale factor 0.7: 1.0004159801523036 ± 0.0021671375357823794
Scale factor 1.0: 0.9898058846339917 ± 0.00690183710903159
Scale factor 1.3: 0.9948946719997267 ± 0.002146532859610311
Scale factor 1.5: 0.9927220368192772 ± 0.0020875057190323882

エラーメッセージの取得​

ワークロードのステータスがERRORの場合、以下のようにエラーメッセージを取得するにはjob.result()を使用してください:

# Get the result and truncate for readability
result = sample_job.result()
result_str = str(result)
max_length = 500 # Adjust this value as necessary

if len(result_str) > max_length:
truncated = (
result_str[:max_length]
+ f"... (truncated {len(result_str) - max_length} characters)"
)
else:
truncated = result_str

print(truncated)
PrimitiveResult([PubResult(data=DataBin(evs=np.ndarray(<shape=(2,), dtype=float64>), stds=np.ndarray(<shape=(2,), dtype=float64>), shape=(2,)), metadata={'gate_fidelities': {'CZ': 0.9979444718552628, 'ID1Q': 0.9991994239814883}, 'total_shots': 498600, 'mitigation_shots': 223400, 'transpiled_circs': [{'circuit': 'OPENQASM 3.0;\ninclude "stdgates.inc";\nbit[76] c0;\nqubit[76] q0;\nrx(0) q0[54];\nrx(0) q0[59];\nrx(0) q0[75];\nrz(pi/2) q0[54];\nrz(pi/2) q0[59];\nrz(pi/2) q0[75];\nrx(pi/2) q0[54];\nr... (truncated 3771 characters)

サポートを受ける​

Qedmaのサポートチームがお手伝いします。QESEM Qiskit Functionの使用中に問題が発生した場合や、ご質問がある場合は、遠慮なくお問い合わせください。知識豊富で親切なサポートスタッフが、技術的な懸念やご質問にお答えする準備ができています。

サポートについては、support@qedma.comまでメールでお問い合わせください。迅速かつ正確な対応ができるよう、お困りの問題についてできるだけ詳しい情報をご提供ください。また、メールまたは電話で担当のQedma POC担当者にご連絡いただくこともできます。

より効率的にサポートするため、お問い合わせの際には以下の情報をご提供ください:

  • 問題の詳細な説明

  • ジョブID

  • 関連するエラーメッセージやコード

私たちは、Qiskit Functionでの最善のご体験をお届けするため、迅速かつ効果的なサポートの提供にコミットしています。

製品の改善に常に取り組んでおり、皆様のご提案を歓迎しています。サービスの強化方法や追加を希望される機能についてアイデアがある場合は、support@qedma.comまでご意見をお送りください。

次のステップ​