spin_pulse¶
SpinPulse is an open-source python package for simulating silicon based spin qubits at the pulse-level.
Modules¶
spin_pulse.transpilationThe transpilation module provides a set of classes that enable the simulation of quantum circuits defined in Qiskit on silicon-based spin-qubit hardware models.
spin_pulse.environmentThe environment module provides a set of classes for defining and configuring a quantum experimental environment tailored to spin-qubit systems.
spin_pulse.characterizationThe characterization module provides a set of functions for characterizing spin-qubit control operations and quantifying noise strength.
Re-exported objects¶
The following objects can be directly imported from spin_pulse even if they are implemented in submodules.
Enumeration of supported dynamical decoupling sequences. |
|
Contain a quantum experimental environment with configurable noise models. |
|
Defines the hardware specifications for a spin qubit device model. |
|
Pulse-level representation of a quantum circuit. |
|
Enumeration of pulse envelope shapes. |
Subpackages¶
Submodules¶
Classes¶
Contain a quantum experimental environment with configurable noise models. |
|
Enumeration of supported dynamical decoupling sequences. |
|
Defines the hardware specifications for a spin qubit device model. |
|
Enumeration of pulse envelope shapes. |
|
Pulse-level representation of a quantum circuit. |
Package Contents¶
- class spin_pulse.ExperimentalEnvironment(hardware_specs, noise_type=NoiseType.PINK, T2S=100.0, TJS=None, duration=2**10, only_idle=False, segment_duration=2**10, seed=None)[source]¶
Contain a quantum experimental environment with configurable noise models.
- - hardware_specs
HardwareSpecs class, that defines the hardware settings.
- Type:
class
- - noise_type
Type of noise to simulate. Must be “pink”, “white”, or “quasistatic”.
- Type:
- - T2S
Characteristic time of individual qubits.
- Type:
- - TJS
Characteristic time of coupled two-qubit system at maximal J coupling without noise on the qubit’s frequency.
- Type:
float or None
- - duration
Total duration of the simulation.
- Type:
- - segment_duration
Duration of each noise segment; used to partition the time trace.
- Type:
- - only_idle
Flag to apply noise only to idle qubits.
- Type:
- - time_traces_coupling
List of time traces for coupling noise for each pair of qubits (if TJS is set).
- - seed
seed integer for random number generation. If not specified, no seed used.
- Type:
int or None
Initialize the ExperimentalEnvironment with specified noise characteristics and simulation parameters.
- Parameters:
hardware_specs (class) – HardwareSpecs class, that defines the hardware settings.
noise_type (NoiseType) – Type of noise to simulate. Must be “pink”, “white”, or “quasistatic”.
T2S (float) – Characteristic time of individual qubits.
TJS (float or None) – Characteristic time of coupled two-qubit system at maximal J coupling with no noise on the qubit’s frequency.
duration (int) – Total duration of the simulation.
only_idle (bool) – Flag to apply noise only to idle qubits.
segment_duration (int) – Duration of each noise segment; used to partition the time trace.
seed (int or None) – seed integer for random number generation. If not specified, no seed used.
- Raises:
ValueError – If an invalid noise_type is provided.
- noise_generator: type[spin_pulse.environment.noise.WhiteNoiseTimeTrace] | type[spin_pulse.environment.noise.QuasistaticNoiseTimeTrace] | type[spin_pulse.environment.noise.PinkNoiseTimeTrace]¶
- hardware_specs: spin_pulse.transpilation.hardware_specs.HardwareSpecs¶
- noise_type: spin_pulse.environment.noise.NoiseType¶
- only_idle = False¶
- generate_time_traces()[source]¶
Generate noise time traces for each qubit’s frequency and J coupling to each pair of qubits if TJS is defined.
- Behavior:
For each qubit, instantiate a noise generator using the selected noise_type. The generator uses T2S, duration, and segment_duration to produce a time trace. If TJS is provided, generate additional time traces for J coupling noise for each pair of qubits.
- Effects:
Populate self.time_traces with one noise trace per qubit. If TJS is set, populate self.time_traces_coupling with one trace per pair of qubits (n-1 traces for n qubits).
- class spin_pulse.DynamicalDecoupling(*args, **kwds)[source]¶
Bases:
enum.EnumEnumeration of supported dynamical decoupling sequences.
This enumeration identifies the available pulse-based methods used to mitigate phase noise in spin qubit experiments. The selected sequence determines how control pulses are applied during idle periods in order to reduce the effect of low-frequency noise.
- - FULL_DRIVE
Continuous driving of the qubit during the idle period.
- - SPIN_ECHO
Single refocusing pulse applied at the midpoint of the idle period.
- FULL_DRIVE = 'full_drive'¶
- SPIN_ECHO = 'spin_echo'¶
- class spin_pulse.HardwareSpecs(num_qubits, B_field, delta, J_coupling, rotation_shape, ramp_duration=1, coeff_duration=5, dynamical_decoupling=None, optim=0)[source]¶
Defines the hardware specifications for a spin qubit device model.
This class stores all physical and control parameters required to build pulse instructions, generate rotation gates, and configure backend-level compilation. It also defines the available couplings, supported gate set, and optional dynamical decoupling strategy. The specifications in this object determine how qubit operations and timing constraints are modeled throughout the simulation workflow.
- - rotation_generator
Class used to generate rotation instructions based on the selected pulse shape.
- Type:
- - num_qubits
Number of qubits in the device model.
- Type:
- - J_coupling
Maximum coupling strength between adjacent qubits.
- Type:
- - fields
Dictionary mapping interaction types (“x”, “y”, “z”, “Heisenberg”) to their corresponding field strengths.
- Type:
- - rotation_shape
Shape of the pulses used for qubit control.
- Type:
- - coeff_duration
Duration coefficient for Gaussian pulses when applicable.
- Type:
- - ramp_duration
Duration of the ramp used in square pulses.
- Type:
- - first_pass
Preset first-stage Qiskit pass manager.
- Type:
PassManager
- - second_pass
Additional optimization pass manager.
- Type:
PassManager
- - dynamical_decoupling
Optional dynamical decoupling sequence applied to idle qubits.
- Type:
DynamicalDecoupling | None
Initialize the HardwareSpecs object that defines the hardware specifications.
- Parameters:
num_qubits (int) – Number of qubits considered.
B_field (float) – Maximal magnetic field strength.
delta (float) – Maximal energy difference between two qubits.
J_coupling (float) – Maximal coupling strength between two qubit.
rotation_shape (Shape) – Pulse shape used for qubit manipulation.
ramp_duration (int, optional) – Duration of the pulse ramp for square pulse. Default is 1.
coeff_duration (int, optional) – Duration coefficient for Gaussian pulses. Default is 5.
dynamical_decoupling (DynamicalDecoupling, optional) – If not None, defines the dynamical decoupling sequence to be applied to Idle qubits.
optim (int)
- rotation_generator: type[spin_pulse.transpilation.instructions.RotationInstruction]¶
- first_pass¶
- second_pass¶
- dynamical_decoupling: spin_pulse.transpilation.dynamical_decoupling.DynamicalDecoupling | None = None¶
- class spin_pulse.Shape(*args, **kwds)[source]¶
Bases:
enum.EnumEnumeration of pulse envelope shapes.
This enum defines the functional form of the pulse envelope used for control operations in spin-qubit pulse sequences.
- GAUSSIAN = 'gaussian'¶
Gaussian-shaped pulse envelope.
- SQUARE = 'square'¶
Square (rectangular) pulse envelope.
- class spin_pulse.PulseCircuit(circ, qubits, pulse_layers, hardware_specs, exp_env=None)[source]¶
Pulse-level representation of a quantum circuit.
A PulseCircuit stores a layered decomposition of a qiskit.QuantumCircuit into PulseLayer objects and, optionally, a stochastic noise environment. It provides utilities to visualize the pulse schedule, convert it back to a gate-level circuit, and compute fidelities or average channels under sampled noise realizations.
- - original_circ
Original quantum circuit from which the PulseCircuit was constructed.
- Type:
qiskit.QuantumCircuit
- - num_qubits
Number of qubits in the circuit.
- Type:
- - qubits
Ordered list of qubits acted on by the circuit.
- Type:
list[qiskit.circuit.Qubit]
- - pulse_layers
Ordered list of pulse layers that implement the circuit at the pulse level.
- Type:
- - n_layers
Number of pulse layers.
- Type:
- - duration
Total duration of the pulse circuit, given by the sum of all layer durations (in the discrete time unit of the model).
- Type:
- - t_lab
Current position in the laboratory time axis, used to attach successive noise time traces when averaging over samples.
- Type:
Initialize a PulseCircuit from pulse layers.
The constructor records the original circuit, the list of qubits and the sequence of PulseLayer objects. It computes the total duration, assigns starting times to all layers and computes a dynamical decoupling sequence according to the hardware specifications. If an ExperimentalEnvironment is provided, noise time traces are attached to the circuit and its layers. Optionally, a container for storing per-sample time series can be created.
- Parameters:
circ (QuantumCircuit) – Original quantum circuit represented at the pulse level.
qubits (list[qiskit.circuit.Qubit]) – Ordered list of qubits involved in the circuit.
pulse_layers (list[PulseLayer]) – Pulse layers that realize the circuit in time order.
hardware_specs (HardwareSpecs) – Hardware configuration specifying fields, couplings and dynamical decoupling options.
exp_env (ExperimentalEnvironment | None) – Noise environment from which time traces are drawn and attached to this circuit. If None, no noise trace is attached.
- original_circ: qiskit.QuantumCircuit¶
- num_qubits¶
- pulse_layers¶
- n_layers¶
- duration¶
- t_lab = 0¶
- classmethod from_circuit(circ, hardware_specs, exp_env=None)[source]¶
Construct a PulseCircuit from a qiskit.QuantumCircuit.
The input is first converted to a qiskit.dagcircuit.DAGCircuit then all barrier and measurement gate are removed, and each DAG layer is translated into a PulseLayer using the hardware specifications. Empty layers (containing only barriers) are skipped. The resulting list of pulse layers is used to build a PulseCircuit.
- Parameters:
circ (qiskit.QuantumCircuit) – Circuit to translate into pulse layers.
hardware_specs (HardwareSpecs) – Hardware specification used to map gate operations to pulse sequences.
exp_env (ExperimentalEnvironment | None) – Experimental environment providing noise specification and noise time traces. If None, no noise is attached to the pulses.
- Returns:
A pulse-level representation of the input circuit.
- Return type:
- classmethod from_dag_circuit(dag, hardware_specs, exp_env=None, original_circuit=None)[source]¶
Construct a PulseCircuit from a qiskit.dagcircuit.DAGCircuit.
The input circuit is first stripped of measurements and barrier, if present. Then each DAG layer is translated into a PulseLayer using the hardware specifications. Empty layers (containing only barriers) are skipped. The resulting list of pulse layers is used to build a PulseCircuit.
- Parameters:
dag (qiskit.dagcircuit.DAGCircuit) – Circuit to translate into pulse layers.
hardware_specs (HardwareSpecs) – Hardware specification used to map gate operations to pulse sequences.
exp_env (ExperimentalEnvironment | None) – Experimental environment providing noise specification and noise time traces. If None, no noise is attached to the pulses.
original_circuit (qiskit.QuantumCircuit | None)
- Returns:
A pulse-level representation of the input circuit.
- Return type:
- assign_starting_times()[source]¶
Assign a starting time to each pulse layer to synchronize the different layers and pulse instructions.
The starting time
t_startof each PulseLayer is computed as the cumulative duration of all previous layers, with the first layer starting at time zero. This defines a global time axis for the PulseCircuit.
- plot(hardware_specs=None, label_gates=True)[source]¶
Plot the pulse schedule of the circuit.
This method creates a multi-panel matplotlib figure showing, for each layer, the one-qubit and two-qubit pulse envelopes applied to each qubit and coupling. The vertical scale is chosen consistently with the hardware field and coupling amplitudes if given.
- Parameters:
hardware_specs (HardwareSpecs | None) – Hardware specification used to set the limits of manipulation parameter amplitudes. If None, default symmetric limits are used.
label_gates (bool) – If True, gate labels are shown.
- to_circuit(measure_all=False)[source]¶
Convert the pulse circuit back to a qiskit.QuantumCircuit.
Each PulseLayer is converted into equivalent circuit that are composed into a copy of the original circuit structure. Optionally, a final measurement on all qubits is added.
- Parameters:
measure_all (bool) – If True, all qubits are measured at the end of the reconstructed circuit.
- Returns:
A circuit implementing the same unitary evolution as the PulseCircuit (up to numerical approximations).
- Return type:
qiskit.QuantumCircuit
- circuit_samples(exp_env=None)[source]¶
Compute the number of noisy circuit samples that can be obtained with the given environment.
The number of circuit samples is given by the integer ratio between the environment duration and the pulse-circuit duration. If no environment is provided, a single sample is assumed.
- Parameters:
exp_env (ExperimentalEnvironment | None) – Experimental environment providing the total duration.
- Returns:
Number of non-overlapping samples that can be drawn from the duration of the experiment.
- Return type:
- get_logical_bitstring(physical_bistring)[source]¶
Restore the original logical qubit layout before transpilation. During Qiskit transpilation process, the qubit register may be reordered to produce an optimized physical layout that minimizes gate costs. To recover the logical bitstring and interpret measurement outcomes correctly, it is necessary to invert this remapping and reconstruct the initial logical ordering of the qubits.
The mapping is derived from the layout associated with the original circuit used to build the PulseCircuit. If a TranspileLayout is present, the final index layout is used. If only a Layout is available, its permutation is used and a warning is emitted, as this typically indicates that the circuit was not transpiled. If no layout information is present, the physical and logical orders are assumed to coincide and a warning is emitted.
- averaging_over_samples(f, exp_env=None, *args)[source]¶
Estimate the average value over as many noisy samples as the experimental environment allows it, of a user-provided function using the pulse circuit.
This method repeatedly attaches new pieces of the noise time traces from the experimental environment to the PulseCircuit and evaluates a user-provided function
f(self, *args)for each realization. The results are averaged over all samples, effectively performing a Monte Carlo average over noise trajectories.- Parameters:
f (Callable) – Function that takes the PulseCircuit as first argument and returns a numerical quantity to be averaged.
exp_env (ExperimentalEnvironment | None) – Noise environment from which time traces are drawn. If None, a single deterministic evaluation is performed.
*Parameters – Additional positional arguments forwarded to
f.
- Returns:
The sample-averaged value of
f(self, *args).- Return type:
Any
- run_experiment(exp_env, simulator=AerSimulator())[source]¶
Simulate single-shot measurement on noisy instances of the circuit.
This method repeatedly attaches new pieces of the noise time traces from the experimental environment to the PulseCircuit and simulates with MPS method a single-shot measurement thanks to Qiskit Aer. The results are stored in a dictionary that gather the counts obtained for all possible bitstrings.
- Parameters:
exp_env (ExperimentalEnvironment | None) – Noise environment from which time traces are drawn. If None, a single deterministic evaluation is performed.
simulator (-) – an instance of qiksit’s AerSimulator.
- Returns:
A dictionary which keys are the obtained bitstrings and their respective number of occurences.
- Return type:
- fidelity(circ_ref=None)[source]¶
Compute the average gate fidelity with respect to a reference circuit.
The PulseCircuit is converted to a qiskit.QuantumCircuit, and the average gate fidelity between its unitary and that of the reference circuit is computed using the qiskit.quantum_info.Operator representation.
- Parameters:
circ_ref (qiskit.QuantumCircuit) – Reference circuit used to define the target unitary. Default is self.original_circ
- Returns:
Average gate fidelity between the PulseCircuit unitary and the reference circuit unitary.
- Return type:
- mean_fidelity(exp_env, circ_ref=None)[source]¶
Estimate the mean fidelity under a stochastic noise environment.
The average gate fidelity with respect to a reference circuit is computed for multiple noise realizations drawn from the experimental environment, and the results are averaged using
averaging_over_samples.- Parameters:
circ_ref (qiskit.QuantumCircuit) – Reference circuit used to define the target unitary.
exp_env (ExperimentalEnvironment | None) – Noise environment from which time traces are drawn.
- Returns:
Sample-averaged gate fidelity under the specified noise model.
- Return type:
- mean_channel(exp_env=None)[source]¶
Estimate the mean quantum channel generated by the pulse circuit.
For each noise realization, the PulseCircuit is converted to a qiskit.QuantumCircuit and then to a SuperOp representing the corresponding quantum channel. The channels are averaged over samples using
averaging_over_samples.- Parameters:
exp_env (ExperimentalEnvironment | None) – Noise environment from which time traces are drawn.
- Returns:
Sample-averaged quantum channel acting on the qubit register.
- Return type:
qiskit.quantum_info.SuperOp
- attach_time_traces(exp_env=None)[source]¶
Attach noise time traces from the experimental environment to the pulse circuit.
If an experimental environment is provided, this method extracts segments of the environment time traces that match the total circuit duration and assigns them to the PulseCircuit and each PulseLayer. For one-qubit pulse sequences, the corresponding single-qubit time traces are attached (qubit’s frequency deviation). For two-qubit sequences, coupling time traces are attached if available (i.e. J coupling noise) and used to set the J noise deviation during two-qubit gates.
The internal laboratory time pointer
t_labis incremented by the circuit duration after attaching the time traces, so that subsequent calls use the next segment of the noise time trace.- Parameters:
exp_env (ExperimentalEnvironment | None) – Experimental environment providing qubit’s frequency deviation time trace and, optionally, J coupling deviation time traces. If None, no trace is attached.
- attach_dynamical_decoupling(hardware_specs)[source]¶
Insert dynamical decoupling sequences into all pulse layers, when possible (i.e. Idle time sufficiently long).
If a dynamical decoupling mode is specified in the hardware specifications, each PulseLayer in the circuit is updated by calling its
attach_dynamical_decouplingmethod with the chosen mode. If no dynamical decoupling is configured, the circuit is left unchanged.- Parameters:
hardware_specs (HardwareSpecs) – Hardware configuration specifying the dynamical decoupling mode and available pulse shapes.