Skip to content

Execution Tutorial - Part 1

View on GitHub

This tutorial covers the basics of executing a quantum program using Classiq directly through the Python SDK. It is also possible to use the Classiq Platform to execute quantum algorithms.

For this, we will start by synthesizing the following example from the synthesis tutorial:

from classiq import *


@qfunc
def main(x: Output[QNum[3]], y: Output[QNum]) -> None:
    allocate(x)
    hadamard_transform(x)
    y |= x**2 + 1


qprog = synthesize(main)
show(qprog)
Quantum program link: https://platform.classiq.io/circuit/30HuOnn0LwUGqLIKMlUETImaIfc

This quantum program evaluates the function \(y(x) = x^2 + 1\), for all integers \(x \in [0,7]\). To execute a quantum program and save its results in the Python SDK, create an ExecutionSession. To sample the states using this object, one can use sample:

with ExecutionSession(qprog) as es:
    results = es.sample()
gio: https://platform.classiq.io/circuit/30HuOnn0LwUGqLIKMlUETImaIfc?login=True&version=0.86.1: Operation not supported

The information from the outputs of the quantum program can be obtained in the form of a dataframe using the dataframe attribute:

results.dataframe
x y count probability bitstring
0 1 2 285 0.139160 000010001
1 7 50 262 0.127930 110010111
2 5 26 260 0.126953 011010101
3 4 17 254 0.124023 010001100
4 2 5 253 0.123535 000101010
5 6 37 251 0.122559 100101110
6 3 10 249 0.121582 001010011
7 0 1 234 0.114258 000001000

The information displayed in the dataframe is:

  • counts shows the number of times each state was measured.

  • bitstring is the bitstring that represents each state measured.

  • x and y are the numerical representation of the states associated with the measurement.

  • probability is the probability associated with each measured state.

By default, the number of executions of the quantum program is \(2048\). This quantity, called the number of shots, can be modified using ExecutionPreferences. For instance, if we want to execute the same circuit with \(10{,}000\) shots:

prefs_more_shots = ExecutionPreferences(num_shots=10000)

with ExecutionSession(qprog, execution_preferences=prefs_more_shots) as es:
    results_more_shots = es.sample()

The number of counts for each state will grow proportionally with the number of shots:

results_more_shots.dataframe
x y count probability bitstring
0 7 50 1274 0.1274 110010111
1 2 5 1273 0.1273 000101010
2 1 2 1267 0.1267 000010001
3 6 37 1266 0.1266 100101110
4 4 17 1254 0.1254 010001100
5 5 26 1226 0.1226 011010101
6 3 10 1224 0.1224 001010011
7 0 1 1216 0.1216 000001000

Backend selection

The backend of an execution is the hardware or simulator where the quantum program is executed. To select a specific backend, it is necessary to use its correct Backend Preferences. Check the different Cloud Providers and their backend preferences for execution.

In this section, we will explore two different examples for clarification:

First example: Execution using the state vector simulator from Classiq

A state vector simulator outputs the amplitudes of a quantum program. On real hardware, obtaining these amplitudes requires quantum tomography — the process of measuring in different bases to reconstruct the output state.

Since Classiq provides its own state vector simulator backend, we will use ClassiqBackendPreferences to define it as the state vector simulator. This information is provided on the Cloud Providers page.

To define the quantum program's execution preferences, use execution_preferences under ExecutionSession. In this example, we will perform a simulation with num_shots=1 since the state vector simulator performs an exact simulation of the quantum program.

If no backend is defined in the preferences, then the Classiq simulator is selected by default.

backend_preferences = ClassiqBackendPreferences(
    backend_name="simulator_statevector"
)  # Always check the Cloud Providers to correctly define the backend.

execution_preferences = ExecutionPreferences(
    num_shots=1, backend_preferences=backend_preferences
)

Now, execute the quantum program using execute.

with ExecutionSession(qprog, execution_preferences=execution_preferences) as es:
    results_statevector = es.sample()

The outputs of the quantum program can be displayed using the dataframe property:

results_statevector.dataframe.head()
x y amplitude probability bitstring
0 7 18 3.923208e-15+2.775558e- 17j 1.539233e-29 010010111
1 0 33 3.014272e-15+0.000000e+ 00j 9.085836e-30 100001000
2 4 49 1.538630e-15-5.551115e- 17j 2.370465e-30 110001100
3 3 42 1.303117e-15+2.775558e- 17j 1.698883e-30 101010011
4 5 58 1.185360e-15+1.387779e- 16j 1.424337e-30 111010101

The outputs from the execution obtained via statevector simulator will differ from the default simulator:

  • state_vector will output a dict containing the bitstrings followed by its numerically evaluated amplitudes.

  • parsed_state_vector will output a list of SimulatedState, each containing the values of x and y followed by its bitstrings and its numerically evaluated amplitudes.