PySparQ.pysparq.conformance¶
Reusable semantic conformance harness for PySparQ built-in operators.
Stage 1 of the native QECC.Lang / QFVM plan requires every PySparQ primitive
accelerated for use by QECC.Lang / quantum-cfd-software to pass a shared
conformance matrix before it may be relied upon as a leaf semantics for a
reversible xor_into or inplace_bijective contract (see
pysparq.dynamic_operator module docstring and README for the contract
vocabulary). This module provides that matrix as small, composable
assertions so individual test files stay short and declarative.
The matrix covers:
basis exhaustive / arbitrary nonzero targets —
build_forward_map()runs the operator on every (or a spot-checked sample of) classical basis input and records the resulting output tuple;collisions —
build_forward_map()(andassert_no_collisions()) fail loudly if two distinct inputs map to the same output tuple over the full set of touched registers. This is exactly the bug class described for non-conformantcompile_operatorcallbacks that "overwrite outputs" instead of computing a genuine bijection / XOR-into map;superposition linearity —
assert_superposition_linearity()builds a real, coherent equal-amplitude superposition (viaHadamard_Int) over every swept input, applies the operator once, and checks that each surviving branch agrees with the basis-by-basis reference map with the correct, unchanged amplitude magnitude and branch count. This catches implementations that behave correctly in isolation but corrupt or cross-talk between branches when several coexist;controls —
assert_controls()exercisesconditioned_by_nonzeros/conditioned_by_all_onesin the positive (condition true), negative (condition false => identity), and multi-register conjunction configurations already provided by everyClassControllableC++ operator;forward/dagger identity —
assert_forward_dagger_identity()andassert_dagger_forward_identity()check that applying the operator and its adjoint in either order returns the state to its starting values for arbitrary (not just zero) starting register contents.
Everything in this module operates on named registers pre-declared once via
setup_registers(), then exercised across many independent
SparseState instances — mirroring the AddRegister(...)(state) /
Init_Unsafe(...)(state) idiom already used throughout
pysparq/algorithms.
警告
pysparq.dynamic_operator.compile_operator() produces an arbitrary,
runtime-compiled C++ operator. Compilation only checks that the supplied
operator()/dag() pair type-checks; it can neither statically nor
dynamically prove the pair is unitary or mutually inverse. This harness
is therefore intentionally restricted to named, statically inspectable
PySparQ built-ins (and Python composites built from them) — it cannot
"bless" a dynamically compiled operator, and dynamically compiled
operators must not be used on the supported QCFD path (see
pysparq/dynamic_operator/README.md).
Attributes¶
Classes¶
Declares one register participating in a conformance check. |
Functions¶
Re-check collision-freeness with the output register(s) seeded at |
|
|
Check control-gated behavior: identity when off, action when on. |
|
Check |
|
Check |
|
Re-check an already-built forward map for output collisions. |
|
Verify linearity: one coherent call must equal per-branch reference. |
|
Apply |
|
Build a fresh, single-branch basis state with the given register values. |
|
Read the (masked) values of |
|
Return the values to sweep for a register of the given width. |
|
Clear the global |
|
Sign-extend a bit pattern per the |
|
Decode a two's-complement bit pattern of the given width. |
|
Run the full conformance matrix across a set of width combinations. |
Module Contents¶
- class PySparQ.pysparq.conformance.RegisterSpec[源代码]¶
Declares one register participating in a conformance check.
- PySparQ.pysparq.conformance.assert_collision_free_for_output_starts(make_op: Callable[[], pysparq.BaseOperator], touched: Sequence[str], masks: Mapping[str, int], sweep: Mapping[str, Iterable[int]], output_start_values: Mapping[str, Iterable[int]]) None[源代码]¶
Re-check collision-freeness with the output register(s) seeded at several arbitrary (including nonzero) starting values.
For a genuine
xor_intoleaf,out_new = out_old XOR f(inputs)is a bijection oninputsfor any fixedout_old. Only probing with a clean (zero) starting output — as a singlebuild_forward_map()call conventionally does — cannot distinguish a real XOR-into implementation from one that discards the incoming output value and simply overwrites it withf(inputs): the two agree whenout_old == 0but diverge for any other starting value. This function makes that distinction part of the conformance matrix by rebuilding the forward map (and therefore re-runningbuild_forward_map()'s collision check) once per combination ofoutput_start_values.- 参数:
output_start_values -- one entry per xor_into output register, mapping its name to the (ideally including at least one nonzero) starting values to probe, e.g.
{"c": [0, 1, 5, 7]}.
- PySparQ.pysparq.conformance.assert_controls(make_op: Callable[[], pysparq.BaseOperator], touched: Sequence[str], masks: Mapping[str, int], control_specs: Sequence[RegisterSpec], active_values: Mapping[str, int], inactive_values: Mapping[str, int], fixed: Mapping[str, int] | None = None, conditioned_by: str = 'nonzeros') None[源代码]¶
Check control-gated behavior: identity when off, action when on.
Exercises single controls (one register at a time) as well as the full multi-register conjunction (all controls active together, and each one individually inactive while the others are active — the negative-control cases required by the matrix).
conditioned_byselectsconditioned_by_nonzerosorconditioned_by_all_ones.
- PySparQ.pysparq.conformance.assert_dagger_forward_identity(make_op: Callable[[], pysparq.BaseOperator], touched: Sequence[str], masks: Mapping[str, int], sweep: Mapping[str, Iterable[int]], fixed: Mapping[str, int] | None = None) None[源代码]¶
Check
op(op.dag(state)) == statefor every swept input.
- PySparQ.pysparq.conformance.assert_forward_dagger_identity(make_op: Callable[[], pysparq.BaseOperator], touched: Sequence[str], masks: Mapping[str, int], sweep: Mapping[str, Iterable[int]], fixed: Mapping[str, int] | None = None) None[源代码]¶
Check
op.dag(op(state)) == statefor every swept input.Uses arbitrary (not just zero) starting values for every touched register, per the Stage 1 conformance matrix.
- PySparQ.pysparq.conformance.assert_no_collisions(forward_map: Mapping[tuple, tuple]) None[源代码]¶
Re-check an already-built forward map for output collisions.
Useful when the map was built once and reused by several assertions.
- PySparQ.pysparq.conformance.assert_superposition_linearity(make_op: Callable[[], pysparq.BaseOperator], touched: Sequence[str], masks: Mapping[str, int], hadamard_regs: Sequence[tuple[str, int]], fixed: Mapping[str, int] | None = None, forward_map: Mapping[tuple, tuple] | None = None) None[源代码]¶
Verify linearity: one coherent call must equal per-branch reference.
Builds a genuine equal-amplitude superposition over every combination of the registers in
hadamard_regs(each entry is(name, width)) usingHadamard_Int, appliesmake_op()exactly once, and checks that the branch count, per-branch amplitude magnitude, and per-branch output all agree withforward_map(built withbuild_forward_map()over the same sweep/fixed values if not supplied).
- PySparQ.pysparq.conformance.build_forward_map(make_op: Callable[[], pysparq.BaseOperator], touched: Sequence[str], masks: Mapping[str, int], sweep: Mapping[str, Iterable[int]], fixed: Mapping[str, int] | None = None) dict[tuple, tuple][源代码]¶
Apply
make_op()to every swept basis input and record the result.touchedmust list every register the operator reads or writes (inputs and outputs alike).sweepgives the register(s) whose value is varied;fixedgives the starting value for any other touched register (defaults to 0, i.e. a clean output/work register).重要
For an
xor_intoleaf (out_new = out_old XOR f(inputs)), collision-freeness must hold for every starting value of the output register(s), not only the conventional clean/zero-ancilla start. Calling this function once with the output left at its default (0) is necessary but not sufficient: an implementation that discards/overwrites the incoming output value (rather than genuinely XORing into it) can still happen to look collision-free when the probe always starts from a clean register. Useassert_collision_free_for_output_starts()to additionally sweep arbitrary (including nonzero) starting output values.Returns a dict mapping the full input tuple (over
touched, in order) to the full output tuple. RaisesAssertionErrorif:the operator turns a basis state into a superposition (a classical leaf must map one basis state to exactly one basis state), or
two distinct inputs collide onto the same output tuple (the destructive-overwrite bug class this harness exists to catch).
- PySparQ.pysparq.conformance.make_basis_state(values: Mapping[str, int]) pysparq.SparseState[源代码]¶
Build a fresh, single-branch basis state with the given register values.
Registers not present in
valuesare left at their default (zero).
- PySparQ.pysparq.conformance.read_registers(state: pysparq.SparseState, names: Sequence[str], masks: Mapping[str, int], branch: int = 0) tuple[源代码]¶
Read the (masked) values of
namesfrom one branch ofstate.
- PySparQ.pysparq.conformance.sample_values(width: int, *, max_exhaustive: int = 5, samples: int = 12, rng: random.Random | None = None) list[int][源代码]¶
Return the values to sweep for a register of the given width.
Widths up to
max_exhaustivebits are covered exhaustively (basis exhaustive coverage). Wider registers are spot-checked withsamplespseudo-random values (arbitrary nonzero output targets), always including 0, 1, and the all-ones value so edge cases are never skipped.
- PySparQ.pysparq.conformance.setup_registers(specs: Sequence[RegisterSpec]) None[源代码]¶
Clear the global
Systemschema and (re)declare every register.Must be called once before creating any
SparseStateused by the checks in this module. IndividualSparseStateinstances created afterwards do not need to repeatAddRegister— the fixed-size per-branch register array already reserves every declared slot at zero, soInit_Unsafecan be used directly on a fresh state.
- PySparQ.pysparq.conformance.sign_extend(value: int, width: int) int[源代码]¶
Sign-extend a bit pattern per the
_SInt_slot rule.
- PySparQ.pysparq.conformance.two_complement_decode(value: int, width: int) int[源代码]¶
Decode a two's-complement bit pattern of the given width.
Mirrors the SparQ
get_complementread used by_SInt_slots.
- PySparQ.pysparq.conformance.width_matrix_case(*, label: str, specs_factory: Callable[[tuple[int, ...]], Sequence[RegisterSpec]], make_op: Callable[[Mapping[str, int]], pysparq.BaseOperator], model: Callable[[Mapping[str, int], Mapping[str, int]], Mapping[str, int]], input_names: Sequence[str], output_names: Sequence[str], width_combos: Sequence[tuple[int, ...]], max_exhaustive_pairs: int = 4096, sampled_pairs: int = 48, superposition_max_bits: int = 6, control_case: tuple[tuple[int, ...], Sequence[RegisterSpec], Mapping[str, int], Mapping[str, int]] | None = None, rng: random.Random | None = None) None[源代码]¶
Run the full conformance matrix across a set of width combinations.
Implements the reversibility coverage required by the width and truncation conventions: for every combo in
width_combos(a tuple of widths, one per register in the orderspecs_factoryexpects):model check — the forward map (basis exhaustive when the swept input space is small, sampled otherwise, always including 0/1/all-ones edge values) must equal
model(values, widths)XOR-ed into the starting output values, with inputs untouched;collision check at nonzero output starts — the
xor_intobijection must hold for arbitrary starting output values;dagger identity in both orders (self-adjoint ops:
dag == call);superposition linearity for combos whose swept input bits fit
superposition_max_bits;controls once per call when
control_caseis provided.
model(values, widths)returns a mapping of output-name -> increment (the value XOR-ed into an initially-zero output register);make_opreceives the per-register widths (name -> width) and constructs the operator under test.