quchip.analysis.vna

Continuous-wave scattering through declared Markovian ports.

Classes

PortTone(port, freq, amplitude, _index, _owner)

A fixed coherent input field that enters through one declared port.

VNA(chip, *[, ports])

Small-signal scattering between selected instrument ports of one chip.

class quchip.analysis.vna.PortTone(port, freq, amplitude, _index, _owner)[source]

Bases: object

A fixed coherent input field that enters through one declared port.

Variables:
  • port (str) – Resolved label of the external network port.

  • freq (scalar) – Carrier frequency in GHz.

  • amplitude (scalar) – Complex incident field amplitude in 1/sqrt(ns).

port: str
freq: Any
amplitude: Any
vary(field, values, *, name=None)[source]

Create a sweep axis for this tone’s frequency or amplitude.

Parameters:
  • field ({"freq", "amplitude"}) – Tone attribute to vary. Frequency is in GHz and amplitude is in 1/sqrt(ns).

  • values (array_like) – Values in sweep order.

  • name (str or None, optional) – Public name of the result axis. The default is "<port>.<field>".

Returns:

Axis for VNA.sweep(), VNA.finite_power(), or VNA.measure().

Return type:

Sweep

class quchip.analysis.vna.VNA(chip, *, ports=None)[source]

Bases: object

Small-signal scattering between selected instrument ports of one chip.

VNA(chip) selects every exposed instrument port in the chip’s PortNetwork. To select a subset, pass exposed port objects or their labels as ports. A bare label string is rejected.

S-parameters follow the engineering e^{+jωt} convention, where j = i. Probe and pump amplitudes, returned fields, correlations, and IQ statistics use this convention, while internal mode observables keep the physics convention.

Parameters:
  • chip (Chip) – Chip with a PortNetwork.

  • ports (sequence of port objects or str, optional) – Selected external ports. None selects all external ports.

pump(port, *, freq, amplitude)[source]

Add a fixed coherent pump and return its sweep handle.

Parameters:
  • port (port object or str) – External port receiving the pump.

  • freq (scalar) – Pump frequency in GHz.

  • amplitude (scalar) – Complex incident field in 1/sqrt(ns).

Returns:

Handle to vary the pump frequency or amplitude.

Return type:

PortTone

static zip(*variations)[source]

Pair sweep axes element by element instead of a product.

Parameters:

*variations (Sweep) – Axes with equal lengths.

Returns:

Composite sweep evaluated at corresponding points.

Return type:

ZippedSweep

sweep(frequencies, *variations, when=None, options=None, progress=False)[source]

Sweep the selected ports’ complete small-signal matrix around fixed pumps.

The result contains every S(output, input) between the selected ports. Its matrix has shape (*sweep_axes, n_ports, n_ports) and is indexed [..., output, input]. Ordinary Sweep axes name paths in chip.parameters, rebind the chip at each point, and can mix with pump-tone axes. At each frequency, the passive-linear route solves one multi-right-hand-side mode-space system. The stationary route solves one pumped operating point, then uses one shifted-Liouvillian factorization for every input port. A pump-free model that is static in the lab frame uses one stationary state per chip point and a resolvent at each probe frequency.

Parameters:
  • frequencies (scalar or array_like) – Probe frequencies in GHz.

  • *variations (Sweep or ZippedSweep) – Chip and pump axes. Cartesian axes combine and zipped axes vary together.

  • when (mapping of device objects or labels to int, optional) – Frozen dressed-reference label. Unspecified devices have level zero. Supports zero or one total excitation, static conserving models and vacuum inputs. None uses the ordinary stationary response. An excited reference is fixed in the probe source, while its response includes all loss channels. It does not model an evolving preparation.

  • options (dict or None, optional) – Stationary solver options. None permits the passive-linear path. Explicit when requires None.

  • progress (bool, default=False) – Show a progress bar for stationary solves.

Returns:

Matrix with shape (*shape, n_ports, n_ports) and indexing [..., output, input].

Return type:

SParameterResult

resonances()[source]

Return the poles of the weak-probe response between the selected ports.

The poles come from the model that sweep() solves on its "linear_response" and "vacuum_response" routes, without a fit. Each eigenvalue λ_p of the drift A = -iH - C†C/2 gives a pole frequency f_p = -Im λ_p / 2π in GHz and a response linewidth κ_p = -2 Re λ_p in 1/ns, which includes port, internal, Purcell and dephasing broadening. The frequencies and linewidths stay differentiable under JAX on a fixed structure away from degenerate poles. Compositions and residues are computed when they are read.

Returns:

Poles in increasing frequency, with their composition, dominant mode and residues.

Return type:

ResonanceResult

Raises:

ValueError – If the VNA has pump tones, if no weak-probe route applies, with the reason that sweep() gives, or if two ill-conditioned poles are too close to resolve, as near an exceptional point.

finite_power(frequencies, amplitudes, *variations, input=None, options=None, progress=False)[source]

Solve the stationary mean output fields for a finite coherent probe.

frequencies are in GHz. amplitudes are incident field amplitudes beta in 1/sqrt(ns). Complex values encode phase. The probe enters input beside any fixed pumps. input defaults to the selected port when only one is selected, and is required otherwise. A fixed pump on the probe input is rejected.

At each grid point, the method solves the stationary Liouvillian in the probe frame. Chip and pump sweep axes precede "amplitude" and "frequency". Every selected port must resolve at the probe frequency. The returned MeanFieldResponseResult reports <b_out> with the same reference-plane and hidden-channel bookkeeping as sweep(). It also stores the incident beta, broadcast over the grid.

This method does not use the passive-linear mode-space shortcut or follow sweep-rate hysteresis and metastable branches. A chip whose static model conserves the total excitation N, with ports that lower N, other channels that lower or conserve it, vacuum inputs, no thermal occupation, pumps only at the probe frequency and no output network, solves on excitation sectors. A finite probe couples every N to N ± 1, so this route keeps the product states with N <= K. With chip.with_space(ExcitationCutoff(max_total=K)), K is the chip’s. Without a cutoff, a chip with more than 64 product states starts at K = 2, compares the result with K + 1 at every grid point, raises K until the change is below 1e-6 relative, and warns which K it kept. This is a convergence check, not an error bound. options other than None solve the backend’s stationary Liouvillian. Each entry of diagnostics records the route and its reason under "route".

Parameters:
  • frequencies (scalar or array_like) – Probe frequencies in GHz and incident fields in 1/sqrt(ns).

  • amplitudes (scalar or array_like) – Probe frequencies in GHz and incident fields in 1/sqrt(ns).

  • *variations (Sweep or ZippedSweep) – Chip and pump axes.

  • input (port object or str, optional) – Probe input, required when multiple ports are selected.

  • options (dict or None, optional) – Stationary solver options. Without a cutoff, a dictionary selects the full product space.

  • progress (bool, default=False) – Show a progress bar.

Returns:

Complex means with shape (*shape, n_ports) and incident fields with shape shape.

Return type:

MeanFieldResponseResult

measure(frequencies, amplitudes, *variations, input=None, outputs=None, noise_frequencies=None, options=None, progress=False)[source]

Capture stationary means and joint physical noise before you choose a receiver.

Frequencies are probe frequencies in GHz and amplitudes are in 1/sqrt(ns). Optional noise_frequencies are an increasing symmetric grid of offsets in GHz, including zero. The default spans ±0.1 GHz with logarithmic spacing down to 1 Hz. Choose a grid that covers the model’s noise features. The returned data supports receiver integration and Gaussian sampling without another solve, but it is not a quantum-trajectory distribution. The method also captures internal Fock-mode amplitudes and occupations, which you query with mode_amplitude(device) and photon_number(device).

An excitation-conserving chip solves on the product states with N <= K, as finite_power() describes. Without a cutoff, the automatic check also compares the noise spectra on the requested offset grid when the K + 1 space has at most 1024 states.

Parameters:
  • frequencies (scalar or array_like) – Probe frequencies in GHz and incident fields in 1/sqrt(ns).

  • amplitudes (scalar or array_like) – Probe frequencies in GHz and incident fields in 1/sqrt(ns).

  • *variations (Sweep or ZippedSweep) – Chip and pump axes.

  • input (port object or str, optional) – Probe input, required when multiple ports are selected.

  • outputs (sequence of port objects or str, optional) – Captured outputs. None selects all selected ports.

  • noise_frequencies (array_like or None, optional) – Symmetric increasing offset grid in GHz, including zero.

  • options (dict or None, optional) – Stationary solver options. None permits the passive-linear shortcut and the excitation sectors. A dictionary selects the backend’s stationary Liouvillian.

  • progress (bool, default=False) – Show a progress bar.

Returns:

Means and physical noise spectra reusable by receiver processing.

Return type:

VNAMeasurement

output_spectrum(output, *, frequencies, options=None)[source]

Return the normally ordered output fluctuation spectrum.

Frequencies are offsets in GHz from the stationary tone frame. The coherent carrier is reported separately because it is a delta peak, not a finite sampled spectral density.

A chip with pumps at one frequency solves on excitation sectors under the conditions of finite_power(), and chooses K as it does. result.diagnostics["route"] records the route and its reason.

Parameters:
  • output (port object or str) – Output plane.

  • frequencies (scalar or array_like) – Offset frequencies in GHz.

  • options (dict or None, optional) – Stationary solver options. A dictionary selects the backend’s stationary Liouvillian.

g1(output, delays, *, input=None, options=None)[source]

Return normalized first-order output coherence g1.

The excitation sectors apply as in output_spectrum().

Parameters:
  • output (port object or str) – Delayed output plane.

  • delays (scalar or array_like) – Non-negative delays in ns.

  • input (port object or str, optional) – Cross-correlation input. The default is output.

  • options (dict or None, optional) – Stationary solver options. A dictionary selects the backend’s stationary Liouvillian.

Returns:

Normalized and raw correlations on the delay grid.

Return type:

OutputCorrelationResult

g2(output, delays, *, input=None, options=None)[source]

Return normalized second-order output intensity correlation g2.

The excitation sectors apply as in output_spectrum().

Parameters:
  • output (port object or str) – Delayed output plane.

  • delays (scalar or array_like) – Non-negative delays in ns.

  • input (port object or str, optional) – Cross-correlation input. The default is output.

  • options (dict or None, optional) – Stationary solver options. A dictionary selects the backend’s stationary Liouvillian.

Returns:

Normalized and raw second-order correlations on the delay grid.

Return type:

OutputCorrelationResult