> ## Documentation Index
> Fetch the complete documentation index at: https://b01t.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Demo programs: complete b01t algorithm examples

> Runnable end-to-end demos showing how to build, certify, and execute quantum algorithms with b01t, from textbook circuits to full coherent pipelines.

The `demos/` directory contains complete, runnable examples that show how b01t programs are structured in practice. Each demo pairs a `@coherent` or `@adaptive` circuit with its classical driver, covering algorithms from introductory textbook problems through to multi-layer coherent pipelines. Reading these alongside the source code in `b01t/zoo/` is the fastest way to understand how the DSL components fit together.

<AccordionGroup>
  <Accordion title="Grover search (demos/grover_search/)">
    Implements Grover's algorithm to find `|11⟩` in a 2-qubit space. The demo shows how to inline the oracle and diffusion operator inside a `@parametric` step, then drive two iterations from a `@adaptive` top-level circuit.

    **What it demonstrates:** `@adaptive` + `@parametric` composition, `repeat`, `measure_all`, ancilla discipline in a broad-IR context.

    ```python theme={null}
    from b01t import (
        QReg, adaptive, parametric, h, x, ccx, cz, mcx, z,
        measure_all, ancilla, compute, phase, uncompute, repeat,
    )

    @parametric
    def grover_step(sys: QReg):
        # Oracle: mark |11>
        with ancilla(1) as anc:
            compute(lambda: ccx(sys[0], sys[1], anc[0]))
            phase(lambda: z(anc[0]))
            uncompute()
        # Diffusion: H-X-MCZ-X-H
        for q in sys:
            h(q)
            x(q)
        with ancilla(1) as anc:
            compute(lambda: mcx(sys.wires()[:-1], anc[0]))
            phase(lambda: cz(anc[0], sys[-1]))
            uncompute()
        for q in sys:
            x(q)
            h(q)

    @adaptive
    def grover_search(sys: QReg):
        for q in sys:
            h(q)
        repeat(2, lambda: grover_step(sys))
        return measure_all(sys)
    ```

    **Run it:**

    ```bash theme={null}
    uv run pytest demos/grover_search/
    ```
  </Accordion>

  <Accordion title="Deutsch's algorithm (demos/deutsch/)">
    Determines whether a 1-bit Boolean function `f: {0,1} → {0,1}` is constant or balanced using a single quantum query. Classically you need two evaluations; Deutsch's algorithm needs one.

    **What it demonstrates:** `@coherent` oracle construction, `@adaptive` algorithm, phase kickback with `|−⟩` target, `measure` on a single qubit.

    The oracle `make_deutsch_oracle(f0, f1)` implements `U_f|x,y⟩ = |x, y ⊕ f(x)⟩` using only permutation gates (`X`, `CX`):

    ```python theme={null}
    from b01t import QReg, coherent, cx, x

    def make_deutsch_oracle(f0: int, f1: int):
        @coherent
        def oracle(inp: QReg, tgt: QReg):
            if f0 == 1:
                x(tgt[0])
            if f0 != f1:
                cx(inp[0], tgt[0])
        return oracle
    ```

    The algorithm prepares `|+⟩` on the input and `|−⟩` on the target, queries once, then measures. The result is `0` for constant functions and `1` for balanced functions:

    ```python theme={null}
    from b01t import QReg, adaptive, h, x, cx, measure

    def make_deutsch_algorithm(f0: int, f1: int):
        @adaptive
        def algorithm(inp: QReg, tgt: QReg):
            h(inp[0])
            x(tgt[0]); h(tgt[0])          # prepare |->
            if f0 == 1:
                x(tgt[0])
            if f0 != f1:
                cx(inp[0], tgt[0])
            h(inp[0])
            return measure(inp[0])         # 0=constant, 1=balanced
        return algorithm
    ```

    **Run it:**

    ```bash theme={null}
    uv run pytest demos/deutsch/
    ```
  </Accordion>

  <Accordion title="Bernstein-Vazirani (demos/bernstein_vazirani/)">
    Recovers a hidden binary string `s` from the function `f(x) = s·x (mod 2)` using a single quantum query, where a classical algorithm needs `n` queries.

    **What it demonstrates:** `@coherent` oracle with a secret parameter, `@adaptive` algorithm, `measure_all`, `for_each`-style Hadamard layers.

    The oracle implements `U_f|x,y⟩ = |x, y ⊕ (s·x)⟩` by applying `CX(x_i, target)` for each `i` where `s_i = 1`:

    ```python theme={null}
    from typing import Sequence
    from b01t import QReg, coherent, cx

    def make_bv_oracle(secret: Sequence[int]):
        s = tuple(secret)
        @coherent
        def oracle(inp: QReg, tgt: QReg):
            for i in range(len(s)):
                if s[i] == 1:
                    cx(inp[i], tgt[0])
        return oracle
    ```

    The algorithm applies Hadamard on all inputs, queries the oracle, applies Hadamard again, and measures — the output is the hidden string `s` directly:

    ```python theme={null}
    from b01t import QReg, adaptive, h, x, cx, measure_all

    def make_bv_algorithm(secret: Sequence[int]):
        s = tuple(secret)
        @adaptive
        def algorithm(inp: QReg, tgt: QReg):
            for i in range(len(s)):
                h(inp[i])
            x(tgt[0]); h(tgt[0])          # prepare |->
            for i in range(len(s)):
                if s[i] == 1:
                    cx(inp[i], tgt[0])
            for i in range(len(s)):
                h(inp[i])
            return measure_all(inp)        # outcome = s
        return algorithm
    ```

    **Run it:**

    ```bash theme={null}
    uv run pytest demos/bernstein_vazirani/
    ```
  </Accordion>

  <Accordion title="Simon's algorithm (demos/simon/)">
    Finds a hidden XOR-mask `s` satisfying `f(x) = f(x ⊕ s)` for all `x`, using O(n) quantum rounds followed by classical Gaussian elimination. Classically the problem requires exponentially many queries.

    **What it demonstrates:** multi-register `@coherent` oracle, repeated `@adaptive` rounds, classical post-processing to recover a hidden period.

    Each quantum round produces a random string `y` satisfying `y·s = 0 (mod 2)`. After `n − 1` linearly independent samples, `s` is recovered classically:

    ```python theme={null}
    from typing import Sequence
    from b01t import QReg, adaptive, h, cx, measure_all

    def make_simon_algorithm(secret: Sequence[int]):
        s = tuple(secret)
        n = len(s)
        pivot = next((i for i in range(n) if s[i] == 1), None)

        @adaptive
        def algorithm(inp: QReg, out: QReg):
            for i in range(n):
                h(inp[i])
            # Oracle: copy input, then conditionally XOR s into output
            for i in range(n):
                cx(inp[i], out[i])
            if pivot is not None:
                for i in range(n):
                    if s[i] == 1 and i != pivot:
                        cx(inp[pivot], out[i])
                cx(inp[pivot], out[pivot])
            for i in range(n):
                h(inp[i])
            return measure_all(inp)   # y such that y·s = 0 mod 2

        return algorithm
    ```

    **Run it:**

    ```bash theme={null}
    uv run pytest demos/simon/
    ```
  </Accordion>

  <Accordion title="Shor's algorithm (demos/shor/)">
    Factors an integer `N` by finding the period of `a^x mod N` using Quantum Phase Estimation with a modular exponentiation oracle.

    **What it demonstrates:** `@adaptive` top-level circuit, `@parametric` modular exponentiation inlined for broad-IR, `inverse_qft` from `zoo.qft`, and classical continued-fraction post-processing.

    `make_shor_circuit(a_val, N, num_counting_bits)` returns an `@adaptive` function that:

    1. Initialises the work register to `|1⟩`.
    2. Applies Hadamard to the counting register.
    3. Runs the modular exponentiation oracle.
    4. Applies `inverse_qft` on the counting register.
    5. Measures the counting register.

    ```python theme={null}
    from b01t import QReg, adaptive, x, h, measure_all
    from b01t.zoo.qft import inverse_qft

    def make_shor_circuit(a_val: int, N: int, num_counting_bits: int):
        oracle = _make_parametric_modular_exp(a_val, N, num_counting_bits)

        @adaptive
        def shor_circuit(counting: QReg, y_reg: QReg, acc: QReg, scratch: QReg):
            x(y_reg[0])                       # initialise work to |1>
            for i in range(len(counting)):
                h(counting[i])
            oracle(counting, y_reg, acc, scratch)
            inverse_qft(counting)
            return measure_all(counting)

        return shor_circuit
    ```

    The measurement is then decoded classically using continued fractions. The demo includes helper utilities for this post-processing step:

    ```python theme={null}
    # Classical post-processing: decode QPE measurement to period, then factor
    # measurement is the integer read from the counting register
    # r = period of a^x mod N recovered via continued fractions
    # factors = gcd(a^(r/2) ± 1, N)
    measurement = 42        # example QPE output
    # See demos/shor/ for the classical continued-fraction utilities
    ```

    **Run it:**

    ```bash theme={null}
    uv run pytest demos/shor/
    ```
  </Accordion>

  <Accordion title="Rollout oracle (demos/rollout/)">
    Implements coherent rollout oracles for sequential decision problems, where a quantum circuit simulates multiple rounds of a stochastic environment in superposition.

    **What it demonstrates:** multi-register `@coherent` state-preparation, `rank_select_binary` from `zoo.rank_select`, complex ancilla discipline across many sub-circuits.

    Two environments are provided:

    * **`sway/`** — a two-player stochastic board game where black and white alternate placing stones on a grid, with stochastic rule transitions.
    * **`epidemic/`** — an SIR epidemic intervention model where a policy selects interventions over time.

    The rollout oracle structure for the Sway game prepares a superposition over all outcomes by:

    1. Placing selector registers in uniform superposition (`H` on each bit).
    2. Using `rank_select_binary` to coherently map a selector index to the corresponding legal move.
    3. Applying the transition and terminal evaluation circuits.

    ```python theme={null}
    from b01t import QReg, coherent, h
    from b01t.zoo.rank_select import rank_select_binary
    from demos.rollout.sway.sway_spec import SwaySpec

    spec = SwaySpec(rows=2, cols=2, horizon=1)
    # register_specs() returns (name, size) pairs for every qubit register
    reg_specs = spec.register_specs()
    ```

    **Run it:**

    ```bash theme={null}
    uv run pytest tests/test_rollout_sway.py
    uv run pytest tests/test_rollout_epidemic.py
    ```
  </Accordion>

  <Accordion title="Best arm (demos/best_arm/)">
    A full coherent pipeline that identifies the highest-payoff action in a decision problem using quantum maximum finding. It composes three layers: a rollout oracle, coherent amplitude estimation, and Dürr–Høyer maximum finding.

    **What it demonstrates:** end-to-end composition of `zoo.qae.make_coherent_ae`, `zoo.max_finding.make_comparison_oracle`, and `zoo.max_finding.DurrHoyerRunner`. This is the most complex demo and shows how the zoo modules stack together.

    The pipeline is:

    ```
    DurrHoyerRunner (O(√k) comparisons)
      └─ comparison oracle
           ├─ coherent AE (QPE on Grover iterate, O(1/ε) depth)
           │    └─ Grover iterate G = mark · A† · S₀ · A
           │         └─ A = arm-specific rollout oracle
           ├─ less_than comparison to threshold
           └─ uncompute
    ```

    Each "arm" is a different first action for the player. The arm oracle fixes the first-round selector to a specific action index while leaving the rest of the game randomness in superposition:

    ```python theme={null}
    from b01t.zoo.qae import make_coherent_ae
    from b01t.zoo.max_finding import make_comparison_oracle, DurrHoyerRunner
    from demos.best_arm.arm_oracle import make_arm_state_prep, make_arm_mark_oracle
    from demos.rollout.sway.sway_spec import SwaySpec

    spec = SwaySpec(rows=2, cols=2, horizon=1)
    mark_oracle = make_arm_mark_oracle(spec)

    # Build per-arm state-prep oracles
    arm_preps = [make_arm_state_prep(spec, action_index=i)
                 for i in range(spec.black_choices(1))]

    # Coherent AE for each arm
    ae_circuits = [make_coherent_ae(prep, mark_oracle) for prep in arm_preps]

    # Comparison oracle: does arm i beat the current threshold?
    ae_arm0 = ae_circuits[0]
    comp = make_comparison_oracle(ae_arm0, threshold_value=1, precision=2)
    ```

    **Run it:**

    ```bash theme={null}
    uv run python -m demos.best_arm.demo
    uv run pytest tests/test_best_arm_correctness.py
    ```
  </Accordion>
</AccordionGroup>

## Running all demos

You can run every demo's test suite from the repository root:

```bash theme={null}
uv run pytest demos/
```

Or run the full best-arm pipeline demo to see the circuit qubit counts and gate counts printed to the console:

```bash theme={null}
uv run python -m demos.best_arm.demo
```
