Quantum Instance Migration Guide#
The QuantumInstance
is a utility class that allows the joint
configuration of the circuit transpilation and execution steps, and provides functions
at a higher level of abstraction for a more convenient integration with algorithms.
These include measurement error mitigation, splitting/combining execution to
conform to job limits,
and ensuring reliable execution of circuits with additional job management tools.
The QuantumInstance
is being deprecated for several reasons:
On one hand, the functionality of execute()
has
now been delegated to the different implementations of the primitives
base classes.
On the other hand, with the direct implementation of transpilation at the primitives level,
the algorithms no longer
need to manage that aspect of execution, and thus transpile()
is no longer
required by the workflow. If desired, custom transpilation routines can still be performed at the
user level through the transpiler
module (see table below).
The following table summarizes the migration alternatives for the QuantumInstance
class:
Método QuantumInstance |
Alternativa |
---|---|
|
|
The remainder of this guide will focus on the QuantumInstance.execute()
to
primitives
migration path.
Contenido#
Atención
Background on the Qiskit Primitives
The Qiskit Primitives are algorithmic abstractions that encapsulate the access to backends or simulators for an easy integration into algorithm workflows.
The current pool of primitives includes two different types of primitives: Sampler and Estimator.
Qiskit provides reference implementations in qiskit.primitives.Sampler
and qiskit.primitives.Estimator
. Additionally,
qiskit.primitives.BackendSampler
and a qiskit.primitives.BackendEstimator
are
wrappers for backend.run()
that follow the primitives interface.
Providers can implement these primitives as subclasses of BaseSampler
and BaseEstimator
respectively.
IBM’s Qiskit Runtime (qiskit_ibm_runtime
) and Aer (qiskit_aer.primitives
) are examples of native implementations of primitives.
This guide uses the following naming convention:
Primitives - Any Sampler/Estimator implementation using base classes
qiskit.primitives.BackendSampler
and aqiskit.primitives.BackendEstimator
.Reference Primitives -
qiskit.primitives.Sampler
andqiskit.primitives.Estimator
are reference implementations that come with Qiskit.Aer Primitives - The Aer primitive implementations
qiskit_aer.primitives.Sampler
andqiskit_aer.primitives.Estimator
.Qiskit Runtime Primitives - IBM’s Qiskit Runtime primitive implementations
qiskit_ibm_runtime.Sampler
andqiskit_ibm_runtime.Estimator
.Backend Primitives - Instances of
qiskit.primitives.BackendSampler
andqiskit.primitives.BackendEstimator
. These allow any backend to implement primitive interfaces
For guidelines on which primitives to choose for your task, please continue reading.
Choosing the right primitive for your task#
The QuantumInstance
was designed to be an abstraction over transpile/run.
It took inspiration from execute()
, but retained config information that could be set
at the algorithm level, to save the user from defining the same parameters for every transpile/execute call.
The qiskit.primitives
share some of these features, but unlike the QuantumInstance
,
there are multiple primitive classes, and each is optimized for a specific
purpose. Selecting the right primitive (Sampler
or Estimator
) requires some knowledge about
what it is expected to do and where/how it is expected to run.
Nota
The role of the primitives is two-fold. On one hand, they act as access points to backends and simulators. On the other hand, they are algorithmic abstractions with defined tasks:
The
Estimator
takes in circuits and observables and returns expectation values.The
Sampler
takes in circuits, measures them, and returns their quasi-probability distributions.
In order to know which primitive to use instead of QuantumInstance
, you should ask
yourself two questions:
- What is the minimal unit of information used by your algorithm?
Expectation value - you will need an
Estimator
Probability distribution (from sampling the device) - you will need a
Sampler
How do you want to execute your circuits?
This question is not new. In the legacy algorithm workflow, you would have to decide to set up a
QuantumInstance
with either a real backend from a provider, or a simulator. Now, this «backend selection» process is translated to where do you import your primitives from:Using local statevector simulators for quick prototyping: Reference Primitives
Using local noisy simulations for finer algorithm tuning: Aer Primitives
Accessing runtime-enabled backends (or cloud simulators): Qiskit Runtime Primitives
Accessing non runtime-enabled backends : Backend Primitives
Arguably, the Sampler
is the closest primitive to QuantumInstance
, as they
both execute circuits and provide a result back. However, with the QuantumInstance
,
the result data was backend dependent (it could be a counts dict
, a numpy.array
for
statevector simulations, etc), while the Sampler
normalizes its SamplerResult
to
return a QuasiDistribution
object with the resulting quasi-probability distribution.
The Estimator
provides a specific abstraction for the expectation value calculation that can replace
the use of QuantumInstance
as well as the associated pre- and post-processing steps, usually performed
with an additional library such as qiskit.opflow
.
Choosing the right primitive for your settings#
Certain QuantumInstance
features are only available in certain primitive implementations.
The following table summarizes the most common QuantumInstance
settings and which
primitives expose a similar setting through their interface:
Atención
In some cases, a setting might not be exposed through the interface, but there might an alternative path to make
it work. This is the case for custom transpiler passes, which cannot be set through the primitives interface,
but pre-transpiled circuits can be sent if setting the option skip_transpilation=True
. For more information,
please refer to the API reference or source code of the desired primitive implementation.
QuantumInstance |
Primitivas de Referencia |
Primitivas de Aer |
Qiskit Runtime Primitives |
Primitivas de Backend |
---|---|---|---|---|
Seleccionar |
No |
No |
Si |
Si |
Establecer |
Si |
Si |
Si |
Si |
Configuraciones del simulador: |
No |
Si |
Si |
No (inferred from internal |
Transpiler settings: |
No |
No |
Yes (via |
Yes (via |
Set unbound |
No |
No |
No (but can |
No (but can |
Establecer |
No |
No |
No |
Si |
Set |
No |
No |
No (only |
No |
Measurement error mitigation: |
No |
No |
Sampler default -> M3 (*) |
No |
Administración de trabajos (job): |
No aplica |
No aplica |
Sessions, callback (**) |
No |
(*) For more information on error mitigation and setting options on Qiskit Runtime Primitives, visit this link.
(**) For more information on Runtime sessions, visit this how-to.