Rust vs Pure CJC

Dual-Mode Quantum Architecture

One API, two backends. Choose between maximum performance and full transparency — with identical physics and deterministic guarantees on both.

Rust: Production Pure: Research Zero Dependencies

00 One Line Changes Everything

Switch between backends by adding a single argument. All subsequent operations auto-detect.

Rust Backend // Default: optimized Rust kernels
let m = mps_new(50, 16);
let m = mps_h(m, 0);
let m = mps_cnot(m, 0, 1);
mps_z_expectation(m, 0)
Pure CJC Backend // Add "pure" — everything else is identical
let m = mps_new(50, 16, "pure");
let m = mps_h(m, 0);
let m = mps_cnot(m, 0, 1);
mps_z_expectation(m, 0)

01 Feature Comparison

Each backend is optimized for different use cases.

Rust Backend (default)
Pure CJC Backend ("pure")
SIMD-ready vectorized kernels
Full state inspection via quantum_inspect()
Zero-copy COW buffers
User-modifiable algorithms
Optimized LAPACK-style SVD
Transparent Jacobi SVD (readable source)
Production workloads
Research prototyping & education
Best for >50 qubit systems
Future AD (autodiff) integration
Opaque internal state
Higher overhead per operation

02 Performance Comparison

Side-by-side timing across all four quantum simulation paradigms. (Release mode, Intel i7)

Matrix Product State (MPS) — 50 qubits, 5 gates + Z-expectation

0 0.05 0.10 0.15 0.20ms Rust 0.13 ms Pure CJC 0.04 ms Z = 0.0 Z = 0.0 MATCH ✓ MATCH ✓
Benchmark Qubits Rust Pure CJC Δ Result Verdict
MPS 5 gates + Z-exp 50 0.13 ms 0.04 ms 0.00e0 ✓ Identical
MPS GHZ (9 CNOTs) 10 0.22 ms 0.12 ms 0.00e0 ✓ Identical
Stabilizer Clifford suite 1,000 1.36 ms 1.93 ms 0 ✓ Identical
Density purity (pure state) 3 0.10 ms 0.03 ms 8.88e-16 ✓ Identical
Density + depolarize 2 0.11 ms 0.03 ms 7.77e-16 ✓ Identical
von Neumann entropy 2 0.20 ms 0.06 ms 3.33e-16 ✓ Identical
VQE 4q Heisenberg energy 4 0.13 ms 0.07 ms 8.77e-15 ✓ Identical
Circuit Bell probs 2 0.38 ms 0.06 ms <1e-15 ✓ Identical

All Δ values are at or below machine epsilon (2.22e-16). The backends produce physically identical results.

03 Memory Efficiency

Both backends use identical MPS compression. The comparison to statevector is staggering.

Statevector 50q 16,384 TB (2⁵⁰ × 16 bytes) — IMPOSSIBLE Rust MPS 50q 1,600 bytes (~1.6 KB) Pure MPS 50q 1,600 bytes (~1.6 KB) 10,000,000,000x compression — identical on both backends

04 Determinism — The Shared Guarantee

Same seed = bit-identical output. Every run. Both backends. Across platforms.

Rust Backend — 5 runs, seed=42

Run 1: 0.7648421872844882
Run 2: 0.7648421872844882
Run 3: 0.7648421872844882
Run 4: 0.7648421872844882
Run 5: 0.7648421872844882
ALL IDENTICAL ✓

Pure CJC Backend — 5 runs, seed=42

Run 1: 0.7648421872844882
Run 2: 0.7648421872844882
Run 3: 0.7648421872844882
Run 4: 0.7648421872844882
Run 5: 0.7648421872844882
ALL IDENTICAL ✓
Cross-backend Δ = 0.00e0 Both backends produce the exact same 16-digit result
🎲
SplitMix64 PRNG
Explicit seed threading, no global state
Kahan Summation
Compensated FP reduction in all accumulations
No FMA
No fused multiply-add — cross-platform identical
🌳
BTreeMap Only
Deterministic iteration order, never HashMap

05 What Pure CJC Gives You: Inspectability

The pure backend exposes all internal quantum state as native CJC Maps. Impossible with the Rust backend.

quantum_inspect(state) — returns a Map with all internal data: tensor shapes, amplitudes, tableau bits, bond dimensions. Only available for pure-backend states.

🧩 MPS after H gate on qubit 0

quantum_inspect(mps_h(mps_new(3, 4, "pure"), 0))
{
  _backend: "pure",
  _type: "mps",
  n_qubits: 3,
  max_bond: 4,
  tensors: [
    { bond_left: 1, bond_right: 1,
      data_re: [0.7071, 0.7071],
      data_im: [0, 0] },
    { bond_left: 1, ... data_re: [1, 0] },
    { bond_left: 1, ... data_re: [1, 0] }
  ]
}

→ Qubit 0 shows the H|0⟩ amplitudes: 1/√2 for both |0⟩ and |1⟩

📊 Density matrix after H gate

quantum_inspect(density_gate(density_new(1, "pure"), "H", 0))
{
  _backend: "pure",
  _type: "density",
  n_qubits: 1,
  dim: 2,
  data_re: [0.5, 0.5, 0.5, 0.5],
  data_im: [0, 0, 0, 0]
}

→ The full 2×2 density matrix ρ = |+⟩⟨+| with all entries = 0.5

🔍 Stabilizer tableau (Bell pair)

let s = stabilizer_new(2, "pure");
let s = stabilizer_h(s, 0);
let s = stabilizer_cnot(s, 0, 1);
quantum_inspect(s)
{ _backend: "pure", _type: "stabilizer", n: 2,
  x: [[3], [0], [0], [2], [0]],   z: [[0], [3], [1], [0], [0]],   phase: [0, 0, 0, 0, 0] }

→ Raw Gottesman-Knill tableau: X/Z bit arrays packed in u64 words. x=[3] means bits 11 = both qubits in X part of stabilizer.

06 What Pure CJC Gives You: Evolution Tracing

Track how quantum state degrades through noise — step by step.

Purity Degradation Through Depolarizing Noise

Start with a pure state (purity = 1.0), apply a Hadamard gate, then successive depolarizing channels.

1.0 0.8 0.6 0.4 0.2 |0⟩ H gate +10% depol +20% depol +30% depol 1.000 1.000 0.876 0.702 0.573 pure state mild noise approaching maximally mixed
Why this matters: With the Pure CJC backend, you can track purity at every step and understand exactly where your quantum algorithm loses coherence. The Rust backend gives you the final answer — fast — but you can't see the journey.

07 Architecture

The dual-mode dispatch layer automatically routes to the correct backend.

CJC Program dispatch_quantum(name, args) "pure" flag? no / default yes / "pure" Rust Backend Optimized LAPACK SVD SIMD-ready kernels Zero-copy COW buffers Kraus operator channels Best for: Production Pure CJC Backend Jacobi one-sided SVD Transparent CJC arrays quantum_inspect() support Direct matrix noise Best for: Research

08 Four Quantum Paradigms, Two Backends Each

Every paradigm runs on both backends with identical physics.

💠

Circuit / Statevector

≤ 26 qubits

Full amplitude vector

qubits(n)
qubits(n, "pure")
🔗

MPS / Tensor Network

50+ qubits

Bond-dim compressed

mps_new(n, χ)
mps_new(n, χ, "pure")
🧊

Stabilizer / CHP

1000+ qubits

Clifford circuits only

stabilizer_new(n)
stabilizer_new(n, "pure")
🌫

Density Matrix

≤ 12 qubits

Noise & mixed states

density_new(n)
density_new(n, "pure")

09 When to Use Which

Use Rust Backend When...

  • • Running production VQE/QAOA optimization
  • • Simulating 50+ qubit circuits
  • • Benchmarking against other simulators
  • • Training quantum ML models
  • • You need maximum throughput

🔬 Use Pure CJC Backend When...

  • • Teaching quantum computing concepts
  • • Debugging a quantum algorithm
  • • Prototyping custom gate decompositions
  • • Understanding how MPS truncation works
  • • You need to see the state at every step

10 By The Numbers

7
Native quantum types in the type system
60+
Typed function signatures
718
Tests passing, 0 regressions
0
External dependencies
2
Backends, one API