quchip.chip¶
Chip topology — the composite quantum system and its two-body couplings.
A Chip bundles devices, couplings, and (optionally) control
equipment into a single composite system that the engine can assemble
into a solver-ready problem. Dressed-state analysis lives in
quchip.chip.analysis and is attached to every chip as
chip._analysis (exposed via the chip’s public methods).
- class quchip.chip.Chip(devices, couplings=None, control_equipment=None, label=None, frame='lab', approximation=RWA(keep_bands=None), basis='native', backend=None, baths=None, ports=None)[source]¶
Bases:
objectComposite quantum system: devices + couplings + (optional) control.
The chip is the primary user-facing object. It exposes:
Hamiltonian construction (
hamiltonian()),dressed-state analysis (
dress(),energy(),freq(), …) delegated toChipAnalysis,state factories (
state(),bare_state()),observable construction (
observable(),e_ops()),solver surface (
solve(),solve_many(),steadystate()),serialization / cloning (
to_dict(),from_dict(),clone(),updated()).
Methods that accept a device reference take either a device object or its label string; object references are preferred in examples.
- Parameters:
devices (list[BaseDevice]) – Ordered device list. Tensor-product position equals list index; labels must be unique.
couplings (list[BaseCoupling], optional) – Two-body couplings. Each coupling’s referenced devices must be in
devices.control_equipment (ControlEquipment, optional) – Aggregates drive lines and signal-chain transforms (crosstalk, delays, gains). Can also be attached later via
wire()orconnect().label (str, optional) – Human-readable chip label.
frame (FrameSpec) –
Initial frame specification:
"lab"— all reference frequencies 0 GHz (default)."rotating"— per-device rotating frame at dressed drive frequencies.scalar-like — one shared reference frequency for all devices.
dict— per-device references keyed by label or device.
approximation (Approximation) – Engine strategy applied after the complete authored Hamiltonian is assembled. Defaults to
RWA.basis ({"native", "eigen"}) – Chip-wide local solver-basis policy.
"native"preserves each device’s authored coordinate basis;"eigen"transforms into its retained local energy subspace. A device-levelbasisoverrides this policy.backend (str or Backend, optional) – Chip-specific backend.
Noneuses the process default.baths (list[Bath], optional) – Shared or collective unobserved environments.
ports (list[Port], optional) – Accessible Markovian input-output channels. Ports add collapse channels without adding Hilbert-space factors.
Examples
>>> from quchip import DuffingTransmon, Resonator, Capacitive, Chip >>> q = DuffingTransmon(freq=5.0, anharmonicity=-0.25, levels=3, label="q") >>> r = Resonator(freq=7.0, levels=5, label="r") >>> chip = Chip([q, r], couplings=[Capacitive(q, r, g=0.05)]) >>> chip.energy({q: 1}) # dressed |1,0⟩ eigenvalue, GHz
- unresolved_hamiltonian()[source]¶
Return the authored lab-frame static Hamiltonian.
Embeds every device Hamiltonian into the full tensor space and adds each coupling’s embedded interaction. Does not apply the rotating-frame transform or any drive envelopes.
This is the exact authored lab-frame Hamiltonian. RWA and frame transformations are applied only inside the engine. At solve time, the engine subtracts
2π Σ_i ω_ref,i n̂_ifor each device, whereω_ref,iis the frame reference resolved byquchip.engine.frames.resolve_frame(). The 2π boundary crossing and the subtraction both live inquchip.engine.assembly._build_static_h0(). Useframe_info()to inspect which reference frequency each device will use.- Returns:
Symbolic Hamiltonian on
⨂_d H_d. Call.matrix()for a dense numerical view using current bindings.- Return type:
- resolve(*, frame=None, approximation=None)[source]¶
Return a frozen engine contract without mutating chip intent.
frame=Noneusesframe; an explicit frame resolves this snapshot only.approximation=Nonelikewise uses the chip default. Neither override mutates chip intent.- Parameters:
frame (FrameSpec | None)
approximation (Approximation | None)
- Return type:
- dynamic_contributions()[source]¶
Chip-owned time-dependent Hamiltonian contributions with their support.
Returns
(local_op, time_dependence, support, owner, origin, tag)tuples: one support index for a device-local operator, two for a coupling’s two-body operator. Operators are lab-frame, ordinary GHz — the engine applies the 2π boundary. Drive terms are not included; they are schedule-owned and enter through engine assembly’s drive compilation.
- collapse_contributions(bases=None)[source]¶
Every Lindblad collapse operator on the chip, with its support.
Returns
(operator, rate, support, source, channel, parameter_paths)tuples: one device index for a device- or drive-line-local operator, two for a coupling’s two-body operator, and an empty tuple for an operator already embedded in the full space (baths). Rates are in 1/ns, Lindblad-ready — each component owns its rate physics, including any intrinsic 2π (e.g. a resonator’s κ = 2π·f/Q).Every returned operator is authored locally and transformed by the engine into the same fixed local solver bases as the Hamiltonian. This is the standard local-Lindblad approximation (Breuer & Petruccione, The Theory of Open Quantum Systems, Oxford, 2002, Ch. 3) rather than a dressed-basis (polaron-frame) master equation, and applies chip-wide regardless of which components carry noise — see the
"chip"entry ofphysics_notes().
- property device_map: dict[str, BaseDevice]¶
Label → device mapping (the chip’s own dict; do not mutate).
- property coupling_map: dict[str, BaseCoupling]¶
Couplings by label, insertion-ordered (do not mutate).
- coupling(coupling)[source]¶
Return a coupling by label or object.
- Parameters:
coupling (str | BaseCoupling)
- Return type:
- property backend: Backend¶
per-call override > chip-specific > process default.
The per-call override is the
backend=argument ofsimulate()/simulate_batch(scoped throughquchip.backend._backend_context()); it outranks even a chip-constructed backend so one chip can serve, e.g., QuTiP sweeps and dynamiqs gradient solves without global state flips.- Type:
Active backend
- property frame: FrameSpec¶
Current frame specification (see
set_frame()).
- property approximation: Approximation¶
Default engine approximation strategy.
- property control_equipment: ControlEquipment | None¶
Attached control equipment, if any.
- property devices: tuple[BaseDevice, ...]¶
Ordered tuple of devices; index matches tensor-product position.
- property couplings: tuple[BaseCoupling, ...]¶
Tuple of couplings in insertion order.
- property basis: Literal['native', 'eigen']¶
Chip-wide local solver-basis policy inherited by devices.
- resolve_basis(device)[source]¶
Resolve a device override against the chip basis policy.
- Parameters:
device (str | BaseDevice)
- Return type:
Literal[‘native’, ‘eigen’]
- property baths: tuple[Bath, ...]¶
Chip-level baths (shared/collective dissipation), insertion order.
- add_bath(bath)[source]¶
Attach a bath to this chip and return it (for fluent use).
Baths may be added at any time after construction — the next simulate/solve collects the bath’s collapse operators automatically, no rebuild needed. The bath is validated immediately: a non-
Bathargument, a target label not on this chip, or a label colliding with an already-attached bath fails here rather than cryptically at solve time (or, for a label collision, silently overwriting an entry on thephysics_notes()audit surface).
- set_noise(config=None, *, baths=None)[source]¶
Replace this chip’s entire noise description in one call.
The call is the chip’s complete noise state: for every device, each noise parameter (see
noise_parameter_names()) is set from config when given and reset toNoneotherwise, and the chip’s baths become exactly baths (omitted → no baths).chip.set_noise()therefore clears all noise. Re-running the same call is a silent no-op, so notebook cells converge instead of stacking duplicate baths.Only dissipation knobs are reachable — a key that is not a noise parameter of that device (e.g.
freq) raises, so an optimized Hamiltonian cannot be perturbed by this call. The full target state is validated before anything is written (the same checks the constructors run); on error the chip is left exactly as it was. Applied changes are printed one per line; a no-op prints nothing.Custom dissipation is supported by declaring it on the device class beforehand with a
parameter(noise=True)rate field and adissipation()override. The declared rate is then an ordinary noise parameter here: sweepable, differentiable, serializable. Runtime closure-style channels are deliberately not supported — their rates could be neither swept, nor differentiated, nor serialized.- Parameters:
config (mapping, optional) –
{device_or_label: {noise_param: value}}. Devices may appear as objects or labels, once each.baths (list[Bath], optional) – The chip’s complete new bath list (validated like
add_bath()).
- Return type:
None
- device_index(label)[source]¶
Tensor-product index of a device. Accepts a label string or object.
- Parameters:
label (str | BaseDevice)
- Return type:
- plot_graph(path='chip_topology.html', *, full=True, exclude=None, values='bare', **kwargs)[source]¶
Render chip topology — delegates to
quchip.viz.chip.
- plot_energy_levels(*, ax=None, **kwargs)[source]¶
Render dressed spectrum — delegates to
quchip.viz.chip.
- set_frame(frame)[source]¶
Set the frame used when assembling simulation inputs.
Supported values:
"lab"— all reference frequencies are 0.0 GHz."rotating"— per-device references use dressed drive frequencies.scalar-like — shared reference frequency for all devices.
dict— per-device references keyed by label or device.
Frame changes never alter dressed-state data — dressing is always computed from the lab-frame static Hamiltonian.
- Parameters:
frame (FrameSpec)
- Return type:
None
- property analysis: ChipAnalysis¶
Dressed-state analysis namespace — the chip’s
ChipAnalysis.Canonical entry point for the full dressed-analysis surface (power users, less-common methods). The common quantities are also exposed as flat
chip.*forwarders —energy(),freq(),dress(),dispersive_shift(), … — which delegate here; reach forchip.analysisfor everything else.
- dress(*, overlap_threshold=0.5, force=False, labeling='DE')[source]¶
Compute (or retrieve) the dressed-state decomposition. See
ChipAnalysis.dress().- Parameters:
- Return type:
- property is_dressed: bool¶
Whether a valid dressed-state result is cached. See
ChipAnalysis.is_dressed.
- energy(device_states=None, /, **device_state_kwargs)[source]¶
Dressed eigenenergy (GHz) for a bare-state label. See
ChipAnalysis.energy().
- dressed_spectrum()[source]¶
Raw dressed eigenvalue array without Python scalar coercion. See
ChipAnalysis.dressed_spectrum().- Return type:
- dressed_index(device_states=None, /, **device_state_kwargs)[source]¶
Dressed-state index matching a bare-state label, or
None. SeeChipAnalysis.dressed_index().
- bare_label(dressed_index)[source]¶
Bare-state label assigned to a dressed-state index. See
ChipAnalysis.bare_label().
- operator_in_dressed_basis(device, op, *, truncate=None)[source]¶
Embedded device operator transformed to the dressed eigenbasis.
See
ChipAnalysis.operator_in_dressed_basis().
- drive_matrix_elements(transition, *, drives=None)[source]¶
Return
<final~|D_j|initial~>for wired drive lines.The final dressed state is the row index and the initial dressed state is the column index. In the weak-drive projection these matrix elements set the effective driven-Hamiltonian coefficients. See E. Magesan and J. M. Gambetta, Phys. Rev. A 101, 052308 (2020), DOI 10.1103/PhysRevA.101.052308, and
ChipAnalysis.drive_matrix_elements()for the transition shorthand, parameters, return type, and error conditions.- Parameters:
transition (str | BaseDevice | tuple[Mapping[str | BaseDevice, int], Mapping[str | BaseDevice, int]])
- Return type:
- state_components(state=None, /, *, n_components=5, **device_state_kwargs)[source]¶
Leading bare-basis probabilities for a dressed eigenstate. See
ChipAnalysis.state_components().
- dispersive_shift(device_a, device_b)[source]¶
Dressed cross-Kerr shift (GHz):
E(1,1) − E(1,0) − E(0,1) + E(0,0).See
ChipAnalysis.dispersive_shift().- Parameters:
device_a (str | BaseDevice)
device_b (str | BaseDevice)
- Return type:
- static_zz(device_a, device_b)¶
Dressed cross-Kerr shift (GHz):
E(1,1) − E(1,0) − E(0,1) + E(0,0).See
ChipAnalysis.dispersive_shift().- Parameters:
device_a (str | BaseDevice)
device_b (str | BaseDevice)
- Return type:
- zz(device_a, device_b)¶
Dressed cross-Kerr shift (GHz):
E(1,1) − E(1,0) − E(0,1) + E(0,0).See
ChipAnalysis.dispersive_shift().- Parameters:
device_a (str | BaseDevice)
device_b (str | BaseDevice)
- Return type:
- kerr_matrix()[source]¶
Return the labeled dressed self-Kerr and cross-Kerr matrix in GHz.
See
ChipAnalysis.kerr_matrix().- Return type:
- dressed_anharmonicity(device)[source]¶
Dressed anharmonicity of one device with others grounded (GHz).
See
ChipAnalysis.dressed_anharmonicity().- Parameters:
device (str | BaseDevice)
- Return type:
- transition_frequency(target, lower, upper, when=None)[source]¶
Return a dressed transition in GHz with optional spectator levels.
Unspecified spectators are in their ground state.
targetand entries inwhenaccept either device objects or labels.- Parameters:
target (str | BaseDevice)
lower (int)
upper (int)
when (dict[str | BaseDevice, int] | None)
- Return type:
- effective_subspace_hamiltonian(states)[source]¶
Dressed effective Hamiltonian in a labeled bare subspace.
See
ChipAnalysis.effective_subspace_hamiltonian().
- freq(target: None = None, when: dict[str | BaseDevice, int] | None = None) dict[str, float][source]¶
- freq(target: str | BaseDevice, when: dict[str | BaseDevice, int] | None = None) float
All dressed 0→1 frequencies (GHz), or one conditional transition. See
ChipAnalysis.freq().Overloaded: no
targetreturns the full{label: freq}dict; a singletarget(label or device) returns one scalar 0→1 frequency. Underjax.jitthe scalar is a traced 0-d array; the overload is type-only and preserves traceability.- Parameters:
target (str | BaseDevice | None)
when (dict[str | BaseDevice, int] | None)
- Return type:
- frame_info()[source]¶
Per-device frame reference frequency
ω_ref,i(GHz). SeeChipAnalysis.frame_info().
- physics_notes()[source]¶
Aggregate
physics_notes()across every component.Returns a dict keyed
"chip"for the chip-level entry, and"<kind>:<label>"—kindone of"device","coupling","drive","bath","port"— for every component, mapping to that component’s declared approximations: Hilbert truncation, model regime, RWA status, noise-channel selection, and any other non-obvious assumption the component explicitly declares. Keys are kind-qualified rather than bare labels because the label namespaces are not globally disjoint — a device, coupling, drive, and bath may share a label — and this is an audit surface, so one component’s entry silently overwriting another’s is unacceptable. Drives are enumerated fromcontrol_equipment’s wiring rather than per-deviceconnected_drives, so an edge-targetParametricDrive(pumping a coupling, not a device) is included too. The chip-level entry keyed"chip"states the local-Lindblad approximation every collapse operator this chip assembles is built under (seecollapse_contributions()) — present even with no baths, since it applies regardless. Intended for inspection/audit rather than for runtime dispatch.
- property settings: Mapping[str, Any]¶
Read-only structural choices that are not numerical fit parameters.
- with_params(bindings)[source]¶
Return an isolated structural copy with component-owned values rebound.
- partition()[source]¶
Split into independent sub-chips along the independence graph.
Couplings, non-separable bath target sets, and drive-crosstalk pairs all count as connections. Exact — the joint solve factorizes as the tensor product of the component solves.
simulate/seq.simulateconsult this automatically; call it directly to orchestrate solves yourself.- Return type:
- from_array(data, device=None)[source]¶
Build a backend operator from a raw NumPy array.
With device, the array is interpreted as a local operator on that device’s subspace and embedded into the full tensor-product space. With
device=Nonethe array must already span the full chip Hilbert space.- Parameters:
data (Any)
device (str | BaseDevice | None)
- Return type:
- observable(device, op)[source]¶
Embed a device operator onto the full chip Hilbert space.
Accepts either an operator name (
"X","Y","Z","n","a","a_dag","I") or an already-built local-space operator, and returns it embedded on the chip’s tensor-product space.This is for manual full-space operator construction and analysis; it is not a solver
e_op. For solver expectation values usee_ops(), which keeps operators local so the demodulation pipeline can band-decompose and embed them correctly.- Parameters:
device (str | BaseDevice)
- Return type:
- e_ops(*, correlators=None, **specs)[source]¶
Build a dict-form
e_opsmapping for the solver pipeline.Each keyword maps a device label to an operator specification: a name string, a list of names, a raw local-space operator, or a mixed list of strings and operators. Two-device correlators (e.g.
⟨Z₁⊗Z₂⟩) are specified via correlators as device-label pairs → operator pairs. Returns local-space operators (not embedded) — the demodulation pipeline embeds as needed.Examples
>>> from quchip import DuffingTransmon, Capacitive, Chip >>> q1 = DuffingTransmon(freq=5.0, anharmonicity=-0.25, levels=3, label="q1") >>> q2 = DuffingTransmon(freq=5.2, anharmonicity=-0.22, levels=3, label="q2") >>> chip = Chip([q1, q2], couplings=[Capacitive(q1, q2, g=0.02)]) >>> e = chip.e_ops( ... q1=["X", "Y", "Z"], q2=["X", "Y", "Z"], ... correlators={("q1", "q2"): ("Z", "Z")}, ... )
- set_state_order(*devices, levels=None)[source]¶
Declare the device order used to parse string-state shorthands.
After this is called,
bare_state(),state(), andsuperposition()accept single-string specifications where each character is one level per device in devices order. Level symbols default tog=0, e=1, f=2, h=3; digits0..9are always accepted as energy-level indices.Every chip device must be named exactly once.
Examples
>>> from quchip import DuffingTransmon, Resonator, Chip >>> qb = DuffingTransmon(freq=5.0, anharmonicity=-0.25, levels=3, label="qb") >>> tc = DuffingTransmon(freq=5.5, anharmonicity=-0.20, levels=3, label="tc") >>> cr = Resonator(freq=7.0, levels=4, label="cr") >>> chip = Chip([qb, tc, cr]) >>> chip.set_state_order(qb, tc, cr) >>> _ = chip.bare_state("eg1") # {qb: 1, tc: 0, cr: 1}
- Parameters:
devices (str | BaseDevice)
- Return type:
None
- superposition(*components)[source]¶
Normalized bare-basis superposition of tensor-product states.
Each component is either a bare-state spec (dict keyed by device or label, or a string when
set_state_order()has been called) or an(amplitude, spec)tuple for weighted mixing. Uniform weights by default; results are normalized to unit norm.Unlike
state(), this stays in the bare product basis — no dressed diagonalization — so the probe basis is explicit.Examples
>>> import numpy as np >>> from quchip import DuffingTransmon, Resonator, Chip >>> qb = DuffingTransmon(freq=5.0, anharmonicity=-0.25, levels=3, label="qb") >>> cr = Resonator(freq=7.0, levels=4, label="cr") >>> chip = Chip([qb, cr]) >>> _ = chip.superposition({qb: 0}, {qb: 1}) # equal |00> + |10> >>> _ = chip.superposition( # weighted mix ... (np.sqrt(0.3), {qb: 1, cr: 0}), ... (np.sqrt(0.7), {qb: 1, cr: 1}), ... )
- state(device_states=None, /, **device_state_kwargs)[source]¶
Dressed eigenstate assigned from the given product-state level labels.
Accepts a string shorthand (e.g.
"eg1") whenset_state_order()has been called.Safe inside
jax.jit/grad/vmap: under tracing the assigned eigenvector column is selected through thelabel_eigensystem()array kernel, so dressed initial states are differentiable end-to-end. The global phase is gauge-dependent (eighcolumn convention) — populations and|overlap|figures of merit are unaffected.
- bare_state(device_states=None, /, **device_state_kwargs)[source]¶
Product state from per-device energy levels or authored local kets.
Each device may be specified as either an energy-level index (
int) or a ket vector in that device’s authored local space. Devices not mentioned default to the ground state (level 0). Unlikestate()this does not diagonalize the coupled system.Accepts a string shorthand (e.g.
"eg1") whenset_state_order()has been called.
- wire(*lines, signal_chain=None)[source]¶
Attach or replace classical control wiring.
Preferred user-facing API for attaching control to a chip. If lines is omitted, the existing connected lines are reused and only the signal chain is replaced.
Examples
>>> # chip.wire(drive_q, drive_r, signal_chain=[Crosstalk(drive_q, drive_r, c=0.05)])
- Parameters:
lines (BaseDrive)
signal_chain (Sequence[SignalTransform] | None)
- Return type:
- unwire(line)[source]¶
Remove one control line and every signal-chain transform referencing it.
The inverse of
wire()for a single line. Accepts the drive object or its label. Returns the removed drive so it can be rewired later. Removing the last line detaches the equipment entirely (control_equipmentbecomesNone).
- connect(control_equipment)[source]¶
Attach control equipment to this chip (low-level API).
Validates every drive target and rejects duplicate drive labels, then reconnects each drive to this chip’s canonical device or coupling instance. User-facing code should prefer
wire().- Parameters:
control_equipment (ControlEquipment)
- Return type:
None
- disconnect()[source]¶
Detach control equipment entirely (low-level API).
The inverse of
connect()/wire(): removes all lines and the signal chain at once (control_equipmentbecomesNone). Returns the detached equipment so it can be reconnected later.- Returns:
The equipment that was attached before detachment.
- Return type:
- solve(problem, *, check_truncation=True, truncation_threshold=0.001)[source]¶
Solve a typed
SolveProblemthrough this chip’s backend.Routes through the common
solve_problem()chokepoint, so the Hilbert-truncation safety net applies by default; passcheck_truncation=Falseto opt out or retunetruncation_threshold.- Parameters:
problem (SolveProblem)
check_truncation (bool)
truncation_threshold (float)
- Return type:
- solve_many(batch_or_problems, *, progress=True)[source]¶
Solve a
SolveBatchor list of problems.Chip-level validation only enforces what needs
self(every input was built for this chip); the input-shape dispatch and batching are delegated toquchip.engine.solve_many(), which owns the single SolveBatch / list dispatch.- Parameters:
batch_or_problems (Any)
progress (bool)
- Return type:
- steadystate(*, e_ops=None, options=None, frame=None, approximation=None)[source]¶
Solve this chip’s unique static Lindblad steady state.
- Parameters:
e_ops (dict | None)
options (dict | None)
frame (FrameSpec | None)
approximation (Approximation | None)
- Return type:
- steadystate_batch(*axes, e_ops=None, options=None, frame=None, approximation=None, progress=True)[source]¶
Solve static Lindblad steady states over parameter sweep axes.
- Parameters:
axes (Any)
e_ops (dict | None)
options (dict | None)
frame (FrameSpec | None)
approximation (Approximation | None)
progress (bool)
- Return type:
Any
- describe()[source]¶
Sectioned plain-text report of everything on the chip.
Devices with their declared parameters (units included), noise settings, couplings, control wiring, and baths — the “what did I just build?” view. Returns a string;
print(chip.describe()). Traced parameters render as<traced>and are never concretized.- Return type:
- class quchip.chip.DressedResult(eigenvalues, state_map, dressed_eigenvalues, assignment_overlaps, hybridized_labels, bare_labels, bare_labels_by_dressed_index, eigenvector_matrix=None, overlap_threshold=0.5, labeling='DE', _eigensystem=None)[source]¶
Bases:
objectStore a frozen snapshot of a dressed-state diagonalization.
- Parameters:
eigenvalues (Any)
eigenvector_matrix (Any)
overlap_threshold (float)
labeling (str)
_eigensystem (EigensystemData | None)
- eigenvalues¶
Sorted dressed eigenvalues in GHz.
- Type:
array-like
- eigenstates¶
Backend eigenstate objects in the same order as
eigenvalues. Materialized lazily on first access from the underlyingEigensystemData— the dressing / sweep hot path never touches them, so the per-column backend kets are only built when a caller actually asks for states.- Type:
array-like
- state_map¶
Assignment from bare product-basis label (one int per device) to the dressed eigenstate index it overlaps most with.
- dressed_eigenvalues¶
Dressed eigenvalue for each assigned bare label — direct lookup path for
Chip.energy().
- assignment_overlaps¶
|⟨bare|dressed⟩|²of each assignment; values belowoverlap_thresholdflag hybridization.
- hybridized_labels¶
Bare labels whose assignment quality is below
overlap_threshold. A non-empty tuple triggers a user warning at dress time.
- bare_labels¶
Product energy-level labels exposed by the chip’s resolved local dimensions, in chip order.
- eigenvector_matrix¶
Columns = dressed eigenvectors in the bare product basis. Used for
ChipAnalysis.operator_in_dressed_basis()andChipAnalysis.state_components().- Type:
array-like or None
- labeling¶
Algorithm id (currently only
"DE"), resolved to the confidence-ordered row-greedy overlap-matching policy actually run byChipAnalysis.dress()(assign_rowwise_greedy()).- Type:
- class quchip.chip.KerrMatrix(labels, values)[source]¶
Bases:
objectLabeled dressed self-Kerr and cross-Kerr coefficients in GHz.
labelsfollows chip device order.valuesis a real symmetric square array: diagonal entries are dressed anharmonicities and off-diagonal entries are full-pull cross-Kerr shifts.
- class quchip.chip.Bath(recipe, targets=None, *, temperature=None, rate=None, correlated=False, label=None)[source]¶
Bases:
objectA shared environment coupling a set of devices to a common bath.
Attach at construction (
Chip(..., baths=[...])) or at any time after viaadd_bath()— the next simulate/solve collects the bath’s collapse operators automatically.- Parameters:
recipe (str) – Built-in collapse-channel model. One of
"thermal","collective_decay", or"correlated_dephasing". The argument name is retained for API and serialization compatibility.targets (list[BaseDevice | str] | None) – Devices the bath couples to (objects or labels).
None(default) means every device in the chip — natural for a global thermal bath.temperature (float | None) – Bath temperature in mK (required for
"thermal"). May be a JAX tracer for sweeps / gradients.rate (float | None) – Bath–device coupling rate γ in 1/ns. For
"thermal"it is the environmental coupling rate (explicit — never silently borrowed from a deviceT1, so it cannot double-count device-level noise). For the collective models it is the overall jump rate.Nonedefaults to1.0(user controls the absolute scale elsewhere).correlated (bool) –
"thermal"only:False(default) emits independent per-device channels sharing one temperature.Trueis unsupported and raisesNotImplementedError. The collective models always emit a single correlated operator regardless of this flag.label (str | None) – Auto-generated
"bath_{n}"when omitted.
Examples
>>> from quchip import DuffingTransmon, Chip, Bath >>> q = DuffingTransmon(freq=5.0, anharmonicity=-0.25, levels=3, label="q") >>> chip = Chip([q]) >>> _ = chip.add_bath(Bath("thermal", temperature=20.0)) # global 20 mK bath >>> _ = chip.add_bath(Bath("collective_decay", targets=[q], rate=0.01))
- property separable: bool¶
Whether this bath factorizes into independent per-target channels.
Truefor models that emit one collapse operator per target ("thermal"with independent channels);Falsefor models that emit a single jump operator summed over targets ("collective_decay","correlated_dephasing"). Partitioning treats a non-separable bath’s target set as one inseparable block.
- classmethod from_dict(d)[source]¶
Reconstruct a bath from serialized state (targets as label strings).
- physics_notes()[source]¶
Return human-readable declarations of this bath’s model and scope.
Mirrors
physics_notes(): one entry naming the model and its targets, plus a model-specific assumption a user of this bath should be aware of.
- copy()[source]¶
Independent copy of this bath (targets normalize to label strings).
Used by
Chip.cloneandeliminateso a transformed chip never shares liveBathobjects with its source — mutating one chip’s bath must not silently change another chip’s physics. Parameter values (temperature, rate) are carried by reference, so traced values stay traced.- Return type:
- dissipation(chip, bases=None)[source]¶
Return authored full-chip collapse channels.
"thermal"emits independent per-target relaxation/absorption pairs sharing one bath temperature (_bose()). The two collective models instead each emit a single jump operator summed over the resolved targets:"collective_decay":L = sum_i a_iat rategamma— an equal-phase, equal-weight rank-one collective channel, not general collective (super/subradiant) decay, which requires per-pair phase and weight factors set by the target geometry (Lehmberg, Phys. Rev. A 2, 883 (1970), for the general collective-radiative-decay construction)."correlated_dephasing":L = sum_i n_iat rategamma— maximally correlated common-mode dephasing (every target shares the identical dephasing fluctuation), not general correlated dephasing with a target-dependent correlation structure (Breuer & Petruccione, The Theory of Open Quantum Systems, Oxford, 2002, Ch. 3, for the general Lindblad construction).
Contributions remain backend-neutral; the engine projects and lowers them with the same basis records used for Hamiltonian terms.
- Parameters:
- Return type:
tuple[CollapseChannel, …]
- class quchip.chip.Port(target, *, rate=None, external_quality_factor=None, operator=None, phase=0.0, label=None)[source]¶
Bases:
objectOne accessible Markovian channel with a dimensionless coupling operator.
- Parameters:
target (Any | Sequence[Any])
rate (Any)
external_quality_factor (Any)
operator (Any)
phase (Any)
label (str | None)
- rate_value(chip)[source]¶
Return the external coupling rate in
1/ns.- Parameters:
chip (Chip)
- Return type:
Any
- class quchip.chip.Capacitive(device_a, device_b, g=unbound, *, label=None)[source]¶
Bases:
CouplingModelCapacitive (charge-charge) coupling between two devices.
The capacitive interaction between two electromagnetic modes takes the canonical dipole-dipole form in the raising/lowering basis:
Full form:
H_int = g · (a + a†)(b + b†)Band-RWA form:
H_int = g · (a†b + a b†)(derived, not authored)
The coupling authors only the full form;
RWAretaining theΔa + Δb == 0bands of it, which is exactlyg · (a†b + a b†). The RWA drops the counter-rotating termsa banda† b†, valid whenω_a + ω_b ≫ g— the sum-frequency condition that makes those terms fast-rotating and hence negligible. This is distinct from the dispersive condition|ω_a − ω_b| ≫ g, which instead governs whether the retained exchange termg · (a†b + a b†)can be treated perturbatively (seeTunableCapacitive/eliminate()for the dispersive reduction). Approximation is selected on the chip or for one solve, never on the coupling.- Parameters:
device_a (BaseDevice or str) – The two coupled devices, given as objects or label strings. Label-string references are late-bound via
Chip.device_b (BaseDevice or str) – The two coupled devices, given as objects or label strings. Label-string references are late-bound via
Chip.g (float) – Coupling strength in GHz. May be a traced JAX scalar for sweeps / autodiff.
label (str, optional) – Human-readable label; defaults to
"cap_{n}".
References
Blais et al., PRA 69, 062320 (2004), Eq. 11. Krantz et al., Appl. Phys. Rev. 6, 021318 (2019), §V.B. Blais et al., Rev. Mod. Phys. 93, 025005 (2021), §II.B.
Examples
>>> from quchip import DuffingTransmon, Resonator, Capacitive >>> q = DuffingTransmon(freq=5.0, anharmonicity=-0.25, levels=3, label="q") >>> r = Resonator(freq=7.0, levels=5, label="r") >>> coupling = Capacitive(q, r, g=0.05)
- default_fit_observable: ClassVar[str] = 'cross_kerr'¶
Observable represented by this coupling’s declared scalar when the enclosing chip is passed to
fit_a_dressas a dressed specification. Concrete coupling models override this when their inverse-design quantity is a dressed interaction observable.
- g: Any = Parameter(default=unbound, positive=False, nonnegative=False, serialize=True, unit='GHz', symbol='g', noise=False, kw_only=False, required=False)¶
- interaction(a, b, p)[source]¶
Return the full capacitive interaction
g * (a + a†)(b + b†).- Parameters:
- Return type:
- classmethod from_dict(d, device_a, device_b)[source]¶
Reconstruct a capacitive coupling from serialized state.
- Parameters:
device_a (BaseDevice)
device_b (BaseDevice)
- Return type:
- class quchip.chip.Coupling(device_a, device_b, g, *, op_a=None, op_b=None, interaction=None, label=None)[source]¶
Bases:
BaseCouplingGeneric two-body coupling with a user-supplied interaction.
Use this escape hatch when no concrete coupling class models the desired physics (inductive, longitudinal, cross-Kerr test forms, synthetic spin-spin couplings, photonics-style beam-splitters, …). The user supplies the operator structure; this class only provides the
gscaling, RWA pass-through, and bookkeeping.Two mutually exclusive modes:
Product form —
H_int = g · op_a(device_a) ⊗ op_b(device_b):Coupling(q, r, g=0.02, op_a=lambda d: d.number_operator(), op_b=lambda d: d.number_operator())
Callable form —
H_int = g · interaction(device_a, device_b, backend):Coupling(q, r, g=0.02, interaction=lambda a, b, bk: ( bk.tensor(bk.dag(a.lowering_operator()), b.lowering_operator()) + bk.tensor(a.lowering_operator(), bk.dag(b.lowering_operator())) ))
The selected chip approximation is applied to the complete user-supplied operator after authored physics is assembled.
- Parameters:
device_a (BaseDevice | str)
device_b (BaseDevice | str)
g (float)
op_a (Callable[[BaseDevice], Operator] | None)
op_b (Callable[[BaseDevice], Operator] | None)
interaction (Callable[[BaseDevice, BaseDevice, 'Backend'], Operator] | None)
label (str | None)
- classmethod from_dict(d, device_a, device_b)[source]¶
Reject deserialization because callables cannot be reconstructed.
- Parameters:
device_a (BaseDevice)
device_b (BaseDevice)
- Return type:
- class quchip.chip.CrossKerr(device_a, device_b, chi=unbound, *, label=None)[source]¶
Bases:
CouplingModelCross-Kerr (dispersive) coupling
H_int = χ · n̂_a n̂_b.The effective diagonal interaction left when an exchange coupling is reduced in the dispersive regime — the natural coupling for effective readout chips (qubit + resonator +
CrossKerrprobed by an ordinary charge line) and static-ZZ modelling. Diagonal in both endpoints, so the RWA and full forms coincide and the term is frame-trivial.Declared approximation: this is a uniform-pull model — one χ per edge, the same shift per endpoint excitation; per-level χ differences, dispersive breakdown at the critical photon number, and Purcell decay are not represented (fold Purcell into endpoint
T1viaeliminate()when it matters).- Parameters:
device_a (BaseDevice or str) – The two coupled devices, as objects or label strings.
device_b (BaseDevice or str) – The two coupled devices, as objects or label strings.
chi (float) – Cross-Kerr shift in GHz per excitation pair, sign included (convention: full pull
E₁₁ − E₁₀ − E₀₁ + E₀₀). May be a JAX tracer.label (str, optional) – Defaults to
"crosskerr_{n}".
- default_fit_observable: ClassVar[str] = 'cross_kerr'¶
Observable represented by this coupling’s declared scalar when the enclosing chip is passed to
fit_a_dressas a dressed specification. Concrete coupling models override this when their inverse-design quantity is a dressed interaction observable.
- chi: Any = Parameter(default=unbound, positive=False, nonnegative=False, serialize=True, unit='GHz', symbol='\\chi', noise=False, kw_only=False, required=False)¶
- interaction(a, b, p)[source]¶
Full form
χ · n̂_a n̂_b(diagonal; identical under RWA).- Parameters:
- Return type:
- class quchip.chip.TunableCapacitive(device_a, device_b, g_0=unbound, *, label=None)[source]¶
Bases:
CouplingModelCapacitive coupling with a scheduled parametric pump.
Effective two-body interaction with a static mean coupling strength:
\[H_{\text{int}} \;=\; g_0\,\hat Q_a\hat Q_b\]where \(\hat Q\) is each endpoint’s physical charge-like coupling operator (the position quadrature for a Fock model). The engine applies any requested RWA after local-basis materialization. \(g_0\) is the static coupling strength in GHz; it may be a JAX tracer and flows through
jax.grad()without concretization.Time-dependence is not a construction-time parameter: a
ParametricDrivewired onto this coupling schedules a pump δ(t) viapump(), multiplying the same operator structure the static term uses (parametric_interaction()).- Parameters:
device_a (BaseDevice) – The two coupled devices.
device_b (BaseDevice) – The two coupled devices.
g_0 (float) – Static (mean) coupling strength in GHz. May be a JAX tracer.
label (str, optional) – Human-readable label; defaults to
"tunable_cap_{n}".
Notes
The pump multiplies
parametric_interaction(); frame and RWA logic stay in the engine. A pump tone at the qubits’ difference frequency|ω_a − ω_b|activates the parametric beam-splitter / iSWAP exchange, while a tone at the sum frequencyω_a + ω_binstead activates two-mode-squeezing (a†b†) terms. Either is expressed via the drive’sfreqargument, not a coupling-side carrier.References
McKay, Filipp, Mezzacapo, Magesan, Chow & Gambetta, Universal Gate for Fixed-Frequency Qubits via a Tunable Bus, Phys. Rev. Applied 6, 064007 (2016) — parametric two-qubit gates via coupler flux modulation.
Krantz et al., A quantum engineer’s guide to superconducting qubits, Appl. Phys. Rev. 6, 021318 (2019), §V.D — tunable couplers.
Examples
>>> from quchip import Chip, ControlEquipment, DuffingTransmon, ParametricDrive, TunableCapacitive >>> q0 = DuffingTransmon(freq=5.0, anharmonicity=-0.25, levels=3, label="q0") >>> q1 = DuffingTransmon(freq=5.2, anharmonicity=-0.22, levels=3, label="q1") >>> tc = TunableCapacitive(q0, q1, g_0=0.0, label="tc") >>> pump = ParametricDrive(tc, label="pump") >>> chip = Chip([q0, q1], couplings=[tc], control_equipment=ControlEquipment([pump])) >>> # seq.pump(tc, envelope=..., freq=...) schedules δg(t); see QuantumSequence.pump.
- default_fit_observable: ClassVar[str] = 'cross_kerr'¶
Observable represented by this coupling’s declared scalar when the enclosing chip is passed to
fit_a_dressas a dressed specification. Concrete coupling models override this when their inverse-design quantity is a dressed interaction observable.
- g_0: Any = Parameter(default=unbound, positive=False, nonnegative=False, serialize=True, unit='GHz', symbol='g_0', noise=False, kw_only=False, required=False)¶
- class quchip.chip.ChipTransform(*args, **kwargs)[source]¶
Bases:
ProtocolStructural protocol for any transformation result that yields a chip.
- class quchip.chip.EliminationResult(chip, effective_params, validity, notes=<factory>)[source]¶
Bases:
objectStore the result of
eliminate().- Parameters:
- chip¶
The reduced chip (eliminated mode removed; effect folded into ordinary surviving devices). The input chip is never mutated.
- Type:
- effective_params¶
Derived quantities per survivor:
{label: {"lamb_shift", "purcell_rate", "freq_after", "chi", "kappa"}}(GHz for frequencies, 1/ns for rates).chiis the dispersive pullχ_pull ≡ f_mode(survivor in |1⟩) − f_mode(survivor in |0⟩)— the full resonator pull per survivor excitation, i.e. 2× the σ_z-convention χ ofH_disp = (ω_r + χσ_z)a†a. For a mode touching more than one survivor, the mode is a bus / coupler, not a readout mode, sochiis reported as0.0for every survivor. Otherwisechiis a deferred entry: computed from the input chip’s dressed spectrum (one full-chip diagonalization) on the first["chi"]access and cached, so reductions that never read it stay pure algebra (LazyEffectiveParams); gradients through it followChip.dispersive_shift’s backend rule, while every other entry remains backend-independent algebra.kappais the eliminated mode’s own decay rate, from itsintrinsic_decay_rate()(e.g. a resonator’s combined2π·f_mode/Qphoton loss plus1/T1), or0.0when the mode declares no decay channel.A mode touching two or more survivors additionally emits an
"exchange"entry describing the mediated survivor-survivor coupling(s) derived from the Sylvester/exact pair extraction (quchip.chip.sw). For exactly two survivors (the bridge case) this is a single dict:{"j_eff", "dJ_domega_c", "between", "folded_into", "zz", "pathways"}. For three or more survivors, every survivor pair induces its own mediated exchange, so"exchange"is instead adictkeyed by the pair(label_a, label_b), each value the same per-pair schema. In both cases:j_effis the mediated exchangeJ = g_a g_b / 2 · (1/Δ_a + 1/Δ_b)(F. Yan et al., Phys. Rev. Applied 10, 054062 (2018)), read off themethod="sw"/"exact"pair extraction;dJ_domega_cis its analytic derivative w.r.t. the eliminated mode’s frequency (used by the flux-drive retarget rule);folded_intois the label of the effective edge the exchange landed on (an existing direct coupling between the pair, or a freshly emittedCapacitiveorTunableCapacitive);zzis the exact residual ZZ between the pair (method="exact"only —Noneunder"sw", where it is a higher-order correction not represented);pathwaysis the top virtual-state attribution of the exchange (method="sw"only, fromquchip.chip.sw.pathway_attribution()—Noneunder"exact", which has no perturbative generator to attribute).
- validity¶
Per eliminated coupling:
{coupling_label: {"g_over_delta", "is_valid", "min_block_gap"}}.min_block_gapis the smallest bare-energy gap the Sylvester generator crossed for this mode (quchip.chip.sw.sylvester_generator()), shared across every coupling touching the mode. Wheneliminateruns underjax.jit/grad,is_valid(g_over_delta < 0.1) is a traced boolean, not a Pythonbool— read it outside the traced region, or branch on it withjnp.whererather thanif.
- Every mapping above is a :class:`~quchip.utils.labeling.LabelKeyedDict`
- the device or coupling *object* is as good a key as its label, and pair
- keys match in either order —
- ``res.effective_params[q1]``, ``res.validity[leg]``, and
- ``exchange[(q1, q0)]`` all resolve.
- describe()[source]¶
Plain-text fold report: every fold stated explicitly, before -> after.
Per survivor: freq (and T1 when either side carries one), each Lamb-shifted/Purcell-folded value read back from
effective_paramsrather than a stored “before” chip —freq_before = freq_after - lamb_shiftandT1_beforefrompurcell_rateare exact identities of howeliminate()derivesfreq_after/T1, not an approximation. Multi-survivor targets add the emitted exchange edge (Yan-formula tag) and a ZZ line (unavailable undermethod="sw", the exact residual undermethod="exact"); any control-line retarget and the per-coupling validity verdict follow. Traced parameters render as<traced>and are never concretized; for use outsidejit/gradregions, like every otherdescribe()in the package.- Return type:
- quchip.chip.eliminate(chip, target, *, method='sw')[source]¶
Reduce a far-detuned device or an edge coupling, returning a reduced chip.
targetis resolved against the chip’s device and coupling namespaces (disjoint by construction —Chiprejects a coupling label that collides with a device label) and dispatches to one of two model reductions:Device target — adiabatic elimination of a far-detuned mode, via
quchip.chip.sw. A mode touching one survivor folds into a Lamb shift (and a Purcell channel when the mode dissipates). A mode touching two or more survivors — bus / tunable-coupler (bridge) or several at once — additionally induces a mediated exchangeJ = g_a g_b / 2 · (1/Δ_a + 1/Δ_b)between every survivor pair (with∂J/∂ω_crecorded alongside it), folded into the direct coupling between that pair when one exists or added as a new edge otherwise. A fixed eliminated mode emits aCapacitive; a mode that declares frequency control, has a retargeted flux line, or folds into an already-modulable edge emits aTunableCapacitive. At a tunable coupler’s idle point, itsg_0is the net coupling the pair feels, including any direct-edge cancellation. Eliminating several couplers is sequential composition:eliminate(eliminate(chip, "TC1").chip, "TC2").Coupling target — dispersive reduction of an exchange edge to its dressed cross-Kerr shift: both endpoint devices survive (Lamb-shifted), and the coupling itself is replaced by a
CrossKerrcarrying the dressed pull (seereduce_coupling()). This is the effective-readout-chip flow — reduce a qubit-resonator exchange edge to the diagonal interaction an ordinary charge line probes.methodhas no effect here: no mode is removed, so the reduction always reads the chip’s exact dressed spectrum.
- Parameters:
chip (Chip) – Source chip (never mutated).
target (Any) – The device or coupling to eliminate — label string or object.
method (str) – Device targets only.
"sw"(default) is the 2nd-order Schrieffer-Wolff reduction (Bravyi, DiVincenzo & Loss, Ann. Phys. 326, 2793 (2011)) — cheap, differentiable, and what every effective parameter above is derived from perturbatively."exact"instead exactly diagonalizes the same resolved static model as the SW route (exact-from-dressing,quchip.chip.sw.exact_reduction()) — exact kept-block energies (what residual ZZ needs) at the cost of a full diagonalization, and it raises when near-degenerate dressed states make the bare labeling ambiguous. Any other value raisesValueError.
- Return type:
Examples
>>> from quchip import DuffingTransmon, Resonator, Capacitive, Chip >>> from quchip.chip.transformations import eliminate >>> q = DuffingTransmon(freq=5.0, anharmonicity=-0.25, levels=3, label="q") >>> r = Resonator(freq=7.0, levels=5, label="r") >>> chip = Chip([q, r], couplings=[Capacitive(q, r, g=0.05)]) >>> result = eliminate(chip, r) # r removed; Lamb shift folded into q.freq >>> reduced = result.chip >>> [d.label for d in reduced.devices] ['q']
- class quchip.chip.ActivePatchResult(chip, sequence, active_labels, eliminated_labels, steps, notes)[source]¶
Bases:
objectA reduced patch chip, the re-bound sequence, and the reduction validity record.
- Parameters:
- chip¶
The patch chip: schedule-active devices plus whatever spectators
active_patch()could not eliminate (unreachable, or where elimination itself declined — seenotes).- Type:
Any
- sequence¶
A
QuantumSequencebound tochip, replaying the source sequence’s entries verbatim.- Type:
Any
- eliminated_labels¶
Device labels actually folded away, in elimination order (farthest-from-active first).
- steps¶
The
EliminationResultfrom each successfuleliminate()call, verbatim and ineliminated_labelsorder — reshape nothing here; read.validity/.effective_paramsoff the step objects through the convenience properties below.- Type:
- notes¶
Every explicitly dropped or deferred piece of physics: unreachable spectators left in place, control lines stripped as unused, and (if elimination itself couldn’t proceed past some spectator) why the reduction stopped early — plus every step’s own notes.
- property validity: dict[str, Any]¶
{eliminated label: that step's .validity}— verbatim, per-coupling shape untouched.
- quchip.chip.active_patch(sequence, *, hops=1, method='sw')[source]¶
Reduce a chip to its schedule-active patch by eliminating spectators.
Spectators are eliminated one at a time via
eliminate(), farthest-from-active first; every step’s validity metrics ride on the result untouched. Explicit opt-in — this approximates (Schrieffer-Wolff, or the exact dressed-spectrum route undermethod="exact"), unlike the exact automatic partitioningsimulate()performs internally at solve time.The elimination order and reachability are recomputed from the current reduced chip before every step, not just once up front: a fold can only ever add a bridging edge between the eliminated mode’s neighbors, never remove one, so a label’s distance from the active set can shorten but never make a previously reachable label unreachable — still, reading the graph fresh each time means a label that has already been folded away is never re-considered, and the order always reflects what
eliminatewill actually see. Bridging edges created by earlier folds may beCapacitiveedges carryinggorTunableCapacitiveedges carryingg_0. Both fold onward, so cycles among spectators reduce all the way down. Ifeliminatestill declines a step (its typedNotImplementedErrorsignal for an unsupported elimination — e.g. a Purcell decay fold onto a survivor that carries thermal occupation, which no collapse-channel API can represent without inventing physics that was never present), the reduction stops there: everything eliminated so far stays folded, and the remaining spectators — including the one that failed — are left on the patch chip untouched, with the reason recorded innotes.- Parameters:
sequence (QuantumSequence) – The schedule to reduce around.
hops (int) – Coupling-graph hops the active set expands beyond the scheduled targets (see
active_labels()).method (str) – Forwarded to
eliminate()for every device elimination.
- Return type:
- quchip.chip.register_retarget_rule(drive_type, target_type, result_kind, rule)[source]¶
Register a converter for
(drive type, eliminated-target type, result kind).Lookup (
lookup_retarget_rule()) walks both types’ MROs, so a rule registered for a base type also covers its subclasses;result_kindmatches exactly. This is the extension point for teachingeliminate()to carry a new kind of stranded control line without modifying it.- Parameters:
drive_type (type) – Control-line class the rule handles.
target_type (type) – Eliminated-target class the rule handles: a device type (the eliminated mode itself) for
"edge"/"leaf-fold".result_kind (str) –
"edge","leaf-fold", or"crosskerr".rule (callable) –
rule(line, ctx: RetargetContext) -> RetargetResult.
- Return type:
None
- quchip.chip.register_elimination_target(target)[source]¶
Register an
EliminationTargetkind foreliminate()to dispatch on.- Parameters:
target (EliminationTarget)
- Return type:
None
- quchip.chip.register_reduction_method(method)[source]¶
Register a reduction strategy under its
ReductionMethod.name.- Parameters:
method (ReductionMethod)
- Return type:
None
Modules
Dressed-state analysis owned by |
|
Chip-level baths — shared / collective Lindblad dissipation. |
|
Composite quantum system — |
|
Coupling base class and registry. |
|
Coupling models for two-body interactions between devices. |
|
Human-readable text summaries — the |
|
JAX-traceable dressed-state labeling primitives. |
|
Observable construction for |
|
Exact subsystem partitioning — connected components of a chip's independence graph. |
|
Physical Markovian input-output channels attached to a chip. |
|
Retarget registry for control lines stranded by |
|
Chip serialization, deserialization, and structural cloning. |
|
State factories for |
|
Schrieffer-Wolff reduction kernels (2nd order) on bare chip blocks. |
|
Model reduction: |