{
  "cells": [
    {
      "cell_type": "markdown",
      "id": "44ef87b3",
      "metadata": {},
      "source": [
        "---\n",
        "title: \"動的回路によるキック付きアイジングハミルトニアンのシミュレーション\"\n",
        "description: \"六角キック付きアイジングモデルシミュレーションを用いたユーティリティ規模動的回路の実証チュートリアル\"\n",
        "---\n",
        "\n",
        "{/* cspell:ignore hcords ycords xcords fontsize ncol Krsulich Lishman */}\n",
        "\n",
        "<span id=\"simulation-of-kicked-ising-hamiltonian-with-dynamic-circuits\" />\n",
        "\n",
        "# 動的回路によるキック付きアイジングハミルトニアンのシミュレーション\n",
        "\n"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "2ae52bd4",
      "metadata": {},
      "source": [
        "*使用時間推定値: Heron r3 プロセッサ上で 7.5 分。 （注：これはあくまで概算です。） 実行時間は異なる場合があります。*\n",
        "\n"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "c76f2627",
      "metadata": {},
      "source": [
        "動的回路とは、古典的なフィードフォワードを備えた回路である。言い換えれば、回路の中間測定に続いて、その古典的出力に基づいて量子操作を決定する古典論理演算が行われる回路である。 このチュートリアルでは、六角格子上のスピン系におけるキックド・アイジングモデルをシミュレートし、動的回路を用いてハードウェアの物理的接続性を超えた相互作用を実現する。\n",
        "\n",
        "アイジングモデルは物理学の様々な分野で広く研究されてきた。 格子点間でアイジング相互作用を受けるスピンと、各点における局所磁場からのキックをモデル化する。 本チュートリアルで扱うスピンのトロッター化時間発展は、 [\\[1\\]](#references) より引用した以下のユニタリ演算子によって与えられる：\n",
        "\n",
        "$$\n",
        "U(\\theta)=\\left(\\prod_{\\langle j, k\\rangle} \\exp \\left(i \\frac{\\pi}{8} Z_j Z_k\\right)\\right)\\left(\\prod_j \\exp \\left(-i \\frac{\\theta}{2} X_j\\right)\\right)\n",
        "$$\n",
        "\n",
        "スピンダイナミクスを探るため、我々は各サイトにおけるスピンの平均磁化をトロッターステップの関数として研究する。 したがって、我々は以下の観測量を構築する：\n",
        "\n",
        "$$\n",
        "\\langle O\\rangle =  \\frac{1}{N} \\sum_i \\langle Z_i \\rangle\n",
        "$$\n",
        "\n",
        "格子サイト間のZZ相互作用を実現するため、動的回路機能を用いた解法を提案する。これにより、SWAPゲートを用いた標準的なルーティング手法と比較して、2量子ビット深度が大幅に短縮される。 一方、動的回路における古典的なフィードフォワード演算は、量子ゲートよりも実行時間が長い傾向にある。したがって、動的回路には限界とトレードオフが存在する。 また、 [ストレッチ](/docs/guides/stretch)持続時間を利用して、古典的なフィードフォワード操作中にアイドル状態の量子ビットに対して動的デカップリングシーケンスを追加する方法も提示する。\n",
        "\n"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "a6c0af3b",
      "metadata": {},
      "source": [
        "<span id=\"requirements\" />\n",
        "\n",
        "## 要件\n",
        "\n",
        "このチュートリアルを始める前に、以下のものがインストールされていることを確認してください：\n",
        "\n",
        "* Qiskit SDK v2.0 または[、可視化](/docs/api/qiskit/visualization)サポート付きの後続バージョン\n",
        "* Qiskit Runtime v0.37 またはそれ以降のバージョンで可視化サポート付き (`pip install 'qiskit-ibm-runtime[visualization]'`)\n",
        "* Rustworkx グラフライブラリ (`pip install rustworkx`)\n",
        "* Qiskit Aer (`pip install qiskit-aer`)\n",
        "\n"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "03860584",
      "metadata": {},
      "source": [
        "<span id=\"set-up\" />\n",
        "\n",
        "## のセットアップ\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 1,
      "id": "88a21408",
      "metadata": {},
      "outputs": [],
      "source": [
        "import numpy as np\n",
        "from typing import List\n",
        "import rustworkx as rx\n",
        "import matplotlib.pyplot as plt\n",
        "from rustworkx.visualization import mpl_draw\n",
        "from qiskit.circuit import (\n",
        "    Parameter,\n",
        "    QuantumCircuit,\n",
        "    QuantumRegister,\n",
        "    ClassicalRegister,\n",
        ")\n",
        "from qiskit.transpiler import CouplingMap\n",
        "from qiskit.quantum_info import SparsePauliOp\n",
        "from qiskit.circuit.classical import expr\n",
        "from qiskit.transpiler.preset_passmanagers import (\n",
        "    generate_preset_pass_manager,\n",
        ")\n",
        "from qiskit.transpiler import PassManager\n",
        "from qiskit.circuit.library import RZGate, XGate\n",
        "from qiskit.transpiler.passes import (\n",
        "    ALAPScheduleAnalysis,\n",
        "    PadDynamicalDecoupling,\n",
        ")\n",
        "\n",
        "from qiskit.transpiler.basepasses import TransformationPass\n",
        "from qiskit.circuit.measure import Measure\n",
        "from qiskit.transpiler.passes.utils.remove_final_measurements import (\n",
        "    calc_final_ops,\n",
        ")\n",
        "from qiskit.circuit import Instruction\n",
        "\n",
        "from qiskit.visualization import plot_circuit_layout\n",
        "from qiskit.circuit.tools import pi_check\n",
        "\n",
        "from qiskit_aer import AerSimulator\n",
        "from qiskit_aer.primitives import SamplerV2 as Aer_Sampler\n",
        "\n",
        "from qiskit_ibm_runtime import (\n",
        "    QiskitRuntimeService,\n",
        "    Batch,\n",
        "    SamplerV2 as Sampler,\n",
        ")\n",
        "from qiskit.providers.exceptions import QiskitBackendNotFoundError\n",
        "from qiskit_ibm_runtime.visualization import (\n",
        "    draw_circuit_schedule_timing,\n",
        ")"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "df65631b",
      "metadata": {},
      "source": [
        "<span id=\"step-1-map-classical-inputs-to-a-quantum-circuit\" />\n",
        "\n",
        "## ステップ1：古典的な入力を量子回路にマッピングする\n",
        "\n"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "188f83ae",
      "metadata": {},
      "source": [
        "シミュレーション対象の格子を定義することから始めます。 我々はハニカム（六角形とも呼ばれる）格子を用いて研究を行うことを選択した。これは次数3の頂点を持つ平面グラフである。 ここでは、格子のサイズと、トロッター化されたダイナミクスにおいて関心のある関連回路パラメータを指定する。 我々は、局所磁場に対して3つの異なる $\\theta$ 値のもとで、アイジングモデルにおけるトロッター化時間発展をシミュレートする。\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 2,
      "id": "e8bc54ef",
      "metadata": {},
      "outputs": [],
      "source": [
        "hex_rows = 3  # specify lattice size\n",
        "hex_cols = 5\n",
        "depths = range(9)  # specify Trotter steps\n",
        "zz_angle = np.pi / 8  # parameter for ZZ interaction\n",
        "max_angle = np.pi / 2  # max theta angle\n",
        "points = 3  # number of theta parameters\n",
        "\n",
        "θ = Parameter(\"θ\")\n",
        "params = np.linspace(0, max_angle, points)"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 3,
      "id": "0b12f364",
      "metadata": {},
      "outputs": [],
      "source": [
        "def make_hex_lattice(hex_rows=1, hex_cols=1):\n",
        "    \"\"\"Define hexagon lattice.\"\"\"\n",
        "    hex_cmap = CouplingMap.from_hexagonal_lattice(\n",
        "        hex_rows, hex_cols, bidirectional=False\n",
        "    )\n",
        "    data = list(hex_cmap.physical_qubits)\n",
        "    graph = hex_cmap.graph.to_undirected(multigraph=False)\n",
        "    edge_colors = rx.graph_misra_gries_edge_color(graph)\n",
        "    layer_edges = {color: [] for color in edge_colors.values()}\n",
        "    for edge_index, color in edge_colors.items():\n",
        "        layer_edges[color].append(graph.edge_list()[edge_index])\n",
        "    return data, layer_edges, hex_cmap, graph"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "b2286ebb",
      "metadata": {},
      "source": [
        "まずは小さなテスト例から始めましょう：\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 4,
      "id": "c011bc1a",
      "metadata": {},
      "outputs": [
        {
          "data": {
            "text/plain": [
              "<Image src=\"/docs/images/tutorials/dc-hex-ising/extracted-outputs/c011bc1a-0.avif\" alt=\"Output of the previous code cell\" />"
            ]
          },
          "metadata": {},
          "output_type": "display_data"
        }
      ],
      "source": [
        "hex_rows_test = 1\n",
        "hex_cols_test = 2\n",
        "\n",
        "data_test, layer_edges_test, hex_cmap_test, graph_test = make_hex_lattice(\n",
        "    hex_rows=hex_rows_test, hex_cols=hex_cols_test\n",
        ")\n",
        "\n",
        "# display a small example for illustration\n",
        "node_colors_test = [\"lightblue\"] * len(graph_test.node_indices())\n",
        "pos = rx.graph_spring_layout(\n",
        "    graph_test,\n",
        "    k=5 / np.sqrt(len(graph_test.nodes())),\n",
        "    repulsive_exponent=1,\n",
        "    num_iter=150,\n",
        ")\n",
        "mpl_draw(graph_test, node_color=node_colors_test, pos=pos)"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "8e5f862a",
      "metadata": {},
      "source": [
        "この小さな例を用いて説明とシミュレーションを行います。 以下では、ワークフローを大規模なサイズに拡張できることを示すため、大規模な例も構築します。\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 5,
      "id": "ba481bd4",
      "metadata": {},
      "outputs": [
        {
          "name": "stdout",
          "output_type": "stream",
          "text": [
            "num_qubits = 46\n"
          ]
        },
        {
          "data": {
            "text/plain": [
              "<Image src=\"/docs/images/tutorials/dc-hex-ising/extracted-outputs/ba481bd4-1.avif\" alt=\"Output of the previous code cell\" />"
            ]
          },
          "metadata": {},
          "output_type": "display_data"
        }
      ],
      "source": [
        "data, layer_edges, hex_cmap, graph = make_hex_lattice(\n",
        "    hex_rows=hex_rows, hex_cols=hex_cols\n",
        ")\n",
        "num_qubits = len(data)\n",
        "print(f\"num_qubits = {num_qubits}\")\n",
        "\n",
        "# display the honeycomb lattice to simulate\n",
        "node_colors = [\"lightblue\"] * len(graph.node_indices())\n",
        "pos = rx.graph_spring_layout(\n",
        "    graph,\n",
        "    k=5 / np.sqrt(num_qubits),\n",
        "    repulsive_exponent=1,\n",
        "    num_iter=150,\n",
        ")\n",
        "mpl_draw(graph, node_color=node_colors, pos=pos)\n",
        "plt.show()"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "6eb03e83",
      "metadata": {},
      "source": [
        "<span id=\"build-unitary-circuits\" />\n",
        "\n",
        "### 単一回路を構築する\n",
        "\n"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "f4b421fa",
      "metadata": {},
      "source": [
        "問題の規模とパラメータが指定されたので、 $U(\\theta)$ のトロッター化時間発展をシミュレートするパラメータ化回路を構築する準備が整った。この `depth` 回路は引数によって指定される異なるトロッターステップを用いる。 構築する回路は、 $\\theta$ ゲートと `Rzz` ゲートが交互に積層 `Rx`された層構造を持つ。 ゲート `Rzz` は結合したスピン間のZZ相互作用を実現し、これらは引数 `layer_edges` で指定される各格子点間に配置される。\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 6,
      "id": "9e2dc428",
      "metadata": {},
      "outputs": [],
      "source": [
        "def gen_hex_unitary(\n",
        "    num_qubits=6,\n",
        "    zz_angle=np.pi / 8,\n",
        "    layer_edges=[\n",
        "        [(0, 1), (2, 3), (4, 5)],\n",
        "        [(1, 2), (3, 4), (5, 0)],\n",
        "    ],\n",
        "    θ=Parameter(\"θ\"),\n",
        "    depth=1,\n",
        "    measure=False,\n",
        "    final_rot=True,\n",
        "):\n",
        "    \"\"\"Build unitary circuit.\"\"\"\n",
        "    circuit = QuantumCircuit(num_qubits)\n",
        "    # Build trotter layers\n",
        "    for _ in range(depth):\n",
        "        for i in range(num_qubits):\n",
        "            circuit.rx(θ, i)\n",
        "        circuit.barrier()\n",
        "        for coloring in layer_edges.keys():\n",
        "            for e in layer_edges[coloring]:\n",
        "                circuit.rzz(zz_angle, e[0], e[1])\n",
        "        circuit.barrier()\n",
        "    # Optional final rotation, set True to be consistent with Ref. [1]\n",
        "    if final_rot:\n",
        "        for i in range(num_qubits):\n",
        "            circuit.rx(θ, i)\n",
        "    if measure:\n",
        "        circuit.measure_all()\n",
        "\n",
        "    return circuit"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "24235b4a",
      "metadata": {},
      "source": [
        "小さなテスト回路を可視化する：\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 7,
      "id": "268e6999",
      "metadata": {},
      "outputs": [
        {
          "data": {
            "text/plain": [
              "<Image src=\"/docs/images/tutorials/dc-hex-ising/extracted-outputs/268e6999-0.avif\" alt=\"Output of the previous code cell\" />"
            ]
          },
          "execution_count": 7,
          "metadata": {},
          "output_type": "execute_result"
        }
      ],
      "source": [
        "circ_unitary_test = gen_hex_unitary(\n",
        "    num_qubits=len(data_test),\n",
        "    layer_edges=layer_edges_test,\n",
        "    θ=Parameter(\"θ\"),\n",
        "    depth=1,\n",
        "    measure=True,\n",
        ")\n",
        "circ_unitary_test.draw(output=\"mpl\", fold=-1)"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "0a8abb0d",
      "metadata": {},
      "source": [
        "同様に、大規模な例題のユニタリー回路を異なるトロッター化ステップで構築し、期待値を推定するための観測量を構築する。\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 8,
      "id": "6c9e388a",
      "metadata": {},
      "outputs": [],
      "source": [
        "circuits_unitary = []\n",
        "for depth in depths:\n",
        "    circ = gen_hex_unitary(\n",
        "        num_qubits=num_qubits,\n",
        "        layer_edges=layer_edges,\n",
        "        θ=Parameter(\"θ\"),\n",
        "        depth=depth,\n",
        "        measure=True,\n",
        "    )\n",
        "    circuits_unitary.append(circ)"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 9,
      "id": "695e2bad",
      "metadata": {},
      "outputs": [],
      "source": [
        "observables_unitary = SparsePauliOp.from_sparse_list(\n",
        "    [(\"Z\", [i], 1 / num_qubits) for i in range(num_qubits)],\n",
        "    num_qubits=num_qubits,\n",
        ")"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "84d2cd91",
      "metadata": {},
      "source": [
        "<span id=\"build-dynamic-circuit-implementation\" />\n",
        "\n",
        "### 動的回路実装を構築する\n",
        "\n",
        "このセクションでは、同じトロッター化時間発展をシミュレートするための主要な動的回路実装を示す。 注意：シミュレートしたいハニカム格子は、ハードウェア量子ビットの重格子とは一致しません。 回路をハードウェアにマッピングする単純な方法の一つは、相互作用する量子ビットを隣り合わせにする一連のSWAP操作を導入し、ZZ相互作用を実現することである。 ここでは、動的回路を用いた代替アプローチを解決策として提示する。これは、Qiskit内の回路内で量子計算とリアルタイムの古典計算を組み合わせることで、最近接相互作用を超えた相互作用を実現できることを示している。\n",
        "\n",
        "動的回路実装において、ZZ相互作用は補助量子ビット、回路途中測定、およびフィードフォワードを用いて効果的に実装される。 これを理解するには、ZZ回転が状態のパリティに基づいて位相因子 $e^{i\\theta}$ を適用することに留意されたい。 2量子ビットの場合、計算基底状態は $|00\\rangle$、 $|01\\rangle$、 $|10\\rangle$、および $|11\\rangle$ である。ZZ回転ゲートは、状態 $|01\\rangle$ および $|10\\rangle$ （状態内の1の数が奇数である状態）に位相因子を適用し、偶数パリティの状態は変化させない。 以下では、動的回路を用いて2つの量子ビット間でZZ相互作用を効果的に実装する方法について説明する。\n",
        "\n",
        "1. アンシラ量子ビットにパリティを計算する：2つの量子ビットに直接ZZ演算を適用する代わりに、3つ目の量子ビットであるアンシラ量子ビットを導入し、2つのデータ量子ビットのパリティ情報を格納する。 各データ量子ビットから補助量子ビットへCXゲートを用いて、データ量子ビットと補助量子ビットを絡み合わせる。\n",
        "\n",
        "2. 補助量子ビットに単一量子ビットZ回転を適用する：これは補助量子ビットが2つのデータ量子ビットのパリティ情報を保持しているためであり、これによりデータ量子ビットに対してZZ回転が効果的に実現される。\n",
        "\n",
        "3. 補助量子ビットをX基底で測定する：これが補助量子ビットの状態を収縮させる重要なステップであり、測定結果は起こったことを示す：\n",
        "\n",
        "   * 測定0：結果が0となる場合、我々は実際にデータ量子ビットに対して $ZZ(\\theta)$ 回転を正しく適用したことになる。\n",
        "\n",
        "   * 対策1：結果1が観測された場合、代わりに $ZZ(\\theta + \\pi)$ を適用した。\n",
        "\n",
        "4. 補正ゲートを適用するタイミング（測定時）：1. 測定値が1の場合、データ量子ビットにZゲートを適用し、余分な $\\pi$ 位相を「修正」する。\n",
        "\n",
        "結果として得られた回路は以下の通りです：\n",
        "\n",
        "![動的実装](https://quantum.cloud.ibm.com/docs/images/tutorials/dc-hex-ising/circuit-1.avif)\n",
        "\n"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "9872fed2",
      "metadata": {},
      "source": [
        "この手法を用いてハニカム格子をシミュレートすると、結果として得られる回路はヘビーヘックス格子を持つハードウェアに完全に埋め込まれる：全てのデータ量子ビットは格子の degree-3 サイト上に配置され、これが六角格子を形成する。 各データ量子ビットのペアは、 degree-2 サイト上に存在する補助量子ビットを共有する。 以下に、動的回路実装のための量子ビット格子を構築し、補助量子ビット（濃い紫色の円で示される）を導入する。\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 10,
      "id": "c0e7afd2",
      "metadata": {},
      "outputs": [],
      "source": [
        "def make_lattice(hex_rows=1, hex_cols=1):\n",
        "    \"\"\"Define heavy-hex lattice and corresponding lists of data and ancilla nodes.\"\"\"\n",
        "    hex_cmap = CouplingMap.from_hexagonal_lattice(\n",
        "        hex_rows, hex_cols, bidirectional=False\n",
        "    )\n",
        "    data = list(hex_cmap.physical_qubits)\n",
        "\n",
        "    heavyhex_cmap = CouplingMap()\n",
        "    for d in data:\n",
        "        heavyhex_cmap.add_physical_qubit(d)\n",
        "\n",
        "    # make coupling map\n",
        "    a = len(data)\n",
        "    for edge in hex_cmap.get_edges():\n",
        "        heavyhex_cmap.add_physical_qubit(a)\n",
        "        heavyhex_cmap.add_edge(edge[0], a)\n",
        "        heavyhex_cmap.add_edge(edge[1], a)\n",
        "        a += 1\n",
        "    ancilla = list(range(len(data), a))\n",
        "    qubits = data + ancilla\n",
        "\n",
        "    # color edges\n",
        "    graph = heavyhex_cmap.graph.to_undirected(multigraph=False)\n",
        "    edge_colors = rx.graph_misra_gries_edge_color(graph)\n",
        "    layer_edges = {color: [] for color in edge_colors.values()}\n",
        "    for edge_index, color in edge_colors.items():\n",
        "        layer_edges[color].append(graph.edge_list()[edge_index])\n",
        "\n",
        "    # construct observable\n",
        "    obs_hex = SparsePauliOp.from_sparse_list(\n",
        "        [(\"Z\", [i], 1 / len(data)) for i in data],\n",
        "        num_qubits=len(qubits),\n",
        "    )\n",
        "\n",
        "    return (data, qubits, ancilla, layer_edges, heavyhex_cmap, graph, obs_hex)"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "5c39eeab",
      "metadata": {},
      "source": [
        "データ量子ビットと補助量子ビットの重六角格子を小規模で可視化する：\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 11,
      "id": "2d7224ef",
      "metadata": {},
      "outputs": [
        {
          "name": "stdout",
          "output_type": "stream",
          "text": [
            "number of data qubits = 46\n",
            "number of ancilla qubits = 60\n"
          ]
        },
        {
          "data": {
            "text/plain": [
              "<Image src=\"/docs/images/tutorials/dc-hex-ising/extracted-outputs/2d7224ef-1.avif\" alt=\"Output of the previous code cell\" />"
            ]
          },
          "metadata": {},
          "output_type": "display_data"
        }
      ],
      "source": [
        "(data, qubits, ancilla, layer_edges, heavyhex_cmap, graph, obs_hex) = (\n",
        "    make_lattice(hex_rows=hex_rows, hex_cols=hex_cols)\n",
        ")\n",
        "\n",
        "print(f\"number of data qubits = {len(data)}\")\n",
        "print(f\"number of ancilla qubits = {len(ancilla)}\")\n",
        "\n",
        "node_colors = []\n",
        "for node in graph.node_indices():\n",
        "    if node in ancilla:\n",
        "        node_colors.append(\"purple\")\n",
        "    else:\n",
        "        node_colors.append(\"lightblue\")\n",
        "\n",
        "pos = rx.graph_spring_layout(\n",
        "    graph,\n",
        "    k=1 / np.sqrt(len(qubits)),\n",
        "    repulsive_exponent=2,\n",
        "    num_iter=200,\n",
        ")\n",
        "\n",
        "# Visualize the graph, blue circles are data qubits and purple circles are ancillas\n",
        "mpl_draw(graph, node_color=node_colors, pos=pos)\n",
        "plt.show()"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "bf9177d2",
      "metadata": {},
      "source": [
        "以下に、トロッター化時間発展のための動的回路を構築する。 ゲート `RZZ` は、上記の手順を用いて動的回路実装に置き換えられる。\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 12,
      "id": "4c98664f",
      "metadata": {},
      "outputs": [],
      "source": [
        "def gen_hex_dynamic(\n",
        "    depth=1,\n",
        "    zz_angle=np.pi / 8,\n",
        "    θ=Parameter(\"θ\"),\n",
        "    hex_rows=1,\n",
        "    hex_cols=1,\n",
        "    measure=False,\n",
        "    add_dd=True,\n",
        "):\n",
        "    \"\"\"Build dynamic circuits.\"\"\"\n",
        "    (data, qubits, ancilla, layer_edges, heavyhex_cmap, graph, obs_hex) = (\n",
        "        make_lattice(hex_rows=hex_rows, hex_cols=hex_cols)\n",
        "    )\n",
        "    # Initialize circuit\n",
        "    qr = QuantumRegister(len(qubits), \"qr\")\n",
        "    cr = ClassicalRegister(len(ancilla), \"cr\")\n",
        "    circuit = QuantumCircuit(qr, cr)\n",
        "\n",
        "    for k in range(depth):\n",
        "        # Single-qubit Rx layer\n",
        "        for d in data:\n",
        "            circuit.rx(θ, d)\n",
        "        circuit.barrier()\n",
        "\n",
        "        # CX gates from data qubits to ancilla qubits\n",
        "        for same_color_edges in layer_edges.values():\n",
        "            for e in same_color_edges:\n",
        "                circuit.cx(e[0], e[1])\n",
        "        circuit.barrier()\n",
        "\n",
        "        # Apply Rz rotation on ancilla qubits and rotate into X basis\n",
        "        for a in ancilla:\n",
        "            circuit.rz(zz_angle, a)\n",
        "            circuit.h(a)\n",
        "        # Add barrier to align terminal measurement\n",
        "        circuit.barrier()\n",
        "\n",
        "        # Measure ancilla qubits\n",
        "        for i, a in enumerate(ancilla):\n",
        "            circuit.measure(a, i)\n",
        "        d2ros = {}\n",
        "        a2ro = {}\n",
        "        # Retrieve ancilla measurement outcomes\n",
        "        for a in ancilla:\n",
        "            a2ro[a] = cr[ancilla.index(a)]\n",
        "\n",
        "        # For each data qubit, retrieve measurement outcomes of neighboring\n",
        "        # ancilla qubits\n",
        "        for d in data:\n",
        "            ros = [a2ro[a] for a in heavyhex_cmap.neighbors(d)]\n",
        "            d2ros[d] = ros\n",
        "\n",
        "        # Build classical feedforward operations (optionally add DD on idling\n",
        "        # data qubits)\n",
        "        for d in data:\n",
        "            if add_dd:\n",
        "                circuit = add_stretch_dd(circuit, d, f\"data_{d}_depth_{k}\")\n",
        "\n",
        "            # # XOR the neighboring readouts of the data qubit;\n",
        "            # if True, apply Z to it\n",
        "            ros = d2ros[d]\n",
        "            parity = ros[0]\n",
        "            for ro in ros[1:]:\n",
        "                parity = expr.bit_xor(parity, ro)\n",
        "            with circuit.if_test(expr.equal(parity, True)):\n",
        "                circuit.z(d)\n",
        "\n",
        "        # Reset the ancilla if its readout is 1\n",
        "        for a in ancilla:\n",
        "            with circuit.if_test(expr.equal(a2ro[a], True)):\n",
        "                circuit.x(a)\n",
        "        circuit.barrier()\n",
        "\n",
        "    # Final single-qubit Rx layer to match the unitary circuits\n",
        "    for d in data:\n",
        "        circuit.rx(θ, d)\n",
        "\n",
        "    if measure:\n",
        "        circuit.measure_all()\n",
        "    return circuit, obs_hex\n",
        "\n",
        "\n",
        "def add_stretch_dd(qc, q, name):\n",
        "    \"\"\"Add XpXm DD sequence.\"\"\"\n",
        "    s = qc.add_stretch(name)\n",
        "    qc.delay(s, q)\n",
        "    qc.x(q)\n",
        "    qc.delay(s, q)\n",
        "    qc.delay(s, q)\n",
        "    qc.rz(np.pi, q)\n",
        "    qc.x(q)\n",
        "    qc.rz(-np.pi, q)\n",
        "    qc.delay(s, q)\n",
        "    return qc"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "c8b3b632",
      "metadata": {},
      "source": [
        "<span id=\"dynamical-decoupling-dd-and-support-for-stretch-duration\" />\n",
        "\n",
        "#### 動的デカップリング（DD）と `stretch` 持続時間のサポート\n",
        "\n"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "1f08bda1",
      "metadata": {},
      "source": [
        "動的回路実装を用いてZZ相互作用を実現する際の注意点として、回路中間測定と古典的フィードフォワード操作は、量子ゲートよりも実行に通常より長い時間を要する点が挙げられる。 量子ビットのデコヒーレンスを抑制するため、古典演算が行われる待機時間中に、補助量子ビットに対する測定演算の後、データ量子ビットに対する条件付きZ演算の前、すなわち `if_test` \\`\\`文の前に[動的デカップリング](/docs/guides/error-mitigation-and-suppression-techniques#dynamical-decoupling) （DD）シーケンスを追加した。\n",
        "\n",
        "DDシーケンスは、この関数によって追加されます `add_stretch_dd()`。この関数は、各DDゲートの間の時間間隔を決定するために、各ゲートの[持続 `stretch` 時間](/docs/guides/stretch)を使用します。 「持続 `stretch` 時間」とは、遅延時間が量子ビットのアイドル時間を埋めるまで長くなるように、その `delay` 操作に対して伸縮可能な時間間隔を指定する方法である。 で指定された持続時間変数は、コンパイル時に、特定の制約を満たす所望の持続時間へと解決 `stretch` されます。 これは、優れた誤差抑制性能を実現するためにDDシーケンスのタイミングが極めて重要となる場合に、非常に有用です。 この型 `stretch` に関する詳細については、 [OpenQASM](https://openqasm.com/language/delays.html#duration-and-stretch-types) のドキュメントを参照してください。 現在、この型の `stretch` サポートは実験的な段階にあります。 使用上の制約に関する詳細については、ドキュメント `stretch` の「 [制限事項」のセクション](/docs/guides/stretch#qiskit-runtime-limitations)をご参照ください。\n",
        "\n",
        "上記で定義した関数を用いて、DDの有無に応じたトロッター化時間発展回路と、それに対応する観測量を構築する。\n",
        "\n"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "997419c8",
      "metadata": {},
      "source": [
        "まず、小さな例題の動的回路を可視化することから始めます：\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 13,
      "id": "b6e2e76c",
      "metadata": {},
      "outputs": [
        {
          "data": {
            "text/plain": [
              "<Image src=\"/docs/images/tutorials/dc-hex-ising/extracted-outputs/b6e2e76c-0.avif\" alt=\"Output of the previous code cell\" />"
            ]
          },
          "metadata": {},
          "output_type": "display_data"
        }
      ],
      "source": [
        "hex_rows_test = 1\n",
        "hex_cols_test = 1\n",
        "\n",
        "(\n",
        "    data_test,\n",
        "    qubits_test,\n",
        "    ancilla_test,\n",
        "    layer_edges_test,\n",
        "    heavyhex_cmap_test,\n",
        "    graph_test,\n",
        "    obs_hex_test,\n",
        ") = make_lattice(hex_rows=hex_rows_test, hex_cols=hex_cols_test)\n",
        "\n",
        "node_colors = []\n",
        "for node in graph_test.node_indices():\n",
        "    if node in ancilla_test:\n",
        "        node_colors.append(\"purple\")\n",
        "    else:\n",
        "        node_colors.append(\"lightblue\")\n",
        "pos = rx.graph_spring_layout(\n",
        "    graph_test,\n",
        "    k=5 / np.sqrt(len(qubits_test)),\n",
        "    repulsive_exponent=2,\n",
        "    num_iter=150,\n",
        ")\n",
        "\n",
        "# display a small example for illustration\n",
        "node_colors_test = [\"lightblue\"] * len(graph_test.node_indices())\n",
        "mpl_draw(graph_test, node_color=node_colors, pos=pos)"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 14,
      "id": "735e590a",
      "metadata": {},
      "outputs": [
        {
          "data": {
            "text/plain": [
              "<Image src=\"/docs/images/tutorials/dc-hex-ising/extracted-outputs/735e590a-0.avif\" alt=\"Output of the previous code cell\" />"
            ]
          },
          "execution_count": 14,
          "metadata": {},
          "output_type": "execute_result"
        }
      ],
      "source": [
        "circuit_dynamic_test, obs_dynamic_test = gen_hex_dynamic(\n",
        "    depth=1,\n",
        "    θ=Parameter(\"θ\"),\n",
        "    hex_rows=hex_rows_test,\n",
        "    hex_cols=hex_cols_test,\n",
        "    measure=False,\n",
        "    add_dd=False,\n",
        ")\n",
        "circuit_dynamic_test.draw(\"mpl\", fold=-1)"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 15,
      "id": "5de9381a",
      "metadata": {},
      "outputs": [
        {
          "data": {
            "text/plain": [
              "<Image src=\"/docs/images/tutorials/dc-hex-ising/extracted-outputs/5de9381a-0.avif\" alt=\"Output of the previous code cell\" />"
            ]
          },
          "execution_count": 15,
          "metadata": {},
          "output_type": "execute_result"
        }
      ],
      "source": [
        "circuit_dynamic_dd_test, _ = gen_hex_dynamic(\n",
        "    depth=1,\n",
        "    θ=Parameter(\"θ\"),\n",
        "    hex_rows=hex_rows_test,\n",
        "    hex_cols=hex_cols_test,\n",
        "    measure=False,\n",
        "    add_dd=True,\n",
        ")\n",
        "circuit_dynamic_dd_test.draw(\"mpl\", fold=-1)"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "956dd43e",
      "metadata": {},
      "source": [
        "同様に、大規模な例に対する動的回路を構築する：\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 16,
      "id": "bd7b2be0",
      "metadata": {},
      "outputs": [],
      "source": [
        "circuits_dynamic = []\n",
        "circuits_dynamic_dd = []\n",
        "observables_dynamic = []\n",
        "for depth in depths:\n",
        "    circuit, obs = gen_hex_dynamic(\n",
        "        depth=depth,\n",
        "        θ=Parameter(\"θ\"),\n",
        "        hex_rows=hex_rows,\n",
        "        hex_cols=hex_cols,\n",
        "        measure=True,\n",
        "        add_dd=False,\n",
        "    )\n",
        "    circuits_dynamic.append(circuit)\n",
        "\n",
        "    circuit_dd, _ = gen_hex_dynamic(\n",
        "        depth=depth,\n",
        "        θ=Parameter(\"θ\"),\n",
        "        hex_rows=hex_rows,\n",
        "        hex_cols=hex_cols,\n",
        "        measure=True,\n",
        "        add_dd=True,\n",
        "    )\n",
        "    circuits_dynamic_dd.append(circuit_dd)\n",
        "    observables_dynamic.append(obs)"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "0f0fdf70",
      "metadata": {},
      "source": [
        "<span id=\"step-2-optimize-problem-for-hardware-execution\" />\n",
        "\n",
        "## ステップ2: ハードウェア実行に向けた問題の最適化\n",
        "\n"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "86642d2b",
      "metadata": {},
      "source": [
        "回路をハードウェアへトランスパイルする準備が整いました。 単一標準実装と動的回路実装の両方をハードウェアへトランスパイルします。\n",
        "\n",
        "ハードウェアへトランスパイルするには、まずバックエンドをインスタンス化します。 利用可能な場合、(`measure_2`) [`MidCircuitMeasure`](/docs/guides/measure-qubits) 命令をサポートするバックエンドを選択します。\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 17,
      "id": "ec904b18",
      "metadata": {},
      "outputs": [],
      "source": [
        "service = QiskitRuntimeService()\n",
        "try:\n",
        "    backend = service.least_busy(\n",
        "        operational=True,\n",
        "        simulator=False,\n",
        "        use_fractional_gates=True,\n",
        "        filters=lambda b: \"measure_2\" in b.supported_instructions,\n",
        "    )\n",
        "except QiskitBackendNotFoundError:\n",
        "    backend = service.least_busy(\n",
        "        operational=True,\n",
        "        simulator=False,\n",
        "        use_fractional_gates=True,\n",
        "    )"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "610622b4",
      "metadata": {},
      "source": [
        "<span id=\"transpilation-for-dynamic-circuits\" />\n",
        "\n",
        "### 動的回路のためのトランスパイル\n",
        "\n",
        "まず、動的回路をトランスパイルします。DDシーケンスを追加する場合と追加しない場合の両方で。 一貫した結果を得るため、全ての回路で同一の物理量子ビットセットを使用することを保証するには、まず回路を一度トランスパイルし、その後パ [`initial_layout`](/docs/api/qiskit/qiskit.transpiler.TranspileLayout#initial_layout) スマネージャーで指定される後続の全ての回路に対してそのレイアウトを使用します。 次に[、プリミティブ統一ブロック](/docs/guides/primitive-input-output) （PUB）をサンプリングプリミティブの入力として構築する。\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 18,
      "id": "aa653907",
      "metadata": {},
      "outputs": [],
      "source": [
        "pm_temp = generate_preset_pass_manager(\n",
        "    optimization_level=3,\n",
        "    backend=backend,\n",
        ")\n",
        "isa_temp = pm_temp.run(circuits_dynamic[-1])\n",
        "dynamic_layout = isa_temp.layout.initial_index_layout(filter_ancillas=True)\n",
        "\n",
        "pm = generate_preset_pass_manager(\n",
        "    optimization_level=3, backend=backend, initial_layout=dynamic_layout\n",
        ")\n",
        "\n",
        "dynamic_isa_circuits = [pm.run(circ) for circ in circuits_dynamic]\n",
        "dynamic_pubs = [(circ, params) for circ in dynamic_isa_circuits]\n",
        "\n",
        "dynamic_isa_circuits_dd = [pm.run(circ) for circ in circuits_dynamic_dd]\n",
        "dynamic_pubs_dd = [(circ, params) for circ in dynamic_isa_circuits_dd]"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "6979ad68",
      "metadata": {},
      "source": [
        "以下のトランスパイルされた回路の量子ビット配置を可視化できます。 黒い円は、動的回路実装で使用されるデータ量子ビットと補助量子ビットを示している。\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 19,
      "id": "65b2df70",
      "metadata": {},
      "outputs": [],
      "source": [
        "def _heron_coords_r2():\n",
        "    cord_map = np.array(\n",
        "        [\n",
        "            [\n",
        "                0,\n",
        "                1,\n",
        "                2,\n",
        "                3,\n",
        "                4,\n",
        "                5,\n",
        "                6,\n",
        "                7,\n",
        "                8,\n",
        "                9,\n",
        "                10,\n",
        "                11,\n",
        "                12,\n",
        "                13,\n",
        "                14,\n",
        "                15,\n",
        "                3,\n",
        "                7,\n",
        "                11,\n",
        "                15,\n",
        "                0,\n",
        "                1,\n",
        "                2,\n",
        "                3,\n",
        "                4,\n",
        "                5,\n",
        "                6,\n",
        "                7,\n",
        "                8,\n",
        "                9,\n",
        "                10,\n",
        "                11,\n",
        "                12,\n",
        "                13,\n",
        "                14,\n",
        "                15,\n",
        "                1,\n",
        "                5,\n",
        "                9,\n",
        "                13,\n",
        "                0,\n",
        "                1,\n",
        "                2,\n",
        "                3,\n",
        "                4,\n",
        "                5,\n",
        "                6,\n",
        "                7,\n",
        "                8,\n",
        "                9,\n",
        "                10,\n",
        "                11,\n",
        "                12,\n",
        "                13,\n",
        "                14,\n",
        "                15,\n",
        "                3,\n",
        "                7,\n",
        "                11,\n",
        "                15,\n",
        "                0,\n",
        "                1,\n",
        "                2,\n",
        "                3,\n",
        "                4,\n",
        "                5,\n",
        "                6,\n",
        "                7,\n",
        "                8,\n",
        "                9,\n",
        "                10,\n",
        "                11,\n",
        "                12,\n",
        "                13,\n",
        "                14,\n",
        "                15,\n",
        "                1,\n",
        "                5,\n",
        "                9,\n",
        "                13,\n",
        "                0,\n",
        "                1,\n",
        "                2,\n",
        "                3,\n",
        "                4,\n",
        "                5,\n",
        "                6,\n",
        "                7,\n",
        "                8,\n",
        "                9,\n",
        "                10,\n",
        "                11,\n",
        "                12,\n",
        "                13,\n",
        "                14,\n",
        "                15,\n",
        "                3,\n",
        "                7,\n",
        "                11,\n",
        "                15,\n",
        "                0,\n",
        "                1,\n",
        "                2,\n",
        "                3,\n",
        "                4,\n",
        "                5,\n",
        "                6,\n",
        "                7,\n",
        "                8,\n",
        "                9,\n",
        "                10,\n",
        "                11,\n",
        "                12,\n",
        "                13,\n",
        "                14,\n",
        "                15,\n",
        "                1,\n",
        "                5,\n",
        "                9,\n",
        "                13,\n",
        "                0,\n",
        "                1,\n",
        "                2,\n",
        "                3,\n",
        "                4,\n",
        "                5,\n",
        "                6,\n",
        "                7,\n",
        "                8,\n",
        "                9,\n",
        "                10,\n",
        "                11,\n",
        "                12,\n",
        "                13,\n",
        "                14,\n",
        "                15,\n",
        "                3,\n",
        "                7,\n",
        "                11,\n",
        "                15,\n",
        "                0,\n",
        "                1,\n",
        "                2,\n",
        "                3,\n",
        "                4,\n",
        "                5,\n",
        "                6,\n",
        "                7,\n",
        "                8,\n",
        "                9,\n",
        "                10,\n",
        "                11,\n",
        "                12,\n",
        "                13,\n",
        "                14,\n",
        "                15,\n",
        "            ],\n",
        "            -1\n",
        "            * np.array([j for i in range(15) for j in [i] * [16, 4][i % 2]]),\n",
        "        ],\n",
        "        dtype=int,\n",
        "    )\n",
        "\n",
        "    hcords = []\n",
        "    ycords = cord_map[0]\n",
        "    xcords = cord_map[1]\n",
        "    for i in range(156):\n",
        "        hcords.append([xcords[i] + 1, np.abs(ycords[i]) + 1])\n",
        "\n",
        "    return hcords"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 20,
      "id": "98d402e0",
      "metadata": {},
      "outputs": [
        {
          "data": {
            "text/plain": [
              "<Image src=\"/docs/images/tutorials/dc-hex-ising/extracted-outputs/98d402e0-0.avif\" alt=\"Output of the previous code cell\" />"
            ]
          },
          "execution_count": 20,
          "metadata": {},
          "output_type": "execute_result"
        }
      ],
      "source": [
        "plot_circuit_layout(\n",
        "    dynamic_isa_circuits_dd[8],\n",
        "    backend,\n",
        "    qubit_coordinates=_heron_coords_r2(),\n",
        "    view=\"virtual\",\n",
        ")"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "1bff4d50",
      "metadata": {},
      "source": [
        "<Admonition type=\"note\">\n",
        "  ` `neato`/usr/lib/lib64/lib64-lib64-lib64-lib64-lib64-lib64-lib64-lib64-lib64-lib64-lib64-lib64-lib64-lib64-lib64-lib64-lib64-lib64-lib64-lib64-lib64-lib`graphviz\\`\\`plot\\_circuit\\_layout()`デフォルト以外の場所（例： MacOS を使用`homebrew`）にインストールした場合、環境変数`PATH\\` を更新する必要がある場合があります。 このノートブック内で以下の方法で行うことができます:\n",
        "\n",
        "  ```python\n",
        "  import os\n",
        "  os.environ['PATH'] = f\"path/to/neato{os.pathsep}{os.environ['PATH']}\"\n",
        "  ```\n",
        "</Admonition>\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 21,
      "id": "82fb6fa8",
      "metadata": {},
      "outputs": [
        {
          "data": {
            "text/plain": [
              "<Image src=\"/docs/images/tutorials/dc-hex-ising/extracted-outputs/82fb6fa8-0.avif\" alt=\"Output of the previous code cell\" />"
            ]
          },
          "execution_count": 21,
          "metadata": {},
          "output_type": "execute_result"
        }
      ],
      "source": [
        "dynamic_isa_circuits[1].draw(fold=-1, output=\"mpl\", idle_wires=False)"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 22,
      "id": "99ad295c",
      "metadata": {},
      "outputs": [
        {
          "data": {
            "text/plain": [
              "<Image src=\"/docs/images/tutorials/dc-hex-ising/extracted-outputs/99ad295c-0.avif\" alt=\"Output of the previous code cell\" />"
            ]
          },
          "execution_count": 22,
          "metadata": {},
          "output_type": "execute_result"
        }
      ],
      "source": [
        "dynamic_isa_circuits_dd[1].draw(fold=-1, output=\"mpl\", idle_wires=False)"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "47d43b9e",
      "metadata": {},
      "source": [
        "<span id=\"transpile-using-midcircuitmeasure\" />\n",
        "\n",
        "#### トランスパイルを使用して `MidCircuitMeasure`\n",
        "\n",
        "`MidCircuitMeasure` これは、既存の測定機能に追加されたもので、 [回路中間部の測定](/docs/guides/execute-dynamic-circuits#midcircuit)を行うために特別に校正されています。 その `MidCircuitMeasure` 命令は、バックエンドでサポートされている命令 `measure_2` に対応しています。 なお、 `measure_2` この機能はすべてのバックエンドでサポートされているわけではありません。 を使用して `service.backends(filters=lambda b: \"measure_2\" in b.supported_instructions)` 、それをサポートしているバックエンドを検索できます。 ここでは、バックエンドが対応している場合、回路内で定義された回路中間測定が \\`\\` `MidCircuitMeasure` 演算子を使用して実行されるように、回路をトランスパイルする方法を示す。\n",
        "\n",
        "以下に、命令 `measure_2` の所要時間と標準 `measure` 命令の所要時間を印刷します。\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 23,
      "id": "de870864",
      "metadata": {},
      "outputs": [
        {
          "name": "stdout",
          "output_type": "stream",
          "text": [
            "Mid-circuit measurement `measure_2` duration: 1.3800000000000003 μs\n",
            "Terminal measurement `measure` duration: 2.1800000000000006 μs\n"
          ]
        }
      ],
      "source": [
        "print(\n",
        "    f'Mid-circuit measurement `measure_2` duration: '\n",
        "    f'{backend.instruction_durations.get('measure_2',0) * backend.dt * 1e9/1e3} μs'\n",
        ")\n",
        "print(\n",
        "    f'Terminal measurement `measure` duration: '\n",
        "    f'{backend.instruction_durations.get('measure',0) * backend.dt *1e9/1e3} μs'\n",
        ")"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 24,
      "id": "a1bdc9e7",
      "metadata": {},
      "outputs": [],
      "source": [
        "\"\"\"Pass that replaces terminal measures in the middle of the circuit with\n",
        "MidCircuitMeasure instructions.\"\"\"\n",
        "\n",
        "\n",
        "class ConvertToMidCircuitMeasure(TransformationPass):\n",
        "    \"\"\"This pass replaces terminal measures in the middle of the circuit with\n",
        "    MidCircuitMeasure instructions.\n",
        "    \"\"\"\n",
        "\n",
        "    def __init__(self, target):\n",
        "        super().__init__()\n",
        "        self.target = target\n",
        "\n",
        "    def run(self, dag):\n",
        "        \"\"\"Run the pass on a dag.\"\"\"\n",
        "        mid_circ_measure = None\n",
        "        for inst in self.target.instructions:\n",
        "            if isinstance(inst[0], Instruction) and inst[0].name.startswith(\n",
        "                \"measure_\"\n",
        "            ):\n",
        "                mid_circ_measure = inst[0]\n",
        "                break\n",
        "        if not mid_circ_measure:\n",
        "            return dag\n",
        "\n",
        "        final_measure_nodes = calc_final_ops(dag, {\"measure\"})\n",
        "        for node in dag.op_nodes(Measure):\n",
        "            if node not in final_measure_nodes:\n",
        "                dag.substitute_node(node, mid_circ_measure, inplace=True)\n",
        "\n",
        "        return dag\n",
        "\n",
        "\n",
        "pm = PassManager(ConvertToMidCircuitMeasure(backend.target))\n",
        "\n",
        "dynamic_isa_circuits_meas2 = [pm.run(circ) for circ in dynamic_isa_circuits]\n",
        "dynamic_pubs_meas2 = [(circ, params) for circ in dynamic_isa_circuits_meas2]\n",
        "\n",
        "dynamic_isa_circuits_dd_meas2 = [\n",
        "    pm.run(circ) for circ in dynamic_isa_circuits_dd\n",
        "]\n",
        "dynamic_pubs_dd_meas2 = [\n",
        "    (circ, params) for circ in dynamic_isa_circuits_dd_meas2\n",
        "]"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "a1e982ee",
      "metadata": {},
      "source": [
        "<span id=\"transpilation-for-unitary-circuits\" />\n",
        "\n",
        "### 単一回路のためのトランスパイレーション\n",
        "\n",
        "動的回路とそのユニタリー対応物との公正な比較を確立するため、データ量子ビットとして動的回路で使用された物理量子ビットの同一セットを、ユニタリー回路のトランスパイル用レイアウトとして使用する。\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 25,
      "id": "87962c09",
      "metadata": {},
      "outputs": [],
      "source": [
        "init_layout = [\n",
        "    dynamic_layout[ind] for ind in range(circuits_unitary[0].num_qubits)\n",
        "]\n",
        "\n",
        "\n",
        "pm = generate_preset_pass_manager(\n",
        "    target=backend.target,\n",
        "    initial_layout=init_layout,\n",
        "    optimization_level=3,\n",
        ")\n",
        "\n",
        "\n",
        "def transpile_minimize(circ: QuantumCircuit, pm: PassManager, iterations=10):\n",
        "    \"\"\"Transpile circuits for specified number of iterations and return the one\n",
        "    with smallest two-qubit gate depth\"\"\"\n",
        "    circs = [pm.run(circ) for i in range(iterations)]\n",
        "    circs_sorted = sorted(\n",
        "        circs,\n",
        "        key=lambda x: x.depth(lambda x: x.operation.num_qubits == 2),\n",
        "    )\n",
        "    return circs_sorted[0]\n",
        "\n",
        "\n",
        "unitary_isa_circuits = []\n",
        "for circ in circuits_unitary:\n",
        "    circ_t = transpile_minimize(circ, pm, iterations=100)\n",
        "    unitary_isa_circuits.append(circ_t)\n",
        "\n",
        "unitary_pubs = [(circ, params) for circ in unitary_isa_circuits]"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "e7da0161",
      "metadata": {},
      "source": [
        "トランスパイルされたユニタリ回路の量子ビット配置を可視化する。 黒い円はユニタリー回路をトランスパイルするために使用される物理量子ビットを示し、それらのインデックスは仮想量子ビットのインデックスに対応する。 これを動的回路用に描かれたレイアウトと比較することで、ユニタリー回路が動的回路のデータ量子ビットと同じ物理量子ビットのセットを使用していることを確認できる。\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 26,
      "id": "8c3c633f",
      "metadata": {},
      "outputs": [
        {
          "data": {
            "text/plain": [
              "<Image src=\"/docs/images/tutorials/dc-hex-ising/extracted-outputs/8c3c633f-0.avif\" alt=\"Output of the previous code cell\" />"
            ]
          },
          "execution_count": 26,
          "metadata": {},
          "output_type": "execute_result"
        }
      ],
      "source": [
        "plot_circuit_layout(\n",
        "    unitary_isa_circuits[-1],\n",
        "    backend,\n",
        "    qubit_coordinates=_heron_coords_r2(),\n",
        "    view=\"virtual\",\n",
        ")"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "2fd70904",
      "metadata": {},
      "source": [
        "次に、トランスパイルされた回路にDDシーケンスを追加し、ジョブ提出用の対応するPUBを構築します。\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 27,
      "id": "383ba663",
      "metadata": {},
      "outputs": [],
      "source": [
        "pm_dd = PassManager(\n",
        "    [\n",
        "        ALAPScheduleAnalysis(target=backend.target),\n",
        "        PadDynamicalDecoupling(\n",
        "            dd_sequence=[\n",
        "                XGate(),\n",
        "                RZGate(np.pi),\n",
        "                XGate(),\n",
        "                RZGate(-np.pi),\n",
        "            ],\n",
        "            spacing=[1 / 4, 1 / 2, 0, 0, 1 / 4],\n",
        "            target=backend.target,\n",
        "        ),\n",
        "    ]\n",
        ")\n",
        "\n",
        "unitary_isa_circuits_dd = pm_dd.run(unitary_isa_circuits)\n",
        "unitary_pubs_dd = [(circ, params) for circ in unitary_isa_circuits_dd]"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "c4980277",
      "metadata": {},
      "source": [
        "<span id=\"compare-two-qubit-gate-depth-of-unitary-and-dynamic-circuits\" />\n",
        "\n",
        "### ユニタリ回路と動的回路における2量子ビットゲートの深さの比較\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 28,
      "id": "36f1d72d",
      "metadata": {},
      "outputs": [
        {
          "data": {
            "text/plain": [
              "<matplotlib.legend.Legend at 0x12628b0e0>"
            ]
          },
          "execution_count": 28,
          "metadata": {},
          "output_type": "execute_result"
        },
        {
          "data": {
            "text/plain": [
              "<Image src=\"/docs/images/tutorials/dc-hex-ising/extracted-outputs/36f1d72d-1.avif\" alt=\"Output of the previous code cell\" />"
            ]
          },
          "metadata": {},
          "output_type": "display_data"
        }
      ],
      "source": [
        "# compare circuit depth of unitary and dynamic circuit implementations\n",
        "unitary_depth = [\n",
        "    unitary_isa_circuits[i].depth(lambda x: x.operation.num_qubits == 2)\n",
        "    for i in range(len(unitary_isa_circuits))\n",
        "]\n",
        "\n",
        "dynamic_depth = [\n",
        "    dynamic_isa_circuits[i].depth(lambda x: x.operation.num_qubits == 2)\n",
        "    for i in range(len(dynamic_isa_circuits))\n",
        "]\n",
        "\n",
        "plt.plot(\n",
        "    list(range(len(unitary_depth))),\n",
        "    unitary_depth,\n",
        "    label=\"unitary circuits\",\n",
        "    color=\"#be95ff\",\n",
        ")\n",
        "plt.plot(\n",
        "    list(range(len(dynamic_depth))),\n",
        "    dynamic_depth,\n",
        "    label=\"dynamic circuits\",\n",
        "    color=\"#ff7eb6\",\n",
        ")\n",
        "plt.xlabel(\"Trotter steps\")\n",
        "plt.ylabel(\"Two-qubit depth\")\n",
        "plt.legend()"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "c566243b",
      "metadata": {},
      "source": [
        "測定ベース回路の主な利点は、複数のZZ相互作用を実装する際に、CX層を並列化でき、測定を同時に行える点である。 これは、すべてのZZ相互作用が可換であるため、測定深度1で計算を実行できるからである。 回路をトランスパイルした後、動的回路アプローチは標準的なユニタリアプローチに比べて2量子ビット深度が大幅に短いことが確認された。ただし、追加の中間回路測定と古典的なフィードフォワード自体が時間を要し、独自の誤差源をもたらす点に留意が必要である。\n",
        "\n"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "206a7278",
      "metadata": {},
      "source": [
        "<span id=\"step-3-execute-using-qiskit-primitives\" />\n",
        "\n",
        "## ステップ3: `Qiskit primitives`を使用して実行する\n",
        "\n"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "53a3e876",
      "metadata": {},
      "source": [
        "<span id=\"local-testing-mode\" />\n",
        "\n",
        "#### ローカルテストモード\n",
        "\n",
        "ハードウェアにジョブを送信する前に、 [ローカルテストモード](/docs/guides/local-testing-mode)を使用して動的回路の簡易テストシミュレーションを実行できます。\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 29,
      "id": "cdfd9576",
      "metadata": {},
      "outputs": [
        {
          "name": "stdout",
          "output_type": "stream",
          "text": [
            "Simulated average magnetization at trotter step = 1 at three theta values\n"
          ]
        },
        {
          "data": {
            "text/plain": [
              "array([ 0.16666667,  0.01529948, -0.14290365])"
            ]
          },
          "execution_count": 29,
          "metadata": {},
          "output_type": "execute_result"
        }
      ],
      "source": [
        "aer_sim = AerSimulator()\n",
        "pm = generate_preset_pass_manager(backend=aer_sim, optimization_level=1)\n",
        "circuit_dynamic_test.measure_all()\n",
        "isa_qc = pm.run(circuit_dynamic_test)\n",
        "with Batch(backend=aer_sim) as batch:\n",
        "    sampler = Sampler(mode=batch)\n",
        "    result = sampler.run([(isa_qc, params)]).result()\n",
        "\n",
        "print(\n",
        "    \"Simulated average magnetization at trotter step = 1 at three theta values\"\n",
        ")\n",
        "result[0].data[\"meas\"].expectation_values(obs_dynamic_test[0])"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "59a3a8a0",
      "metadata": {},
      "source": [
        "<span id=\"mps-simulation\" />\n",
        "\n",
        "#### MPSシミュレーション\n",
        "\n",
        "大規模回路の場合、選択した結合次元に応じて期待値に対する近似結果を提供するMPS `matrix_product_state` シミュレータを使用できます。 その後、MPSシミュレーション結果をベースラインとして使用し、ハードウェアからの結果と比較する。\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 30,
      "id": "6fab4462",
      "metadata": {},
      "outputs": [],
      "source": [
        "# The MPS simulation below took approximately 7 minutes to run on a\n",
        "# laptop with Apple M1 chip\n",
        "\n",
        "mps_backend = AerSimulator(\n",
        "    method=\"matrix_product_state\",\n",
        "    matrix_product_state_truncation_threshold=1e-5,\n",
        "    matrix_product_state_max_bond_dimension=100,\n",
        ")\n",
        "mps_sampler = Aer_Sampler.from_backend(mps_backend)\n",
        "\n",
        "shots = 4096\n",
        "\n",
        "data_sim = []\n",
        "for j in range(points):\n",
        "    circ_list = [\n",
        "        circ.assign_parameters([params[j]]) for circ in circuits_unitary\n",
        "    ]\n",
        "\n",
        "    mps_job = mps_sampler.run(circ_list, shots=shots)\n",
        "    result = mps_job.result()\n",
        "\n",
        "    point_data = [\n",
        "        result[d].data[\"meas\"].expectation_values(observables_unitary)\n",
        "        for d in depths\n",
        "    ]\n",
        "\n",
        "    data_sim.append(point_data)  # data at one theta value\n",
        "\n",
        "data_sim = np.array(data_sim)"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "ebd28d97",
      "metadata": {},
      "source": [
        "回路と観測量が準備されたので、サンプラープリミティブを用いてハードウェア上でそれらを実行する。\n",
        "\n",
        "ここでは、 `dynamic_pubs`、、 `unitary_pubs` に対して3つの `dynamic_pubs_dd`ジョブを提出します。 それぞれは、9種類の異なるトロッターステップと3種類の異なる $\\theta$ パラメータに対応する、パラメータ化された回路のリストである。\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 31,
      "id": "76b5e07e",
      "metadata": {},
      "outputs": [
        {
          "name": "stdout",
          "output_type": "stream",
          "text": [
            "unitary: d96s4b52su3c739hakrg\n",
            "unitary_dd: d96s4bt2su3c739haksg\n",
            "dynamic: d96s4c0tcv6s73dk55mg\n",
            "dynamic_dd: d96s4ckqp3as739qvid0\n",
            "dynamic_meas2: d96s4csqp3as739qvie0\n",
            "dynamic_dd_meas2: d96s4daf47jc73a5v8s0\n"
          ]
        }
      ],
      "source": [
        "shots = 10000\n",
        "\n",
        "with Batch(backend=backend) as batch:\n",
        "    sampler = Sampler(mode=batch)\n",
        "\n",
        "    sampler.options.experimental = {\n",
        "        \"execution\": {\n",
        "            \"scheduler_timing\": True\n",
        "        },  # set to True to retrieve circuit timing info\n",
        "    }\n",
        "\n",
        "    job_unitary = sampler.run(unitary_pubs, shots=shots)\n",
        "    print(f\"unitary: {job_unitary.job_id()}\")\n",
        "\n",
        "    job_unitary_dd = sampler.run(unitary_pubs_dd, shots=shots)\n",
        "    print(f\"unitary_dd: {job_unitary_dd.job_id()}\")\n",
        "\n",
        "    job_dynamic = sampler.run(dynamic_pubs, shots=shots)\n",
        "    print(f\"dynamic: {job_dynamic.job_id()}\")\n",
        "\n",
        "    job_dynamic_dd = sampler.run(dynamic_pubs_dd, shots=shots)\n",
        "    print(f\"dynamic_dd: {job_dynamic_dd.job_id()}\")\n",
        "\n",
        "    job_dynamic_meas2 = sampler.run(dynamic_pubs_meas2, shots=shots)\n",
        "    print(f\"dynamic_meas2: {job_dynamic_meas2.job_id()}\")\n",
        "\n",
        "    job_dynamic_dd_meas2 = sampler.run(dynamic_pubs_dd_meas2, shots=shots)\n",
        "    print(f\"dynamic_dd_meas2: {job_dynamic_dd_meas2.job_id()}\")"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "273fa3a0",
      "metadata": {},
      "source": [
        "<span id=\"step-4-post-process-and-return-results-in-desired-classical-format\" />\n",
        "\n",
        "## ステップ4：後処理を行い、結果を希望の古典的な形式で返す\n",
        "\n",
        "ジョブが完了した後、ジョブ結果のメタデータから実行時間を取得し、実行スケジュールの情報を可視化することができます。 回路のスケジューリング情報の可視化について詳しくは、 [こちらのページ](/docs/guides/qiskit-runtime-circuit-timing)をご覧ください。\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 32,
      "id": "bc16418f",
      "metadata": {},
      "outputs": [],
      "source": [
        "# Circuit durations is reported in the unit of `dt`\n",
        "# which can be retrieved from `Backend` object\n",
        "unitary_durations = [\n",
        "    job_unitary.result()[i].metadata[\"compilation\"][\"scheduler_timing\"][\n",
        "        \"circuit_duration\"\n",
        "    ]\n",
        "    for i in depths\n",
        "]\n",
        "\n",
        "dynamic_durations = [\n",
        "    job_dynamic.result()[i].metadata[\"compilation\"][\"scheduler_timing\"][\n",
        "        \"circuit_duration\"\n",
        "    ]\n",
        "    for i in depths\n",
        "]\n",
        "\n",
        "dynamic_durations_meas2 = [\n",
        "    job_dynamic_meas2.result()[i].metadata[\"compilation\"][\"scheduler_timing\"][\n",
        "        \"circuit_duration\"\n",
        "    ]\n",
        "    for i in depths\n",
        "]\n",
        "\n",
        "result_dd = job_dynamic_dd.result()[1]\n",
        "circuit_schedule_dd = result_dd.metadata[\"compilation\"][\"scheduler_timing\"][\n",
        "    \"timing\"\n",
        "]\n",
        "\n",
        "# to visualize the circuit schedule, one can show the figure below\n",
        "fig_dd = draw_circuit_schedule_timing(\n",
        "    circuit_schedule=circuit_schedule_dd,\n",
        "    included_channels=None,\n",
        "    filter_readout_channels=False,\n",
        "    filter_barriers=False,\n",
        "    width=1000,\n",
        ")\n",
        "\n",
        "# Save to a file since the figure is large\n",
        "fig_dd.write_html(\"scheduler_timing_dd.html\")"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "bee08b77",
      "metadata": {},
      "source": [
        "ユニタリー回路と動的回路の回路持続時間をプロットする。 下図から、中間回路測定と古典的操作に要する時間にもかかわらず、動的回路実装はユニタリー実装と同等の `measure_2` 回路実行時間をもたらすことがわかる。\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 33,
      "id": "639221e6",
      "metadata": {},
      "outputs": [
        {
          "data": {
            "text/plain": [
              "<matplotlib.legend.Legend at 0x12bfde270>"
            ]
          },
          "execution_count": 33,
          "metadata": {},
          "output_type": "execute_result"
        },
        {
          "data": {
            "text/plain": [
              "<Image src=\"/docs/images/tutorials/dc-hex-ising/extracted-outputs/639221e6-1.avif\" alt=\"Output of the previous code cell\" />"
            ]
          },
          "metadata": {},
          "output_type": "display_data"
        }
      ],
      "source": [
        "# visualize circuit durations\n",
        "\n",
        "\n",
        "def convert_dt_to_microseconds(circ_duration: List, backend_dt: float):\n",
        "    dt = backend_dt * 1e6  # dt in microseconds\n",
        "    return list(map(lambda x: x * dt, circ_duration))\n",
        "\n",
        "\n",
        "dt = backend.target.dt\n",
        "plt.plot(\n",
        "    depths,\n",
        "    convert_dt_to_microseconds(unitary_durations, dt),\n",
        "    color=\"#be95ff\",\n",
        "    linestyle=\":\",\n",
        "    label=\"unitary\",\n",
        ")\n",
        "plt.plot(\n",
        "    depths,\n",
        "    convert_dt_to_microseconds(dynamic_durations, dt),\n",
        "    color=\"#ff7eb6\",\n",
        "    linestyle=\"-.\",\n",
        "    label=\"dynamic\",\n",
        ")\n",
        "plt.plot(\n",
        "    depths,\n",
        "    convert_dt_to_microseconds(dynamic_durations_meas2, dt),\n",
        "    color=\"#ff7eb6\",\n",
        "    linestyle=\"-.\",\n",
        "    marker=\"s\",\n",
        "    mfc=\"none\",\n",
        "    label=\"dynamic w/ meas2\",\n",
        ")\n",
        "\n",
        "plt.xlabel(\"Trotter steps\")\n",
        "plt.ylabel(r\"Circuit durations in $\\mu$s\")\n",
        "plt.legend()"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "3c2bd06f",
      "metadata": {},
      "source": [
        "ジョブが完了した後、以下のデータを取得し、先に構築した観測量 `observables_unitary``observables_dynamic` または によって推定される平均磁化を計算する。\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 34,
      "id": "f4947049",
      "metadata": {},
      "outputs": [],
      "source": [
        "runs = {\n",
        "    \"unitary\": (\n",
        "        job_unitary,\n",
        "        [observables_unitary] * len(circuits_unitary),\n",
        "    ),\n",
        "    \"unitary_dd\": (\n",
        "        job_unitary_dd,\n",
        "        [observables_unitary] * len(circuits_unitary),\n",
        "    ),\n",
        "    # Omitting Dyn w/o DD and Dynamic w/ DD plots for better readability\n",
        "    # \"dynamic\": (job_dynamic, observables_dynamic),\n",
        "    # \"dynamic_dd\": (job_dynamic_dd, observables_dynamic),\n",
        "    \"dynamic_meas2\": (job_dynamic_meas2, observables_dynamic),\n",
        "    \"dynamic_dd_meas2\": (\n",
        "        job_dynamic_dd_meas2,\n",
        "        observables_dynamic,\n",
        "    ),\n",
        "}"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 35,
      "id": "583d417e",
      "metadata": {},
      "outputs": [],
      "source": [
        "data_dict = {}\n",
        "for key, (job, obs) in runs.items():\n",
        "    data = []\n",
        "    for i in range(points):\n",
        "        data.append(\n",
        "            [\n",
        "                job.result()[ind].data[\"meas\"].expectation_values(obs[ind])[i]\n",
        "                for ind in depths\n",
        "            ]\n",
        "        )\n",
        "    data_dict[key] = data"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "507073d9",
      "metadata": {},
      "source": [
        "以下に、局所磁場の強度に対応する異なる $\\theta$ 値におけるトロッターステップ数に対するスピン磁化をプロットする。 ユニタリー理想回路に対する事前計算されたMPSシミュレーション結果と、以下の実験結果を共にプロットする：\n",
        "\n",
        "1. DDを用いたユニタリー回路の実行\n",
        "2. DDを用いた動的回路の実行 `MidCircuitMeasure`\n",
        "\n"
      ]
    },
    {
      "cell_type": "code",
      "execution_count": 36,
      "id": "662239cf",
      "metadata": {},
      "outputs": [
        {
          "data": {
            "text/plain": [
              "<Image src=\"/docs/images/tutorials/dc-hex-ising/extracted-outputs/662239cf-0.avif\" alt=\"Output of the previous code cell\" />"
            ]
          },
          "metadata": {},
          "output_type": "display_data"
        }
      ],
      "source": [
        "plt.figure(figsize=(10, 6))\n",
        "\n",
        "colors = [\"#0f62fe\", \"#be95ff\", \"#ff7eb6\"]\n",
        "for i in range(points):\n",
        "    plt.plot(\n",
        "        depths,\n",
        "        data_sim[i],\n",
        "        color=colors[i],\n",
        "        linestyle=\"solid\",\n",
        "        label=f\"θ={pi_check(i*max_angle/(points-1))} (MPS)\",\n",
        "    )\n",
        "    # plt.plot(\n",
        "    #     depths,\n",
        "    #     data_dict[\"unitary\"][i],\n",
        "    #     color=colors[i],\n",
        "    #     linestyle=\":\",\n",
        "    #     label=f\"θ={pi_check(i*max_angle/(points-1))} (Unitary)\",\n",
        "    # )\n",
        "\n",
        "    plt.plot(\n",
        "        depths,\n",
        "        data_dict[\"unitary_dd\"][i],\n",
        "        color=colors[i],\n",
        "        marker=\"o\",\n",
        "        mfc=\"none\",\n",
        "        linestyle=\":\",\n",
        "        label=f\"θ={pi_check(i*max_angle/(points-1))} (Unitary w/DD)\",\n",
        "    )\n",
        "\n",
        "    # Omitting Dyn w/o DD and Dynamic w/ DD plots for better readability\n",
        "    # plt.plot(\n",
        "    #     depths,\n",
        "    #     data_dict[\"dynamic\"][i],\n",
        "    #     color=colors[i],\n",
        "    #     linestyle=\"-.\",\n",
        "    #     label=f\"θ={pi_check(i*max_angle/(points-1))} (Dyn w/o DD)\",\n",
        "    # )\n",
        "    # plt.plot(\n",
        "    #     depths,\n",
        "    #     data_dict[\"dynamic_dd\"][i],\n",
        "    #     marker=\"D\",\n",
        "    #     mfc=\"none\",\n",
        "    #     color=colors[i],\n",
        "    #     linestyle=\"-.\",\n",
        "    #     label=f\"θ={pi_check(i*max_angle/(points-1))} (Dynamic w/ DD)\",\n",
        "    # )\n",
        "\n",
        "    # plt.plot(\n",
        "    #     depths,\n",
        "    #     data_dict[\"dynamic_meas2\"][i],\n",
        "    #     color=colors[i],\n",
        "    #     marker=\"s\",\n",
        "    #     mfc=\"none\",\n",
        "    #     linestyle=':',\n",
        "    #     label=f\"θ={pi_check(i*max_angle/(points-1))} (Dynamic w/ MidCircuitMeas)\",\n",
        "    # )\n",
        "\n",
        "    plt.plot(\n",
        "        depths,\n",
        "        data_dict[\"dynamic_dd_meas2\"][i],\n",
        "        color=colors[i],\n",
        "        marker=\"*\",\n",
        "        markersize=8,\n",
        "        linestyle=\":\",\n",
        "        label=f\"θ={pi_check(i*max_angle/(points-1))} \"\n",
        "        f\"(Dynamic w/ DD & MidCircuitMeas)\",\n",
        "    )\n",
        "\n",
        "\n",
        "plt.xlabel(\"Trotter steps\", fontsize=16)\n",
        "plt.ylabel(\"Average magnetization\", fontsize=16)\n",
        "plt.xticks(rotation=45)\n",
        "handles, labels = plt.gca().get_legend_handles_labels()\n",
        "plt.legend(\n",
        "    handles,\n",
        "    labels,\n",
        "    loc=\"upper right\",\n",
        "    bbox_to_anchor=(1.46, 1.0),\n",
        "    shadow=True,\n",
        "    ncol=1,\n",
        ")\n",
        "plt.title(\n",
        "    f\"{hex_rows}x{hex_cols} hex ring, {num_qubits} data qubits, \"\n",
        "    f\"{len(ancilla)} ancilla qubits \\n{backend.name}: Sampler\"\n",
        ")\n",
        "plt.show()"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "aead1034",
      "metadata": {},
      "source": [
        "実験結果とシミュレーション結果を比較すると、動的回路実装（星印の付いた点線）が標準ユニタリー実装（丸印の付いた点線）よりも全体的に優れた性能を示していることがわかる。 要約すると、我々はハニカム格子上でのアイジングスピンモデルのシミュレーション手法として動的回路を提案する。このトポロジーはハードウェアに固有のものではない。 動的回路ソリューションは、最隣接でない量子ビット間のZZ相互作用を可能とし、SWAPゲートを使用する場合よりも短い2量子ビットゲート深度を実現する。ただし、追加の補助量子ビットと古典的なフィードフォワード操作を導入する代償を伴う。\n",
        "\n"
      ]
    },
    {
      "cell_type": "markdown",
      "id": "52fb43e1",
      "metadata": {},
      "source": [
        "<span id=\"references\" />\n",
        "\n",
        "## 参照\n",
        "\n",
        "\\[1] Qiskitを用いた量子コンピューティング、Javadi-Abhari, A. 著 トレイニッシュ, M., クルシリッチ, K., ウッド、 C.J リシュマン, J., ガコン, J., マルティエル, S., ネイション、 P.D ビショップ、 L.S クロス、 A.W。およびジョンソン、 B.R 2024. arXiv プレプリント [arXiv:2405.08810 (2024)](https://arxiv.org/abs/2405.08810)\n",
        "\n"
      ]
    },
    {
      "cell_type": "markdown",
      "metadata": {},
      "id": "a1b8767d",
      "source": "© IBM Corp., 2017-2026"
    }
  ],
  "metadata": {
    "kernelspec": {
      "display_name": "Python 3",
      "language": "python",
      "name": "python3"
    },
    "language_info": {
      "codemirror_mode": {
        "name": "ipython",
        "version": 3
      },
      "file_extension": ".py",
      "mimetype": "text/x-python",
      "name": "python",
      "nbconvert_exporter": "python",
      "pygments_lexer": "ipython3",
      "version": "3"
    },
    "hours": 1,
    "qpuSeconds": 450
  },
  "nbformat": 4,
  "nbformat_minor": 5
}