Skip to content

Carry one state through a D-A-D experiment

Prepare a qubit with a Digital gate, evolve it under an Analog drive, then apply a Digital readout gate. Compare this continuous experiment with a control that starts the Analog block from a fresh ground state. The two probability distributions make state continuity observable.

Start with gates and coherence and global Analog drive. This local experiment has one qubit, four Analog time steps and 16 shots per run. Run it from the repository root after installation.

Predict the two distributions

The first H gate prepares |+⟩ = (|0⟩ + |1⟩)/√2. The Analog block uses zero detuning and phase, so its Hamiltonian is Ω(t) X / 2. Its pulse area is (0.2 + 0.6) × 0.1 / 2 = 0.04 rad.

|+⟩ is an eigenstate of X. This drive therefore changes only its global phase. The final H maps it back to |0⟩, so the ideal terminal measurement yields 0 with probability one. A changing control does not necessarily change measurement probabilities for every input state.

For the reset control, omit the preparation H. The Analog block now receives |0⟩. Rotation about X keeps the X expectation at zero, and the last H turns an X-basis measurement into a Z-basis measurement. The predicted probabilities are then 1/2 and 1/2.

Build all blocks before measuring

"""Run a first Digital-Analog-Digital program on one continuous state.

Learning goals:
1. Build native Digital and Analog payloads without touching internal IR.
2. Compose both payloads with ``HybridProgram``.
3. Verify state continuity from the result's block-state chain.

Run this file from the repository root. The fixed seed and small workload make
the output deterministic and keep the lesson fully offline.
"""

from __future__ import annotations

import json

from cascaqit import (
    AHSProgram,
    AtomRegister,
    Circuit,
    HybridProgram,
    LocalBackend,
    Waveform,
)


def main() -> None:
    """Build, execute, and inspect one minimal shared-state experiment."""
    # Digital preparation changes the same state later consumed by Analog evolution.
    prepare = Circuit(1, program_id="lesson.hybrid.beginner.prepare").h(0)

    # A short global drive supplies a real time-dependent Analog block.
    evolve = AHSProgram(
        AtomRegister.line(count=1, spacing=5.0),
        program_id="lesson.hybrid.beginner.evolve",
    ).drive(
        rabi=Waveform.linear(0.2, 0.6, duration=0.1),
        detuning=Waveform.constant(0.0, duration=0.1),
        phase=0.0,
    )

    # The last H changes the readout basis; measurement ends the whole program.
    program = (
        HybridProgram("lesson.hybrid.beginner")
        .digital("prepare", prepare)
        .analog("evolve", evolve)
        .digital("readout", Circuit(1).h(0))
        .measure_all()
    )
    result = LocalBackend(analog_time_steps=4).run(program, shots=16, seed=101).result()
    transitions = result.state_transitions()
    reset_program = (
        HybridProgram("lesson.hybrid.reset-control")
        .analog("evolve", evolve)
        .digital("readout", Circuit(1).h(0))
        .measure_all()
    )
    reset_result = (
        LocalBackend(analog_time_steps=4)
        .run(reset_program, shots=16, seed=101)
        .result()
    )

    payload = {
        "track": "hybrid_researcher",
        "level": "beginner",
        "lesson": "first_shared_state",
        "facts": {
            "block_kinds": [item.program_kind for item in transitions],
            "state_continuous": all(
                left.output_state_hash == right.input_state_hash
                for left, right in zip(transitions, transitions[1:])
            ),
            "probabilities": result.probabilities,
            "reset_control_probabilities": reset_result.probabilities,
            "counts_total": sum(result.counts.values()),
            "program_hash_present": len(result.program_hash) == 64,
        },
        "boundaries": {
            "hardware_execution": False,
            "cloud_execution": False,
            "network_accessed": False,
            "credentials_loaded": False,
        },
    }
    print(json.dumps(payload, sort_keys=True))


if __name__ == "__main__":
    main()

Download the full script

python3 examples/user/tracks/hybrid_researcher/01_beginner_first_shared_state_en.py

digital("prepare", ...), analog("evolve", ...) and digital("readout", ...) append operations in order. Neither payload measures halfway through the experiment. measure_all() closes the Hybrid program after the last block.

A separate LocalBackend.run() call starts a separate experiment. Passing an Analog program to it after running a circuit does not automatically transfer the circuit's final state. Use one HybridProgram for the continuous sequence.

{
  "boundaries": {
    "cloud_execution": false,
    "credentials_loaded": false,
    "hardware_execution": false,
    "network_accessed": false
  },
  "facts": {
    "block_kinds": [
      "digital",
      "analog",
      "digital"
    ],
    "counts_total": 16,
    "probabilities": {
      "0": 1.0,
      "1": 0.0
    },
    "program_hash_present": true,
    "reset_control_probabilities": {
      "0": 0.5,
      "1": 0.5
    },
    "state_continuous": true
  },
  "lesson": "first_shared_state",
  "level": "beginner",
  "track": "hybrid_researcher"
}

block_kinds should read ["digital", "analog", "digital"]. state_continuous checks that each block's recorded output state is the next block's input. This is useful execution evidence; the probability comparison supplies a separate numerical check against the physical prediction.

Read probabilities and reset_control_probabilities. They should match the two predictions above within numerical precision. The count total for the D-A-D run is 16. The reset run uses 16 shots too, but its sample counts need not split 8/8. Add print(reset_result.counts) if you want to inspect them.

Try a different readout or input

  1. Remove the last H from both programs. Predict their Z probabilities before running.
  2. Keep all three blocks and change the Analog ramp endpoints to 0.4 and 1.2 rad/us. Will the ideal D-A-D probability change? What does the reset control show in the original readout basis?
  3. Replace preparation H with X, keep the original Analog drive and remove readout H. Predict P(1) from the pulse area.
Check your reasoning

Without the last H, the continuous run stays balanced in Z. The reset run has P(1) = sin²(0.04/2), about 0.000400. Doubling the X-drive area still changes only the global phase of |+⟩, so the full D-A-D output remains 0; the reset A-D control remains balanced. Starting from |1⟩ instead gives P(1) = cos²(0.04/2) before readout, about 0.999600. These formulas use zero detuning and phase with one qubit; do not apply them unchanged to interacting arrays.

When the result differs from your prediction, check block order, terminal measurement placement and the initial state of each separately submitted run. A matching state-hash chain alone cannot validate the Hamiltonian, units or intended observable. See shared simulation state for the representation, then follow the Hybrid route into shared parameters, scans and noise.

Concept reference: shared simulation state.

中文版

SDK 1.0.8a · `8b227bff`