# Cycle benchmarking (CB)¶

This example page breaks down the process of implementing Cycle Benchmarking (CB), including the selection of useful parameters, using True-Qᵀᴹ. While the example uses a simulator to demonstrate how to run CB, the circuits generated by this protocol can also be used to characterize the process fidelity of a dressed cycle (a target cycle preceded by a cycle of random elements of the twirling group) in hardware. For example, see Executing Circuits on Qiskit Providers for information about how use True-Qᵀᴹ to submit circuits to hardware which uses a Qiskit backend.

## Choosing CB Parameters¶

True-Qᵀᴹ’s make_cb() method generates a circuit collection to perform cycle benchmarking. The first arguement required by make_cb() is the cycle to be benchmarked. The second parameter is also a required parameter; the parameter n_random_cycles tells make_cb() how many times to apply the dressed cycle during the protocol.

The number of circuits for each circuit length, n_circuits is 30 by default and should be chosen to optimize the tradeoff between desired speed and accuracy of the estimation.

The number of randomly chosen Pauli decay strings used to measure the process fidelity, n_decays, should be chosen to exceed $$min(20, 4 * n_{qubits} - 1)$$. The default value for n_decays is 20 to satisfy this bound. Choosing a value lower than $$min(20, 4 * n_{qubits} - 1)$$ may result in a biased estimate of the fidelity of the dressed cycle. For this example we eschew this constraint to make the example run faster and the output shorter for easier visualization, and instead let n_decays = 6.

The twirling_group parameter specifies which twirling group the random gates which form the pre-compiled dressed cycles are pulled from. By default, make_cb() uses the Pauli group, "P".

The choice of circuit lengths in n_random_cycles depends on the cycle being characterized as well as the selection of twirling group. If the cycle is a Clifford and the twirling group is "P", lengths should be chosen such that applying the cycle to be benchmarked n_random_cycles times will result in an identity operation. In the example below, we benchmark a cycle containing an X gate and a controlled-Z gate, both of which apply an identity operation when raised to even powers. We therefore choose cycle lengths 4, 12, and 32. While the values of n_random_cycles can be any multiple of 2 for this example, users should be careful to choose a range of values such that the exponential decay is evident in the plot; this will ensure that the fit function gets enough information to accurately estimate the fidelity of the dressed cycle. To validate that this condition has been satisfied, users can plot the data from the CB circuits after running the circuits on a simulator or on hardware to see where the chosen data points fall.

The final parameter is a bool, propagate_correction, which tells make_cb() whether to compile correction gates for the twirling group into neighbouring cycles (propagate_correction = False) or propagate them to the end of the circuit (propagate_correction = True). By default, propagate_correction = False. Warning: propagating correction to the end of the circuit can result in arbitrary two-qubit gates at the end of the circuit! The final circuit can be converted to a user-specified gateset using True-Qᵀᴹ’s Configuration tools.

## Applying Cycle Benchmarking¶

Import True-Qᵀᴹ and initialize a cycle to benchmark:

import trueq as tq

cycle = {(0,): tq.Gate.x, (1, 2): tq.Gate.cz}


Generate a circuit collection to run CB on the above cycle with n_circuits = 30 random circuits for each circuit length in n_random_cycles = [4, 32, 64] and n_decays = 6 randomly chosen Pauli decay strings. For the purpose of demonstrating how to recognize a poor choice of n_random_cycles, we generate a second CB circuit collection with the same parameters, except n_random_cycles = [2, 4, 6]. A good choice of n_random_cycles will result in a lower uncertainty in the fit parameters and therefore a more accurate estimate of the average gate fidelity.

circuits = tq.make_cb(cycle, [4, 12, 32], 30, 6)
bad_circuits = tq.make_cb(cycle, [2, 4, 6], 30, 6)


Initialize a simulator with stochastic pauli noise and run the cycle benchmarking circuits on the simulator to populate the results:

sim = tq.Simulator().add_stochastic_pauli(px=0.01)
sim.run(circuits)
sim.run(bad_circuits)


Plot the results of the circuits with badly chosen n_random_cycles:

bad_circuits.plot.raw(labels=[[0, 1, 2]])


We can see in the plots above that the data points from n_random_cycles are close together, in some cases nearly forming a linear rather than exponential decay. This shows us that the parameters chosen for n_random_cycles are not a good representation of the data. We next plot the decay curves for the CB circuits with n_random_cycles = [4, 32, 64]:

circuits.plot.raw(labels=[[0, 1, 2]])


We can see from the plots above that the chosen n_random_cycles were reasonable for this example as they clearly outline an exponential decay.

The output parameters of this protocol are displayed below using the fit() function. When the circuits were generated, n_decays = 6 random 3-qubit Paulis were chosen as representatives, and the rate of decay of each was measured; these decay rates are reported. However, the parameter of interest is the composite parameter r, which is an estimate of the average gate infidelity of the entire cycle.

circuits.fit(labels=[[0, 1, 2]])

CB on [0, 1, 2]
Name
Estimate
95% CI

Description
r
4.354
[3.625,5.083]
e-02
Process infidelity of the noise map
CB on [0, 1, 2] with decay IXX
Name
Estimate
95% CI

Description
A
0.942
[0.889,0.994]
SPAM of the exponential decay A * p ** m
p
0.961
[0.956,0.966]
Decay rate of the exponential decay A * p ** m
CB on [0, 1, 2] with decay IZI
Name
Estimate
95% CI

Description
A
0.986
[0.946,1.026]
SPAM of the exponential decay A * p ** m
p
0.962
[0.957,0.966]
Decay rate of the exponential decay A * p ** m
CB on [0, 1, 2] with decay XXZ
Name
Estimate
95% CI

Description
A
0.925
[0.888,0.962]
SPAM of the exponential decay A * p ** m
p
0.981
[0.978,0.984]
Decay rate of the exponential decay A * p ** m
CB on [0, 1, 2] with decay YXI
Name
Estimate
95% CI

Description
A
0.912
[0.854,0.969]
SPAM of the exponential decay A * p ** m
p
0.945
[0.936,0.955]
Decay rate of the exponential decay A * p ** m
CB on [0, 1, 2] with decay YXZ
Name
Estimate
95% CI

Description
A
0.890
[0.830,0.951]
SPAM of the exponential decay A * p ** m
p
0.945
[0.936,0.955]
Decay rate of the exponential decay A * p ** m
CB on [0, 1, 2] with decay YZX
Name
Estimate
95% CI

Description
A
0.951
[0.887,1.015]
SPAM of the exponential decay A * p ** m
p
0.945
[0.936,0.953]
Decay rate of the exponential decay A * p ** m

Total running time of the script: ( 0 minutes 6.909 seconds)

Gallery generated by Sphinx-Gallery