Pulse (qiskit.pulse
)#
Qiskit-Pulse is a pulse-level quantum programming kit. This lower level of
programming offers the user more control than programming with
QuantumCircuit
s.
Extracting the greatest performance from quantum hardware requires real-time pulse-level instructions. Pulse answers that need: it enables the quantum physicist user to specify the exact time dynamics of an experiment. It is especially powerful for error mitigation techniques.
The input is given as arbitrary, time-ordered signals (see: Instructions) scheduled in parallel over multiple virtual hardware or simulator resources (see: Channels). The system also allows the user to recover the time dynamics of the measured output.
This is sufficient to allow the quantum physicist to explore and correct for noise in a quantum system.
Configurations for pulse experiments.
Instructions (qiskit.pulse.instructions
)#
The instructions
module holds the various Instruction
s which are supported by
Qiskit Pulse. Instructions have operands, which typically include at least one
Channel
specifying where the instruction will be applied.
Every instruction has a duration, whether explicitly included as an operand or implicitly defined.
For instance, a ShiftPhase
instruction can be instantiated
with operands phase and channel, for some float phase
and a
Channel
channel
:
ShiftPhase(phase, channel)
The duration of this instruction is implicitly zero. On the other hand, the
Delay
instruction takes an explicit duration:
Delay(duration, channel)
An instruction can be added to a Schedule
, which is a
sequence of scheduled Pulse Instruction
s over many channels. Instruction
s and
Schedule
s implement the same interface.
|
The Acquire instruction is used to trigger the ADC associated with a particular qubit; e.g. |
|
Pulse |
|
Pulse compiler directive that refers to a subroutine. |
|
A blocking instruction with no other effect. |
|
This instruction is responsible for applying a pulse on a channel. |
|
Pulse |
|
Set the channel frequency. |
|
Shift the channel frequency away from the current frequency. |
|
The set phase instruction sets the phase of the proceeding pulses on that channel to |
|
The shift phase instruction updates the modulation phase of proceeding pulses played on the same |
|
An instruction targeted for simulators, to capture a moment in the simulation. |
|
Pulse |
These are all instances of the same base class:
Pulse Library (qiskit.pulse.library
)#
This library provides Pulse users with convenient methods to build Pulse waveforms.
A pulse programmer can choose from one of several Pulse Models such as
Waveform
and SymbolicPulse
to create a pulse program.
The Waveform
model directly stores the waveform data points in each class instance.
This model provides the most flexibility to express arbitrary waveforms and allows
a rapid prototyping of new control techniques. However, this model is typically memory
inefficient and might be hard to scale to large-size quantum processors.
Several waveform subclasses are defined by Waveform Pulse Representation,
but a user can also directly instantiate the Waveform
class with samples
argument
which is usually a complex numpy array or any kind of array-like data.
In contrast, the SymbolicPulse
model only stores the function and its parameters
that generate the waveform in a class instance.
It thus provides greater memory efficiency at the price of less flexibility in the waveform.
This model also defines a small set of pulse subclasses in Parametric Pulse Representation
which are commonly used in superconducting quantum processors.
An instance of these subclasses can be serialized in the QPY Format
while keeping the memory-efficient parametric representation of waveforms.
Note that Waveform
object can be generated from an instance of
a SymbolicPulse
which will set values for the parameters and
sample the parametric expression to create the Waveform
.
Pulse Models#
|
A pulse specified completely by complex-valued samples; each sample is played for the duration of the backend cycle-time, dt. |
|
Subclass of |
|
The pulse representation model with parameters and symbolic expressions. |
|
The abstract superclass for parametric pulses. |
Waveform Pulse Representation#
- qiskit.pulse.library.constant(duration, amp, name=None)[소스]#
Generates constant-sampled
Waveform
.For \(A=\)
amp
, samples from the function:\[f(x) = A\]버전 0.25.0_pending부터 폐지됨: The function
qiskit.pulse.library.discrete.constant()
is pending deprecation as of qiskit-terra 0.25.0. It will be marked deprecated in a future release, and then removed no earlier than 3 months after the release date. The discrete pulses library, including constant() is pending deprecation. Instead, use the SymbolicPulse library to create the waveform with pulse.Constant(…).get_waveform(). Note that complex value support for the amp parameter is pending deprecation in the SymbolicPulse library. It is therefore recommended to use two float values for (amp, angle) instead of complex amp
- qiskit.pulse.library.zero(duration, name=None)[소스]#
Generates zero-sampled
Waveform
.Samples from the function:
\[f(x) = 0\]버전 0.25.0_pending부터 폐지됨: The function
qiskit.pulse.library.discrete.zero()
is pending deprecation as of qiskit-terra 0.25.0. It will be marked deprecated in a future release, and then removed no earlier than 3 months after the release date. The discrete pulses library, including zero() is pending deprecation. Instead, use the SymbolicPulse library to create the waveform with pulse.Constant(amp=0,…).get_waveform().
- qiskit.pulse.library.square(duration, amp, freq=None, phase=0, name=None)[소스]#
Generates square wave
Waveform
.For \(A=\)
amp
, \(T=\)period
, and \(\phi=\)phase
, applies the midpoint sampling strategy to generate a discrete pulse sampled from the continuous function:\[f(x) = A \text{sign}\left[ \sin\left(\frac{2 \pi x}{T} + 2\phi\right) \right]\]with the convention \(\text{sign}(0) = 1\).
버전 0.25.0_pending부터 폐지됨: The function
qiskit.pulse.library.discrete.square()
is pending deprecation as of qiskit-terra 0.25.0. It will be marked deprecated in a future release, and then removed no earlier than 3 months after the release date. The discrete pulses library, including square() is pending deprecation. Instead, use the SymbolicPulse library to create the waveform with pulse.Square(…).get_waveform(). Note that pulse.Square() does not support complex values for amp, and that the phase is defined differently. See documentation.- 매개변수:
- 반환 형식:
- qiskit.pulse.library.sawtooth(duration, amp, freq=None, phase=0, name=None)[소스]#
Generates sawtooth wave
Waveform
.For \(A=\)
amp
, \(T=\)period
, and \(\phi=\)phase
, applies the midpoint sampling strategy to generate a discrete pulse sampled from the continuous function:\[f(x) = 2 A \left( g(x) - \left\lfloor \frac{1}{2} + g(x) \right\rfloor\right)\]where \(g(x) = x/T + \phi/\pi\).
버전 0.25.0_pending부터 폐지됨: The function
qiskit.pulse.library.discrete.sawtooth()
is pending deprecation as of qiskit-terra 0.25.0. It will be marked deprecated in a future release, and then removed no earlier than 3 months after the release date. The discrete pulses library, including sawtooth() is pending deprecation. Instead, use the SymbolicPulse library to create the waveform with pulse.Sawtooth(…).get_waveform(). Note that pulse.Sawtooth() does not support complex values for amp. Instead, use two float values for (amp, angle). Also note that the phase is defined differently, such that 2*pi phase shifts by a full cycle.- 매개변수:
- 반환 형식:
예제
import matplotlib.pyplot as plt from qiskit.pulse.library import sawtooth import numpy as np duration = 100 amp = 1 freq = 1 / duration sawtooth_wave = np.real(sawtooth(duration, amp, freq).samples) plt.plot(range(duration), sawtooth_wave) plt.show()
- qiskit.pulse.library.triangle(duration, amp, freq=None, phase=0, name=None)[소스]#
Generates triangle wave
Waveform
.For \(A=\)
amp
, \(T=\)period
, and \(\phi=\)phase
, applies the midpoint sampling strategy to generate a discrete pulse sampled from the continuous function:\[f(x) = A \left(-2\left|\text{sawtooth}(x, A, T, \phi)\right| + 1\right)\]This a non-sinusoidal wave with linear ramping.
버전 0.25.0_pending부터 폐지됨: The function
qiskit.pulse.library.discrete.triangle()
is pending deprecation as of qiskit-terra 0.25.0. It will be marked deprecated in a future release, and then removed no earlier than 3 months after the release date. The discrete pulses library, including triangle() is pending deprecation. Instead, use the SymbolicPulse library to create the waveform with pulse.Triangle(…).get_waveform(). Note that pulse.Triangle() does not support complex values for amp. Instead, use two float values for (amp, angle).- 매개변수:
- 반환 형식:
예제
import matplotlib.pyplot as plt from qiskit.pulse.library import triangle import numpy as np duration = 100 amp = 1 freq = 1 / duration triangle_wave = np.real(triangle(duration, amp, freq).samples) plt.plot(range(duration), triangle_wave) plt.show()
- qiskit.pulse.library.cos(duration, amp, freq=None, phase=0, name=None)[소스]#
Generates cosine wave
Waveform
.For \(A=\)
amp
, \(\omega=\)freq
, and \(\phi=\)phase
, applies the midpoint sampling strategy to generate a discrete pulse sampled from the continuous function:\[f(x) = A \cos(2 \pi \omega x + \phi)\]버전 0.25.0_pending부터 폐지됨: The function
qiskit.pulse.library.discrete.cos()
is pending deprecation as of qiskit-terra 0.25.0. It will be marked deprecated in a future release, and then removed no earlier than 3 months after the release date. The discrete pulses library, including cos() is pending deprecation. Instead, use the SymbolicPulse library to create the waveform with pulse.Cos(…).get_waveform(). Note that pulse.Cos() does not support complex values for amp. Instead, use two float values for (amp, angle).
- qiskit.pulse.library.sin(duration, amp, freq=None, phase=0, name=None)[소스]#
Generates sine wave
Waveform
.For \(A=\)
amp
, \(\omega=\)freq
, and \(\phi=\)phase
, applies the midpoint sampling strategy to generate a discrete pulse sampled from the continuous function:\[f(x) = A \sin(2 \pi \omega x + \phi)\]버전 0.25.0_pending부터 폐지됨: The function
qiskit.pulse.library.discrete.sin()
is pending deprecation as of qiskit-terra 0.25.0. It will be marked deprecated in a future release, and then removed no earlier than 3 months after the release date. The discrete pulses library, including sin() is pending deprecation. Instead, use the SymbolicPulse library to create the waveform with pulse.Sin(…).get_waveform(). Note that pulse.Sin() does not support complex values for amp. Instead, use two float values for (amp, angle).
- qiskit.pulse.library.gaussian(duration, amp, sigma, name=None, zero_ends=True)[소스]#
Generates unnormalized gaussian
Waveform
.For \(A=\)
amp
and \(\sigma=\)sigma
, applies themidpoint
sampling strategy to generate a discrete pulse sampled from the continuous function:\[f(x) = A\exp\left(\left(\frac{x - \mu}{2\sigma}\right)^2 \right),\]with the center \(\mu=\)
duration/2
.If
zero_ends==True
, each output sample \(y\) is modified according to:\[y \mapsto A\frac{y-y^*}{A-y^*},\]where \(y^*\) is the value of the endpoint samples. This sets the endpoints to \(0\) while preserving the amplitude at the center. If \(A=y^*\), \(y\) is set to \(1\). By default, the endpoints are at
x = -1, x = duration + 1
.Integrated area under the full curve is
amp * np.sqrt(2*np.pi*sigma**2)
버전 0.25.0_pending부터 폐지됨: The function
qiskit.pulse.library.discrete.gaussian()
is pending deprecation as of qiskit-terra 0.25.0. It will be marked deprecated in a future release, and then removed no earlier than 3 months after the release date. The discrete pulses library, including gaussian() is pending deprecation. Instead, use the SymbolicPulse library to create the waveform with pulse.Gaussian(…).get_waveform(). Note that complex value support for the amp parameter is pending deprecation in the SymbolicPulse library. It is therefore recommended to use two float values for (amp, angle) instead of complex amp- 매개변수:
- 반환 형식:
- qiskit.pulse.library.gaussian_deriv(duration, amp, sigma, name=None)[소스]#
Generates unnormalized gaussian derivative
Waveform
.For \(A=\)
amp
and \(\sigma=\)sigma
applies the midpoint sampling strategy to generate a discrete pulse sampled from the continuous function:\[f(x) = -A\frac{(x - \mu)}{\sigma^2}\exp \left(-\frac{1}{2}\left(\frac{x - \mu}{\sigma}\right)^2 \right)\]i.e. the derivative of the Gaussian function, with center \(\mu=\)
duration/2
.버전 0.25.0_pending부터 폐지됨: The function
qiskit.pulse.library.discrete.gaussian_deriv()
is pending deprecation as of qiskit-terra 0.25.0. It will be marked deprecated in a future release, and then removed no earlier than 3 months after the release date. The discrete pulses library, including gaussian_deriv() is pending deprecation. Instead, use the SymbolicPulse library to create the waveform with pulse.GaussianDeriv(…).get_waveform(). Note that pulse.GaussianDeriv() does not support complex values for amp. Instead, use two float values for (amp, angle).
- qiskit.pulse.library.sech(duration, amp, sigma, name=None, zero_ends=True)[소스]#
Generates unnormalized sech
Waveform
.For \(A=\)
amp
and \(\sigma=\)sigma
, applies themidpoint
sampling strategy to generate a discrete pulse sampled from the continuous function:\[f(x) = A\text{sech}\left(\frac{x-\mu}{\sigma} \right)\]with the center \(\mu=\)
duration/2
.If
zero_ends==True
, each output sample \(y\) is modified according to:\[y \mapsto A\frac{y-y^*}{A-y^*},\]where \(y^*\) is the value of the endpoint samples. This sets the endpoints to \(0\) while preserving the amplitude at the center. If \(A=y^*\), \(y\) is set to \(1\). By default, the endpoints are at
x = -1, x = duration + 1
.버전 0.25.0_pending부터 폐지됨: The function
qiskit.pulse.library.discrete.sech()
is pending deprecation as of qiskit-terra 0.25.0. It will be marked deprecated in a future release, and then removed no earlier than 3 months after the release date. The discrete pulses library, including sech() is pending deprecation. Instead, use the SymbolicPulse library to create the waveform with pulse.Sech(…).get_waveform(). Note that pulse.Sech() does not support complex values for amp. Instead, use two float values for (amp, angle).- 매개변수:
- 반환 형식:
- qiskit.pulse.library.sech_deriv(duration, amp, sigma, name=None)[소스]#
Generates unnormalized sech derivative
Waveform
.For \(A=\)
amp
, \(\sigma=\)sigma
, and center \(\mu=\)duration/2
, applies the midpoint sampling strategy to generate a discrete pulse sampled from the continuous function:\[f(x) = \frac{d}{dx}\left[A\text{sech}\left(\frac{x-\mu}{\sigma} \right)\right],\]i.e. the derivative of \(\text{sech}\).
버전 0.25.0_pending부터 폐지됨: The function
qiskit.pulse.library.discrete.sech_deriv()
is pending deprecation as of qiskit-terra 0.25.0. It will be marked deprecated in a future release, and then removed no earlier than 3 months after the release date. The discrete pulses library, including sech_deriv() is pending deprecation. Instead, use the SymbolicPulse library to create the waveform with pulse.SechDeriv(…).get_waveform(). Note that pulse.SechDeriv() does not support complex values for amp. Instead, use two float values for (amp, angle).
- qiskit.pulse.library.gaussian_square(duration, amp, sigma, risefall=None, width=None, name=None, zero_ends=True)[소스]#
Generates gaussian square
Waveform
.For \(d=\)
duration
, \(A=\)amp
, \(\sigma=\)sigma
, and \(r=\)risefall
, applies themidpoint
sampling strategy to generate a discrete pulse sampled from the continuous function:\[\begin{split}f(x) = \begin{cases} g(x - r) ) & x\leq r \\ A & r\leq x\leq d-r \\ g(x - (d - r)) & d-r\leq x \end{cases}\end{split}\]where \(g(x)\) is the Gaussian function sampled from in
gaussian()
with \(A=\)amp
, \(\mu=1\), and \(\sigma=\)sigma
. I.e. \(f(x)\) represents a square pulse with smooth Gaussian edges.If
zero_ends == True
, the samples for the Gaussian ramps are remapped as ingaussian()
.버전 0.25.0_pending부터 폐지됨: The function
qiskit.pulse.library.discrete.gaussian_square()
is pending deprecation as of qiskit-terra 0.25.0. It will be marked deprecated in a future release, and then removed no earlier than 3 months after the release date. The discrete pulses library, including gaussian_square() is pending deprecation. Instead, use the SymbolicPulse library to create the waveform with pulse.GaussianSquare(…).get_waveform(). Note that complex value support for the amp parameter is pending deprecation in the SymbolicPulse library. It is therefore recommended to use two float values for (amp, angle) instead of complex amp- 매개변수:
duration (int) – Duration of pulse. Must be greater than zero.
amp (complex) – Pulse amplitude.
sigma (float) – Width (standard deviation) of Gaussian rise/fall portion of the pulse.
risefall (float | None) – Number of samples over which pulse rise and fall happen. Width of square portion of pulse will be
duration-2*risefall
.width (float | None) – The duration of the embedded square pulse. Only one of
width
orrisefall
should be specified as the functional form requireswidth = duration - 2 * risefall
.name (str | None) – Name of pulse.
zero_ends (bool) – If True, zero ends at
x = -1, x = duration + 1
, but rescale to preserve amp.
- 예외 발생:
PulseError – If
risefall
andwidth
arguments are inconsistent or not enough info.- 반환 형식:
- qiskit.pulse.library.drag(duration, amp, sigma, beta, name=None, zero_ends=True)[소스]#
Generates Y-only correction DRAG
Waveform
for standard nonlinear oscillator (SNO) [1].For \(A=\)
amp
, \(\sigma=\)sigma
, and \(\beta=\)beta
, applies themidpoint
sampling strategy to generate a discrete pulse sampled from the continuous function:\[f(x) = g(x) + i \beta h(x),\]where \(g(x)\) is the function sampled in
gaussian()
, and \(h(x)\) is the function sampled ingaussian_deriv()
.If
zero_ends == True
, the samples from \(g(x)\) are remapped as ingaussian()
.버전 0.25.0_pending부터 폐지됨: The function
qiskit.pulse.library.discrete.drag()
is pending deprecation as of qiskit-terra 0.25.0. It will be marked deprecated in a future release, and then removed no earlier than 3 months after the release date. The discrete pulses library, including drag() is pending deprecation. Instead, use the SymbolicPulse library to create the waveform with pulse.Drag(…).get_waveform(). Note that complex value support for the amp parameter is pending deprecation in the SymbolicPulse library. It is therefore recommended to use two float values for (amp, angle) instead of complex amp참조
- 매개변수:
duration (int) – Duration of pulse. Must be greater than zero.
amp (complex) – Pulse amplitude at center
duration/2
.sigma (float) – Width (standard deviation) of pulse.
beta (float) – Y correction amplitude. For the SNO this is \(\beta=-\frac{\lambda_1^2}{4\Delta_2}\). Where \(\lambda_1\) is the relative coupling strength between the first excited and second excited states and \(\Delta_2\) is the detuning between the respective excited states.
name (str | None) – Name of pulse.
zero_ends (bool) – If True, zero ends at
x = -1, x = duration + 1
, but rescale to preserve amp.
- 반환 형식:
Parametric Pulse Representation#
|
A simple constant pulse, with an amplitude value and a duration: |
|
The Derivative Removal by Adiabatic Gate (DRAG) pulse is a standard Gaussian pulse with an additional Gaussian derivative component and lifting applied. |
|
A lifted and truncated pulse envelope shaped according to the Gaussian function whose mean is centered at the center of the pulse (duration / 2): |
|
A square pulse with a Gaussian shaped risefall on both sides lifted such that its first sample is zero. |
|
A square pulse with a Drag shaped rise and fall |
|
An echoed Gaussian square pulse with an active tone overlaid on it. |
|
An unnormalized Gaussian derivative pulse. |
|
A sinusoidal pulse. |
|
A cosine pulse. |
|
A sawtooth pulse. |
|
A triangle wave pulse. |
|
A square wave pulse. |
|
An unnormalized sech pulse. |
|
An unnormalized sech derivative pulse. |
Channels (qiskit.pulse.channels
)#
Pulse is meant to be agnostic to the underlying hardware implementation, while still allowing low-level control. Therefore, our signal channels are virtual hardware channels. The backend which executes our programs is responsible for mapping these virtual channels to the proper physical channel within the quantum control hardware.
Channels are characterized by their type and their index. Channels include:
transmit channels, which should subclass
PulseChannel
receive channels, such as
AcquireChannel
non-signal “channels” such as
SnapshotChannel
,MemorySlot
andRegisterChannel
.
Novel channel types can often utilize the ControlChannel
, but if this is not sufficient,
new channel types can be created. Then, they must be supported in the PulseQobj schema and the
assembler. Channels are characterized by their type and their index. See each channel type below to
learn more.
|
Drive channels transmit signals to qubits which enact gate operations. |
|
Measure channels transmit measurement stimulus pulses for readout. |
|
Acquire channels are used to collect data. |
|
Control channels provide supplementary control over the qubit to the drive channel. |
|
Classical resister slot channels represent classical registers (low-latency classical memory). |
|
Memory slot channels represent classical memory storage. |
|
Snapshot channels are used to specify instructions for simulators. |
All channels are children of the same abstract base class:
- class qiskit.pulse.channels.Channel(*args, **kwargs)[소스]#
Base class of channels. Channels provide a Qiskit-side label for typical quantum control hardware signal channels. The final label -> physical channel mapping is the responsibility of the hardware backend. For instance,
DriveChannel(0)
holds instructions which the backend should map to the signal line driving gate operations on the qubit labeled (indexed) 0.When serialized channels are identified by their serialized name
<prefix><index>
. The type of the channel is interpreted from the prefix, and the index often (but not always) maps to the qubit index. All concrete channel classes must have aprefix
class attribute (and instances of that class have an index attribute). Base classes which haveprefix
set toNone
are prevented from being instantiated.To implement a new channel inherit from
Channel
and provide a unique string identifier for theprefix
class attribute.Channel class.
- 매개변수:
index – Index of channel.
Schedules#
Schedules are Pulse programs. They describe instruction sequences for the control hardware.
The Schedule is one of the most fundamental objects to this pulse-level programming module.
A Schedule
is a representation of a program in Pulse. Each schedule tracks the time of each
instruction occuring in parallel over multiple signal channels.
|
A quantum program schedule with exact time constraints for its instructions, operating over all input signal channels and supporting special syntaxes for building. |
|
Time-ordered sequence of instructions with alignment context. |
Pulse Transforms (qiskit.pulse.transforms
)#
The pulse transforms provide transformation routines to reallocate and optimize pulse programs for backends.
Alignments#
The alignment transforms define alignment policies of instructions in ScheduleBlock
.
These transformations are called to create Schedule
s from ScheduleBlock
s.
|
Align instructions with equispaced interval within a specified duration. |
|
Allocate instructions at position specified by callback function. |
Align instructions in as-soon-as-possible manner. |
|
Align instructions in as-late-as-possible manner. |
|
Align instructions sequentially. |
These are all subtypes of the abstract base class AlignmentKind
.
Canonicalization#
The canonicalization transforms convert schedules to a form amenable for execution on OpenPulse backends.
- qiskit.pulse.transforms.add_implicit_acquires(schedule, meas_map)[소스]#
Return a new schedule with implicit acquires from the measurement mapping replaced by explicit ones.
경고
Since new acquires are being added, Memory Slots will be set to match the qubit index. This may overwrite your specification.
- qiskit.pulse.transforms.align_measures(schedules, inst_map=None, cal_gate='u3', max_calibration_duration=None, align_time=None, align_all=True)[소스]#
Return new schedules where measurements occur at the same physical time.
This transformation will align the first
Acquire
on every channel to occur at the same time.Minimum measurement wait time (to allow for calibration pulses) is enforced and may be set with
max_calibration_duration
.By default only instructions containing a
AcquireChannel
orMeasureChannel
will be shifted. If you wish to keep the relative timing of all instructions in the schedule setalign_all=True
.This method assumes that
MeasureChannel(i)
andAcquireChannel(i)
correspond to the same qubit and the acquire/play instructions should be shifted together on these channels.from qiskit import pulse from qiskit.pulse import transforms d0 = pulse.DriveChannel(0) m0 = pulse.MeasureChannel(0) a0 = pulse.AcquireChannel(0) mem0 = pulse.MemorySlot(0) sched = pulse.Schedule() sched.append(pulse.Play(pulse.Constant(10, 0.5), d0), inplace=True) sched.append(pulse.Play(pulse.Constant(10, 1.), m0).shift(sched.duration), inplace=True) sched.append(pulse.Acquire(20, a0, mem0).shift(sched.duration), inplace=True) sched_shifted = sched << 20 aligned_sched, aligned_sched_shifted = transforms.align_measures([sched, sched_shifted]) assert aligned_sched == aligned_sched_shifted
If it is desired to only shift acquisition and measurement stimulus instructions set the flag
align_all=False
:aligned_sched, aligned_sched_shifted = transforms.align_measures( [sched, sched_shifted], align_all=False, ) assert aligned_sched != aligned_sched_shifted
- 매개변수:
schedules (Iterable[Schedule | Instruction]) – Collection of schedules to be aligned together
inst_map (InstructionScheduleMap | None) – Mapping of circuit operations to pulse schedules
cal_gate (str) – The name of the gate to inspect for the calibration time
max_calibration_duration (int | None) – If provided, inst_map and cal_gate will be ignored
align_time (int | None) – If provided, this will be used as final align time.
align_all (bool | None) – Shift all instructions in the schedule such that they maintain their relative alignment with the shifted acquisition instruction. If
False
only the acquisition and measurement pulse instructions will be shifted.
- 반환:
The input list of schedules transformed to have their measurements aligned.
- 예외 발생:
PulseError – If the provided alignment time is negative.
- 반환 형식:
- qiskit.pulse.transforms.block_to_schedule(block)[소스]#
Convert
ScheduleBlock
toSchedule
.- 매개변수:
block (ScheduleBlock) – A
ScheduleBlock
to convert.- 반환:
Scheduled pulse program.
- 예외 발생:
UnassignedDurationError – When any instruction duration is not assigned.
PulseError – When the alignment context duration is shorter than the schedule duration.
- 반환 형식:
참고
This transform may insert barriers in between contexts.
- qiskit.pulse.transforms.compress_pulses(schedules)[소스]#
Optimization pass to replace identical pulses.
- qiskit.pulse.transforms.flatten(program)[소스]#
Flatten (inline) any called nodes into a Schedule tree with no nested children.
- 매개변수:
program (Schedule) – Pulse program to remove nested structure.
- 반환:
Flatten pulse program.
- 예외 발생:
PulseError – When invalid data format is given.
- 반환 형식:
- qiskit.pulse.transforms.inline_subroutines(program)[소스]#
Recursively remove call instructions and inline the respective subroutine instructions.
Assigned parameter values, which are stored in the parameter table, are also applied. The subroutine is copied before the parameter assignment to avoid mutation problem.
- 매개변수:
program (Schedule | ScheduleBlock) – A program which may contain the subroutine, i.e.
Call
instruction.- 반환:
A schedule without subroutine.
- 예외 발생:
PulseError – When input program is not valid data format.
- 반환 형식:
- qiskit.pulse.transforms.pad(schedule, channels=None, until=None, inplace=False, pad_with=None)[소스]#
Pad the input Schedule with
Delay``s on all unoccupied timeslots until ``schedule.duration
oruntil
if notNone
.- 매개변수:
schedule (Schedule) – Schedule to pad.
channels (Iterable[Channel] | None) – Channels to pad. Defaults to all channels in
schedule
if not provided. If the supplied channel is not a member ofschedule
it will be added.until (int | None) – Time to pad until. Defaults to
schedule.duration
if not provided.inplace (bool) – Pad this schedule by mutating rather than returning a new schedule.
pad_with (Type[Instruction] | None) – Pulse
Instruction
subclass to be used for padding. Default toDelay
instruction.
- 반환:
The padded schedule.
- 예외 발생:
PulseError – When non pulse instruction is set to pad_with.
- 반환 형식:
DAG#
The DAG transforms create DAG representation of input program. This can be used for optimization of instructions and equality checks.
- qiskit.pulse.transforms.block_to_dag(block)[소스]#
Convert schedule block instruction into DAG.
ScheduleBlock
can be represented as a DAG as needed. For example, equality of two programs are efficiently checked on DAG representation.with pulse.build() as sched1: with pulse.align_left(): pulse.play(my_gaussian0, pulse.DriveChannel(0)) pulse.shift_phase(1.57, pulse.DriveChannel(2)) pulse.play(my_gaussian1, pulse.DriveChannel(1)) with pulse.build() as sched2: with pulse.align_left(): pulse.shift_phase(1.57, pulse.DriveChannel(2)) pulse.play(my_gaussian1, pulse.DriveChannel(1)) pulse.play(my_gaussian0, pulse.DriveChannel(0))
Here the
sched1 `` and ``sched2
are different implementations of the same program, but it is difficult to confirm on the list representation.Another example is instruction optimization.
with pulse.build() as sched: with pulse.align_left(): pulse.shift_phase(1.57, pulse.DriveChannel(1)) pulse.play(my_gaussian0, pulse.DriveChannel(0)) pulse.shift_phase(-1.57, pulse.DriveChannel(1))
In above program two
shift_phase
instructions can be cancelled out because they are consecutive on the same drive channel. This can be easily found on the DAG representation.- 매개변수:
block ("ScheduleBlock") – A schedule block to be converted.
- 반환:
Instructions in DAG representation.
- 예외 발생:
PulseError – When the context is invalid subclass.
- 반환 형식:
Composite transform#
A sequence of transformations to generate a target code.
- qiskit.pulse.transforms.target_qobj_transform(sched, remove_directives=True)[소스]#
A basic pulse program transformation for OpenPulse API execution.
- 매개변수:
sched (ScheduleBlock | Schedule | Tuple[int, Instruction] | Instruction | Iterable[Tuple[int, Instruction] | Instruction]) – Input program to transform.
remove_directives (bool) – Set True to remove compiler directives.
- 반환:
Transformed program for execution.
- 반환 형식:
Pulse Builder#
Use the pulse builder DSL to write pulse programs with an imperative syntax.
경고
The pulse builder interface is still in active development. It may have breaking API changes without deprecation warnings in future releases until otherwise indicated.
The pulse builder provides an imperative API for writing pulse programs
with less difficulty than the Schedule
API.
It contextually constructs a pulse schedule and then emits the schedule for
execution. For example, to play a series of pulses on channels is as simple as:
from qiskit import pulse
dc = pulse.DriveChannel
d0, d1, d2, d3, d4 = dc(0), dc(1), dc(2), dc(3), dc(4)
with pulse.build(name='pulse_programming_in') as pulse_prog:
pulse.play([1, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 1, 1], d0)
pulse.play([1, 0, 1, 0, 0, 0, 1, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0], d1)
pulse.play([1, 0, 1, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0], d2)
pulse.play([1, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 1, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0], d3)
pulse.play([1, 1, 1, 1, 0, 1, 1, 1, 0, 1, 1, 1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 0, 1, 0], d4)
pulse_prog.draw()

To begin pulse programming we must first initialize our program builder
context with build()
, after which we can begin adding program
statements. For example, below we write a simple program that play()
s
a pulse:
from qiskit import execute, pulse
d0 = pulse.DriveChannel(0)
with pulse.build() as pulse_prog:
pulse.play(pulse.Constant(100, 1.0), d0)
pulse_prog.draw()

The builder initializes a pulse.Schedule
, pulse_prog
and then begins to construct the program within the context. The output pulse
schedule will survive after the context is exited and can be executed like a
normal Qiskit schedule using qiskit.execute(pulse_prog, backend)
.
Pulse programming has a simple imperative style. This leaves the programmer to worry about the raw experimental physics of pulse programming and not constructing cumbersome data structures.
We can optionally pass a Backend
to
build()
to enable enhanced functionality. Below, we prepare a Bell state
by automatically compiling the required pulses from their gate-level
representations, while simultaneously applying a long decoupling pulse to a
neighboring qubit. We terminate the experiment with a measurement to observe the
state we prepared. This program which mixes circuits and pulses will be
automatically lowered to be run as a pulse program:
import math
from qiskit import pulse
from qiskit.providers.fake_provider import FakeOpenPulse3Q
# TODO: This example should use a real mock backend.
backend = FakeOpenPulse3Q()
d2 = pulse.DriveChannel(2)
with pulse.build(backend) as bell_prep:
pulse.u2(0, math.pi, 0)
pulse.cx(0, 1)
with pulse.build(backend) as decoupled_bell_prep_and_measure:
# We call our bell state preparation schedule constructed above.
with pulse.align_right():
pulse.call(bell_prep)
pulse.play(pulse.Constant(bell_prep.duration, 0.02), d2)
pulse.barrier(0, 1, 2)
registers = pulse.measure_all()
decoupled_bell_prep_and_measure.draw()

With the pulse builder we are able to blend programming on qubits and channels. While the pulse schedule is based on instructions that operate on channels, the pulse builder automatically handles the mapping from qubits to channels for you.
In the example below we demonstrate some more features of the pulse builder:
import math
from qiskit import pulse, QuantumCircuit
from qiskit.pulse import library
from qiskit.providers.fake_provider import FakeOpenPulse2Q
backend = FakeOpenPulse2Q()
with pulse.build(backend) as pulse_prog:
# Create a pulse.
gaussian_pulse = library.gaussian(10, 1.0, 2)
# Get the qubit's corresponding drive channel from the backend.
d0 = pulse.drive_channel(0)
d1 = pulse.drive_channel(1)
# Play a pulse at t=0.
pulse.play(gaussian_pulse, d0)
# Play another pulse directly after the previous pulse at t=10.
pulse.play(gaussian_pulse, d0)
# The default scheduling behavior is to schedule pulses in parallel
# across channels. For example, the statement below
# plays the same pulse on a different channel at t=0.
pulse.play(gaussian_pulse, d1)
# We also provide pulse scheduling alignment contexts.
# The default alignment context is align_left.
# The sequential context schedules pulse instructions sequentially in time.
# This context starts at t=10 due to earlier pulses above.
with pulse.align_sequential():
pulse.play(gaussian_pulse, d0)
# Play another pulse after at t=20.
pulse.play(gaussian_pulse, d1)
# We can also nest contexts as each instruction is
# contained in its local scheduling context.
# The output of a child context is a context-schedule
# with the internal instructions timing fixed relative to
# one another. This is schedule is then called in the parent context.
# Context starts at t=30.
with pulse.align_left():
# Start at t=30.
pulse.play(gaussian_pulse, d0)
# Start at t=30.
pulse.play(gaussian_pulse, d1)
# Context ends at t=40.
# Alignment context where all pulse instructions are
# aligned to the right, ie., as late as possible.
with pulse.align_right():
# Shift the phase of a pulse channel.
pulse.shift_phase(math.pi, d1)
# Starts at t=40.
pulse.delay(100, d0)
# Ends at t=140.
# Starts at t=130.
pulse.play(gaussian_pulse, d1)
# Ends at t=140.
# Acquire data for a qubit and store in a memory slot.
pulse.acquire(100, 0, pulse.MemorySlot(0))
# We also support a variety of macros for common operations.
# Measure all qubits.
pulse.measure_all()
# Delay on some qubits.
# This requires knowledge of which channels belong to which qubits.
# delay for 100 cycles on qubits 0 and 1.
pulse.delay_qubits(100, 0, 1)
# Call a quantum circuit. The pulse builder lazily constructs a quantum
# circuit which is then transpiled and scheduled before inserting into
# a pulse schedule.
# NOTE: Quantum register indices correspond to physical qubit indices.
qc = QuantumCircuit(2, 2)
qc.cx(0, 1)
pulse.call(qc)
# Calling a small set of standard gates and decomposing to pulses is
# also supported with more natural syntax.
pulse.u3(0, math.pi, 0, 0)
pulse.cx(0, 1)
# It is also be possible to call a preexisting schedule
tmp_sched = pulse.Schedule()
tmp_sched += pulse.Play(gaussian_pulse, d0)
pulse.call(tmp_sched)
# We also support:
# frequency instructions
pulse.set_frequency(5.0e9, d0)
# phase instructions
pulse.shift_phase(0.1, d0)
# offset contexts
with pulse.phase_offset(math.pi, d0):
pulse.play(gaussian_pulse, d0)
The above is just a small taste of what is possible with the builder. See the rest of the module documentation for more information on its capabilities.
- qiskit.pulse.builder.build(backend=None, schedule=None, name=None, default_alignment='left', default_transpiler_settings=None, default_circuit_scheduler_settings=None)[소스]#
Create a context manager for launching the imperative pulse builder DSL.
To enter a building context and starting building a pulse program:
from qiskit import execute, pulse from qiskit.providers.fake_provider import FakeOpenPulse2Q backend = FakeOpenPulse2Q() d0 = pulse.DriveChannel(0) with pulse.build() as pulse_prog: pulse.play(pulse.Constant(100, 0.5), d0)
While the output program
pulse_prog
cannot be executed as we are using a mock backend. If a real backend is being used, executing the program is done with:qiskit.execute(pulse_prog, backend)
- 매개변수:
backend (Backend) – A Qiskit backend. If not supplied certain builder functionality will be unavailable.
schedule (ScheduleBlock | None) – A pulse
ScheduleBlock
in which your pulse program will be built.name (str | None) – Name of pulse program to be built.
default_alignment (str | AlignmentKind | None) – Default scheduling alignment for builder. One of
left
,right
,sequential
or an alignment context.default_transpiler_settings (Dict[str, Any] | None) – Default settings for the transpiler.
default_circuit_scheduler_settings (Dict[str, Any] | None) – Default settings for the circuit to pulse scheduler.
- 반환:
A new builder context which has the active builder initialized.
- 반환 형식:
AbstractContextManager[ScheduleBlock]
Channels#
Methods to return the correct channels for the respective qubit indices.
from qiskit import pulse
from qiskit.providers.fake_provider import FakeArmonk
backend = FakeArmonk()
with pulse.build(backend) as drive_sched:
d0 = pulse.drive_channel(0)
print(d0)
DriveChannel(0)
- qiskit.pulse.builder.acquire_channel(qubit)[소스]#
Return
AcquireChannel
forqubit
on the active builder backend.Examples:
from qiskit import pulse from qiskit.providers.fake_provider import FakeOpenPulse2Q backend = FakeOpenPulse2Q() with pulse.build(backend): assert pulse.acquire_channel(0) == pulse.AcquireChannel(0)
참고
Requires the active builder context to have a backend set.
- 반환 형식:
- qiskit.pulse.builder.control_channels(*qubits)[소스]#
Return
ControlChannel
forqubit
on the active builder backend.Return the secondary drive channel for the given qubit – typically utilized for controlling multi-qubit interactions.
Examples:
from qiskit import pulse from qiskit.providers.fake_provider import FakeOpenPulse2Q backend = FakeOpenPulse2Q() with pulse.build(backend): assert pulse.control_channels(0, 1) == [pulse.ControlChannel(0)]
참고
Requires the active builder context to have a backend set.
- qiskit.pulse.builder.drive_channel(qubit)[소스]#
Return
DriveChannel
forqubit
on the active builder backend.Examples:
from qiskit import pulse from qiskit.providers.fake_provider import FakeOpenPulse2Q backend = FakeOpenPulse2Q() with pulse.build(backend): assert pulse.drive_channel(0) == pulse.DriveChannel(0)
참고
Requires the active builder context to have a backend set.
- 반환 형식:
- qiskit.pulse.builder.measure_channel(qubit)[소스]#
Return
MeasureChannel
forqubit
on the active builder backend.Examples:
from qiskit import pulse from qiskit.providers.fake_provider import FakeOpenPulse2Q backend = FakeOpenPulse2Q() with pulse.build(backend): assert pulse.measure_channel(0) == pulse.MeasureChannel(0)
참고
Requires the active builder context to have a backend set.
- 반환 형식:
Instructions#
Pulse instructions are available within the builder interface. Here’s an example:
from qiskit import pulse
from qiskit.providers.fake_provider import FakeArmonk
backend = FakeArmonk()
with pulse.build(backend) as drive_sched:
d0 = pulse.drive_channel(0)
a0 = pulse.acquire_channel(0)
pulse.play(pulse.library.Constant(10, 1.0), d0)
pulse.delay(20, d0)
pulse.shift_phase(3.14/2, d0)
pulse.set_phase(3.14, d0)
pulse.shift_frequency(1e7, d0)
pulse.set_frequency(5e9, d0)
with pulse.build() as temp_sched:
pulse.play(pulse.library.Gaussian(20, 1.0, 3.0), d0)
pulse.play(pulse.library.Gaussian(20, -1.0, 3.0), d0)
pulse.call(temp_sched)
pulse.acquire(30, a0, pulse.MemorySlot(0))
drive_sched.draw()

- qiskit.pulse.builder.acquire(duration, qubit_or_channel, register, **metadata)[소스]#
Acquire for a
duration
on achannel
and store the result in aregister
.Examples:
from qiskit import pulse acq0 = pulse.AcquireChannel(0) mem0 = pulse.MemorySlot(0) with pulse.build() as pulse_prog: pulse.acquire(100, acq0, mem0) # measurement metadata kernel = pulse.configuration.Kernel('linear_discriminator') pulse.acquire(100, acq0, mem0, kernel=kernel)
참고
The type of data acquire will depend on the execution
meas_level
.- 매개변수:
duration (int) – Duration to acquire data for
qubit_or_channel (int | AcquireChannel) – Either the qubit to acquire data for or the specific
AcquireChannel
to acquire on.register (StorageLocation) – Location to store measured result.
metadata (Kernel | Discriminator) – Additional metadata for measurement. See
Acquire
for more information.
- 예외 발생:
exceptions.PulseError – If the register type is not supported.
- qiskit.pulse.builder.barrier(*channels_or_qubits, name=None)[소스]#
Barrier directive for a set of channels and qubits.
This directive prevents the compiler from moving instructions across the barrier. Consider the case where we want to enforce that one pulse happens after another on separate channels, this can be done with:
from qiskit import pulse from qiskit.providers.fake_provider import FakeOpenPulse2Q backend = FakeOpenPulse2Q() d0 = pulse.DriveChannel(0) d1 = pulse.DriveChannel(1) with pulse.build(backend) as barrier_pulse_prog: pulse.play(pulse.Constant(10, 1.0), d0) pulse.barrier(d0, d1) pulse.play(pulse.Constant(10, 1.0), d1)
Of course this could have been accomplished with:
from qiskit.pulse import transforms with pulse.build(backend) as aligned_pulse_prog: with pulse.align_sequential(): pulse.play(pulse.Constant(10, 1.0), d0) pulse.play(pulse.Constant(10, 1.0), d1) barrier_pulse_prog = transforms.target_qobj_transform(barrier_pulse_prog) aligned_pulse_prog = transforms.target_qobj_transform(aligned_pulse_prog) assert barrier_pulse_prog == aligned_pulse_prog
The barrier allows the pulse compiler to take care of more advanced scheduling alignment operations across channels. For example in the case where we are calling an outside circuit or schedule and want to align a pulse at the end of one call:
import math d0 = pulse.DriveChannel(0) with pulse.build(backend) as pulse_prog: with pulse.align_right(): pulse.x(1) # Barrier qubit 1 and d0. pulse.barrier(1, d0) # Due to barrier this will play before the gate on qubit 1. pulse.play(pulse.Constant(10, 1.0), d0) # This will end at the same time as the pulse above due to # the barrier. pulse.x(1)
참고
Requires the active builder context to have a backend set if qubits are barriered on.
- qiskit.pulse.builder.call(target, name=None, value_dict=None, **kw_params)[소스]#
Call the subroutine within the currently active builder context with arbitrary parameters which will be assigned to the target program.
참고
If the
target
program is aScheduleBlock
, then aReference
instruction will be created and appended to the current context. Thetarget
program will be immediately assigned to the current scope as a subroutine. If thetarget
program isSchedule
, it will be wrapped by theCall
instruction and appended to the current context to avoid a mixed representation ofScheduleBlock
andSchedule
. If thetarget
program is aQuantumCircuit
it will be scheduled and the newSchedule
will be added as aCall
instruction.예제
Calling a schedule block (recommended)
from qiskit import circuit, pulse from qiskit.providers.fake_provider import FakeBogotaV2 backend = FakeBogotaV2() with pulse.build() as x_sched: pulse.play(pulse.Gaussian(160, 0.1, 40), pulse.DriveChannel(0)) with pulse.build() as pulse_prog: pulse.call(x_sched) print(pulse_prog)
ScheduleBlock( ScheduleBlock( Play( Gaussian(duration=160, amp=(0.1+0j), sigma=40), DriveChannel(0) ), name="block0", transform=AlignLeft() ), name="block1", transform=AlignLeft() )
The actual program is stored in the reference table attached to the schedule.
print(pulse_prog.references)
ReferenceManager: - ('block0', '634b3b50bd684e26a673af1fbd2d6c81'): ScheduleBlock(Play(Gaussian(...
In addition, you can call a parameterized target program with parameter assignment.
amp = circuit.Parameter("amp") with pulse.build() as subroutine: pulse.play(pulse.Gaussian(160, amp, 40), pulse.DriveChannel(0)) with pulse.build() as pulse_prog: pulse.call(subroutine, amp=0.1) pulse.call(subroutine, amp=0.3) print(pulse_prog)
ScheduleBlock( ScheduleBlock( Play( Gaussian(duration=160, amp=(0.1+0j), sigma=40), DriveChannel(0) ), name="block2", transform=AlignLeft() ), ScheduleBlock( Play( Gaussian(duration=160, amp=(0.3+0j), sigma=40), DriveChannel(0) ), name="block2", transform=AlignLeft() ), name="block3", transform=AlignLeft() )
If there is a name collision between parameters, you can distinguish them by specifying each parameter object in a python dictionary. For example,
amp1 = circuit.Parameter('amp') amp2 = circuit.Parameter('amp') with pulse.build() as subroutine: pulse.play(pulse.Gaussian(160, amp1, 40), pulse.DriveChannel(0)) pulse.play(pulse.Gaussian(160, amp2, 40), pulse.DriveChannel(1)) with pulse.build() as pulse_prog: pulse.call(subroutine, value_dict={amp1: 0.1, amp2: 0.3}) print(pulse_prog)
ScheduleBlock( ScheduleBlock( Play(Gaussian(duration=160, amp=(0.1+0j), sigma=40), DriveChannel(0)), Play(Gaussian(duration=160, amp=(0.3+0j), sigma=40), DriveChannel(1)), name="block4", transform=AlignLeft() ), name="block5", transform=AlignLeft() )
Calling a schedule
x_sched = backend.instruction_schedule_map.get("x", (0,)) with pulse.build(backend) as pulse_prog: pulse.call(x_sched) print(pulse_prog)
ScheduleBlock( Call( Schedule( ( 0, Play( Drag( duration=160, amp=(0.18989731546729305+0j), sigma=40, beta=-1.201258305015517, name='drag_86a8' ), DriveChannel(0), name='drag_86a8' ) ), name="x" ), name='x' ), name="block6", transform=AlignLeft() )
Currently, the backend calibrated gates are provided in the form of
Schedule
. The parameter assignment mechanism is available also for schedules. However, the called schedule is not treated as a reference.Calling a quantum circuit
backend = FakeBogotaV2() qc = circuit.QuantumCircuit(1) qc.x(0) with pulse.build(backend) as pulse_prog: pulse.call(qc) print(pulse_prog)
ScheduleBlock( Call( Schedule( ( 0, Play( Drag( duration=160, amp=(0.18989731546729305+0j), sigma=40, beta=-1.201258305015517, name='drag_86a8' ), DriveChannel(0), name='drag_86a8' ) ), name="circuit-87" ), name='circuit-87' ), name="block7", transform=AlignLeft() )
경고
Calling a circuit from a schedule is not encouraged. Currently, the Qiskit execution model is migrating toward the pulse gate model, where schedules are attached to circuits through the
QuantumCircuit.add_calibration()
method.- 매개변수:
target (QuantumCircuit | Schedule | ScheduleBlock | None) – Target circuit or pulse schedule to call.
name (str | None) – Optional. A unique name of subroutine if defined. When the name is explicitly provided, one cannot call different schedule blocks with the same name.
value_dict (Dict[ParameterExpression | float, ParameterExpression | float] | None) – Optional. Parameters assigned to the
target
program. If this dictionary is provided, thetarget
program is copied and then stored in the main built schedule and its parameters are assigned to the given values. This dictionary is keyed onParameter
objects, allowing parameter name collision to be avoided.kw_params (ParameterExpression | float) – Alternative way to provide parameters. Since this is keyed on the string parameter name, the parameters having the same name are all updated together. If you want to avoid name collision, use
value_dict
withParameter
objects instead.
- qiskit.pulse.builder.delay(duration, channel, name=None)[소스]#
Delay on a
channel
for aduration
.Examples:
from qiskit import pulse d0 = pulse.DriveChannel(0) with pulse.build() as pulse_prog: pulse.delay(10, d0)
- qiskit.pulse.builder.play(pulse, channel, name=None)[소스]#
Play a
pulse
on achannel
.Examples:
from qiskit import pulse d0 = pulse.DriveChannel(0) with pulse.build() as pulse_prog: pulse.play(pulse.Constant(10, 1.0), d0)
- qiskit.pulse.builder.reference(name, *extra_keys)[소스]#
Refer to undefined subroutine by string keys.
A
Reference
instruction is implicitly created and a schedule can be separately registered to the reference at a later stage.from qiskit import pulse with pulse.build() as main_prog: pulse.reference("x_gate", "q0") with pulse.build() as subroutine: pulse.play(pulse.Gaussian(160, 0.1, 40), pulse.DriveChannel(0)) main_prog.assign_references(subroutine_dict={("x_gate", "q0"): subroutine})
- qiskit.pulse.builder.set_frequency(frequency, channel, name=None)[소스]#
Set the
frequency
of a pulsechannel
.Examples:
from qiskit import pulse d0 = pulse.DriveChannel(0) with pulse.build() as pulse_prog: pulse.set_frequency(1e9, d0)
- qiskit.pulse.builder.set_phase(phase, channel, name=None)[소스]#
Set the
phase
of a pulsechannel
.Examples:
import math from qiskit import pulse d0 = pulse.DriveChannel(0) with pulse.build() as pulse_prog: pulse.set_phase(math.pi, d0)
- qiskit.pulse.builder.shift_frequency(frequency, channel, name=None)[소스]#
Shift the
frequency
of a pulsechannel
.Examples:
from qiskit import pulse d0 = pulse.DriveChannel(0) with pulse.build() as pulse_prog: pulse.shift_frequency(1e9, d0)
Contexts#
Builder aware contexts that modify the construction of a pulse program. For
example an alignment context like align_right()
may
be used to align all pulses as late as possible in a pulse program.
from qiskit import pulse
d0 = pulse.DriveChannel(0)
d1 = pulse.DriveChannel(1)
with pulse.build() as pulse_prog:
with pulse.align_right():
# this pulse will start at t=0
pulse.play(pulse.Constant(100, 1.0), d0)
# this pulse will start at t=80
pulse.play(pulse.Constant(20, 1.0), d1)
pulse_prog.draw()

- qiskit.pulse.builder.align_equispaced(duration)[소스]#
Equispaced alignment pulse scheduling context.
Pulse instructions within this context are scheduled with the same interval spacing such that the total length of the context block is
duration
. If the total freeduration
cannot be evenly divided by the number of instructions within the context, the modulo is split and then prepended and appended to the returned schedule. Delay instructions are automatically inserted in between pulses.This context is convenient to write a schedule for periodical dynamic decoupling or the Hahn echo sequence.
Examples:
from qiskit import pulse d0 = pulse.DriveChannel(0) x90 = pulse.Gaussian(10, 0.1, 3) x180 = pulse.Gaussian(10, 0.2, 3) with pulse.build() as hahn_echo: with pulse.align_equispaced(duration=100): pulse.play(x90, d0) pulse.play(x180, d0) pulse.play(x90, d0) hahn_echo.draw()
- 매개변수:
duration (int | ParameterExpression) – Duration of this context. This should be larger than the schedule duration.
- 생성:
None
- 반환 형식:
참고
The scheduling is performed for sub-schedules within the context rather than channel-wise. If you want to apply the equispaced context for each channel, you should use the context independently for channels.
- qiskit.pulse.builder.align_func(duration, func)[소스]#
Callback defined alignment pulse scheduling context.
Pulse instructions within this context are scheduled at the location specified by arbitrary callback function position that takes integer index and returns the associated fractional location within [0, 1]. Delay instruction is automatically inserted in between pulses.
This context may be convenient to write a schedule of arbitrary dynamical decoupling sequences such as Uhrig dynamical decoupling.
Examples:
import numpy as np from qiskit import pulse d0 = pulse.DriveChannel(0) x90 = pulse.Gaussian(10, 0.1, 3) x180 = pulse.Gaussian(10, 0.2, 3) def udd10_pos(j): return np.sin(np.pi*j/(2*10 + 2))**2 with pulse.build() as udd_sched: pulse.play(x90, d0) with pulse.align_func(duration=300, func=udd10_pos): for _ in range(10): pulse.play(x180, d0) pulse.play(x90, d0) udd_sched.draw()
- 매개변수:
duration (int | ParameterExpression) – Duration of context. This should be larger than the schedule duration.
func (Callable[[int], float]) – A function that takes an index of sub-schedule and returns the fractional coordinate of of that sub-schedule. The returned value should be defined within [0, 1]. The pulse index starts from 1.
- 생성:
None
- 반환 형식:
참고
The scheduling is performed for sub-schedules within the context rather than channel-wise. If you want to apply the numerical context for each channel, you need to apply the context independently to channels.
- qiskit.pulse.builder.align_left()[소스]#
Left alignment pulse scheduling context.
Pulse instructions within this context are scheduled as early as possible by shifting them left to the earliest available time.
Examples:
from qiskit import pulse d0 = pulse.DriveChannel(0) d1 = pulse.DriveChannel(1) with pulse.build() as pulse_prog: with pulse.align_left(): # this pulse will start at t=0 pulse.play(pulse.Constant(100, 1.0), d0) # this pulse will start at t=0 pulse.play(pulse.Constant(20, 1.0), d1) pulse_prog = pulse.transforms.block_to_schedule(pulse_prog) assert pulse_prog.ch_start_time(d0) == pulse_prog.ch_start_time(d1)
- 생성:
None
- 반환 형식:
AbstractContextManager[None]
- qiskit.pulse.builder.align_right()[소스]#
Right alignment pulse scheduling context.
Pulse instructions within this context are scheduled as late as possible by shifting them right to the latest available time.
Examples:
from qiskit import pulse d0 = pulse.DriveChannel(0) d1 = pulse.DriveChannel(1) with pulse.build() as pulse_prog: with pulse.align_right(): # this pulse will start at t=0 pulse.play(pulse.Constant(100, 1.0), d0) # this pulse will start at t=80 pulse.play(pulse.Constant(20, 1.0), d1) pulse_prog = pulse.transforms.block_to_schedule(pulse_prog) assert pulse_prog.ch_stop_time(d0) == pulse_prog.ch_stop_time(d1)
- 생성:
None
- 반환 형식:
- qiskit.pulse.builder.align_sequential()[소스]#
Sequential alignment pulse scheduling context.
Pulse instructions within this context are scheduled sequentially in time such that no two instructions will be played at the same time.
Examples:
from qiskit import pulse d0 = pulse.DriveChannel(0) d1 = pulse.DriveChannel(1) with pulse.build() as pulse_prog: with pulse.align_sequential(): # this pulse will start at t=0 pulse.play(pulse.Constant(100, 1.0), d0) # this pulse will also start at t=100 pulse.play(pulse.Constant(20, 1.0), d1) pulse_prog = pulse.transforms.block_to_schedule(pulse_prog) assert pulse_prog.ch_stop_time(d0) == pulse_prog.ch_start_time(d1)
- 생성:
None
- 반환 형식:
- qiskit.pulse.builder.circuit_scheduler_settings(**settings)[소스]#
Set the currently active circuit scheduler settings for this context.
Examples:
from qiskit import pulse from qiskit.providers.fake_provider import FakeOpenPulse2Q backend = FakeOpenPulse2Q() with pulse.build(backend): print(pulse.active_circuit_scheduler_settings()) with pulse.circuit_scheduler_settings(method='alap'): print(pulse.active_circuit_scheduler_settings())
{} {'method': 'alap'}
- 반환 형식:
AbstractContextManager[None]
- qiskit.pulse.builder.frequency_offset(frequency, *channels, compensate_phase=False)[소스]#
Shift the frequency of inputs channels on entry into context and undo on exit.
Examples:
from qiskit import pulse d0 = pulse.DriveChannel(0) with pulse.build(backend) as pulse_prog: # shift frequency by 1GHz with pulse.frequency_offset(1e9, d0): pulse.play(pulse.Constant(10, 1.0), d0) assert len(pulse_prog.instructions) == 3 with pulse.build(backend) as pulse_prog: # Shift frequency by 1GHz. # Undo accumulated phase in the shifted frequency frame # when exiting the context. with pulse.frequency_offset(1e9, d0, compensate_phase=True): pulse.play(pulse.Constant(10, 1.0), d0) assert len(pulse_prog.instructions) == 4
- qiskit.pulse.builder.phase_offset(phase, *channels)[소스]#
Shift the phase of input channels on entry into context and undo on exit.
Examples:
import math from qiskit import pulse d0 = pulse.DriveChannel(0) with pulse.build() as pulse_prog: with pulse.phase_offset(math.pi, d0): pulse.play(pulse.Constant(10, 1.0), d0) assert len(pulse_prog.instructions) == 3
- 매개변수:
phase (float) – Amount of phase offset in radians.
channels (PulseChannel) – Channels to offset phase of.
- 생성:
None
- 반환 형식:
AbstractContextManager[None]
- qiskit.pulse.builder.transpiler_settings(**settings)[소스]#
Set the currently active transpiler settings for this context.
Examples:
from qiskit import pulse from qiskit.providers.fake_provider import FakeOpenPulse2Q backend = FakeOpenPulse2Q() with pulse.build(backend): print(pulse.active_transpiler_settings()) with pulse.transpiler_settings(optimization_level=3): print(pulse.active_transpiler_settings())
{} {'optimization_level': 3}
- 반환 형식:
AbstractContextManager[None]
Macros#
Macros help you add more complex functionality to your pulse program.
from qiskit import pulse
from qiskit.providers.fake_provider import FakeArmonk
backend = FakeArmonk()
with pulse.build(backend) as measure_sched:
mem_slot = pulse.measure(0)
print(mem_slot)
MemorySlot(0)
- qiskit.pulse.builder.measure(qubits, registers=None)[소스]#
Measure a qubit within the currently active builder context.
At the pulse level a measurement is composed of both a stimulus pulse and an acquisition instruction which tells the systems measurement unit to acquire data and process it. We provide this measurement macro to automate the process for you, but if desired full control is still available with
acquire()
andplay()
.To use the measurement it is as simple as specifying the qubit you wish to measure:
from qiskit import pulse from qiskit.providers.fake_provider import FakeOpenPulse2Q backend = FakeOpenPulse2Q() qubit = 0 with pulse.build(backend) as pulse_prog: # Do something to the qubit. qubit_drive_chan = pulse.drive_channel(0) pulse.play(pulse.Constant(100, 1.0), qubit_drive_chan) # Measure the qubit. reg = pulse.measure(qubit)
For now it is not possible to do much with the handle to
reg
but in the future we will support using this handle to a result register to build up ones program. It is also possible to supply this register:with pulse.build(backend) as pulse_prog: pulse.play(pulse.Constant(100, 1.0), qubit_drive_chan) # Measure the qubit. mem0 = pulse.MemorySlot(0) reg = pulse.measure(qubit, mem0) assert reg == mem0
참고
Requires the active builder context to have a backend set.
- 매개변수:
- 반환:
The
register
the qubit measurement result will be stored in.- 반환 형식:
List[StorageLocation] | StorageLocation
- qiskit.pulse.builder.measure_all()[소스]#
Measure all qubits within the currently active builder context.
A simple macro function to measure all of the qubits in the device at the same time. This is useful for handling device
meas_map
and single measurement constraints.Examples:
from qiskit import pulse from qiskit.providers.fake_provider import FakeOpenPulse2Q backend = FakeOpenPulse2Q() with pulse.build(backend) as pulse_prog: # Measure all qubits and return associated registers. regs = pulse.measure_all()
참고
Requires the active builder context to have a backend set.
- 반환:
The
register
s the qubit measurement results will be stored in.- 반환 형식:
- qiskit.pulse.builder.delay_qubits(duration, *qubits)[소스]#
Insert delays on all of the
channels.Channel
s that correspond to the inputqubits
at the same time.Examples:
from qiskit import pulse from qiskit.providers.fake_provider import FakeOpenPulse3Q backend = FakeOpenPulse3Q() with pulse.build(backend) as pulse_prog: # Delay for 100 cycles on qubits 0, 1 and 2. regs = pulse.delay_qubits(100, 0, 1, 2)
참고
Requires the active builder context to have a backend set.
Circuit Gates#
To use circuit level gates within your pulse program call a circuit
with call()
.
경고
These will be removed in future versions with the release of a circuit builder interface in which it will be possible to calibrate a gate in terms of pulses and use that gate in a circuit.
import math
from qiskit import pulse
from qiskit.providers.fake_provider import FakeArmonk
backend = FakeArmonk()
with pulse.build(backend) as u3_sched:
pulse.u3(math.pi, 0, math.pi, 0)
- qiskit.pulse.builder.cx(control, target)[소스]#
Call a
CXGate
on the input physical qubits.참고
Calling gates directly within the pulse builder namespace will be deprecated in the future in favor of tight integration with a circuit builder interface which is under development.
Examples:
from qiskit import pulse from qiskit.providers.fake_provider import FakeOpenPulse2Q backend = FakeOpenPulse2Q() with pulse.build(backend) as pulse_prog: pulse.cx(0, 1)
- qiskit.pulse.builder.u1(theta, qubit)[소스]#
Call a
U1Gate
on the input physical qubit.참고
Calling gates directly within the pulse builder namespace will be deprecated in the future in favor of tight integration with a circuit builder interface which is under development.
Examples:
import math from qiskit import pulse from qiskit.providers.fake_provider import FakeOpenPulse2Q backend = FakeOpenPulse2Q() with pulse.build(backend) as pulse_prog: pulse.u1(math.pi, 1)
- qiskit.pulse.builder.u2(phi, lam, qubit)[소스]#
Call a
U2Gate
on the input physical qubit.참고
Calling gates directly within the pulse builder namespace will be deprecated in the future in favor of tight integration with a circuit builder interface which is under development.
Examples:
import math from qiskit import pulse from qiskit.providers.fake_provider import FakeOpenPulse2Q backend = FakeOpenPulse2Q() with pulse.build(backend) as pulse_prog: pulse.u2(0, math.pi, 1)
- qiskit.pulse.builder.u3(theta, phi, lam, qubit)[소스]#
Call a
U3Gate
on the input physical qubit.참고
Calling gates directly within the pulse builder namespace will be deprecated in the future in favor of tight integration with a circuit builder interface which is under development.
Examples:
import math from qiskit import pulse from qiskit.providers.fake_provider import FakeOpenPulse2Q backend = FakeOpenPulse2Q() with pulse.build(backend) as pulse_prog: pulse.u3(math.pi, 0, math.pi, 1)
- qiskit.pulse.builder.x(qubit)[소스]#
Call a
XGate
on the input physical qubit.참고
Calling gates directly within the pulse builder namespace will be deprecated in the future in favor of tight integration with a circuit builder interface which is under development.
Examples:
from qiskit import pulse from qiskit.providers.fake_provider import FakeOpenPulse2Q backend = FakeOpenPulse2Q() with pulse.build(backend) as pulse_prog: pulse.x(0)
Utilities#
The utility functions can be used to gather attributes about the backend and modify how the program is built.
from qiskit import pulse
from qiskit.providers.fake_provider import FakeArmonk
backend = FakeArmonk()
with pulse.build(backend) as u3_sched:
print('Number of qubits in backend: {}'.format(pulse.num_qubits()))
samples = 160
print('There are {} samples in {} seconds'.format(
samples, pulse.samples_to_seconds(160)))
seconds = 1e-6
print('There are {} seconds in {} samples.'.format(
seconds, pulse.seconds_to_samples(1e-6)))
Number of qubits in backend: 1
There are 160 samples in 3.5555555555555554e-08 seconds
There are 1e-06 seconds in 4500 samples.
- qiskit.pulse.builder.active_backend()[소스]#
Get the backend of the currently active builder context.
- 반환:
- The active backend in the currently active
builder context.
- 반환 형식:
- 예외 발생:
exceptions.BackendNotSet – If the builder does not have a backend set.
- qiskit.pulse.builder.active_transpiler_settings()[소스]#
Return the current active builder context’s transpiler settings.
Examples:
from qiskit import pulse from qiskit.providers.fake_provider import FakeOpenPulse2Q backend = FakeOpenPulse2Q() transpiler_settings = {'optimization_level': 3} with pulse.build(backend, default_transpiler_settings=transpiler_settings): print(pulse.active_transpiler_settings())
{'optimization_level': 3}
- qiskit.pulse.builder.active_circuit_scheduler_settings()[소스]#
Return the current active builder context’s circuit scheduler settings.
Examples:
from qiskit import pulse from qiskit.providers.fake_provider import FakeOpenPulse2Q backend = FakeOpenPulse2Q() circuit_scheduler_settings = {'method': 'alap'} with pulse.build( backend, default_circuit_scheduler_settings=circuit_scheduler_settings): print(pulse.active_circuit_scheduler_settings())
{'method': 'alap'}
- qiskit.pulse.builder.num_qubits()[소스]#
Return number of qubits in the currently active backend.
Examples:
from qiskit import pulse from qiskit.providers.fake_provider import FakeOpenPulse2Q backend = FakeOpenPulse2Q() with pulse.build(backend): print(pulse.num_qubits())
2
참고
Requires the active builder context to have a backend set.
- 반환 형식:
- qiskit.pulse.builder.qubit_channels(qubit)[소스]#
Returns the set of channels associated with a qubit.
Examples:
from qiskit import pulse from qiskit.providers.fake_provider import FakeOpenPulse2Q backend = FakeOpenPulse2Q() with pulse.build(backend): print(pulse.qubit_channels(0))
{MeasureChannel(0), ControlChannel(0), DriveChannel(0), AcquireChannel(0), ControlChannel(1)}
참고
Requires the active builder context to have a backend set.
참고
A channel may still be associated with another qubit in this list such as in the case where significant crosstalk exists.
Configuration#
Mapping from |
Exceptions#
- exception qiskit.pulse.PulseError(*message)[소스]#
Errors raised by the pulse module.
Set the error message.
- exception qiskit.pulse.BackendNotSet(*message)[소스]#
Raised if the builder context does not have a backend.
Set the error message.
- exception qiskit.pulse.NoActiveBuilder(*message)[소스]#
Raised if no builder context is active.
Set the error message.