Inégalité CHSH
Estimation d'utilisation : deux minutes sur un processeur Heron r2 (REMARQUE : il s'agit uniquement d'une estimation. Ton temps d'exécution peut varier.)
Contexte
Dans ce tutoriel, tu vas exécuter une expérience sur un ordinateur quantique pour démontrer la violation de l'inégalité CHSH avec la primitive Estimator.
L'inégalité CHSH, nommée d'après ses auteurs Clauser, Horne, Shimony et Holt, est utilisée pour prouver expérimentalement le théorème de Bell (1969). Ce théorème affirme que les théories à variables cachées locales ne peuvent pas rendre compte de certaines conséquences de l'intrication en mécanique quantique. La violation de l'inégalité CHSH est utilisée pour montrer que la mécanique quantique est incompatible avec les théories à variables cachées locales. Il s'agit d'une expérience importante pour comprendre les fondements de la mécanique quantique.
Le prix Nobel de physique 2022 a été décerné à Alain Aspect, John Clauser et Anton Zeilinger en partie pour leurs travaux pionniers en science de l'information quantique, et en particulier pour leurs expériences avec des photons intriqués démontrant la violation des inégalités de Bell.
Prérequis
Avant de commencer ce tutoriel, assure-toi que les éléments suivants sont installés :
- Qiskit SDK v1.0 ou version ultérieure, avec le support de visualisation
- Qiskit Runtime (
pip install qiskit-ibm-runtime) v0.22 ou version ultérieure
Configuration
# Added by doQumentation — required packages for this notebook
!pip install -q matplotlib numpy qiskit qiskit-ibm-runtime
# General
import numpy as np
# Qiskit imports
from qiskit import QuantumCircuit
from qiskit.circuit import Parameter
from qiskit.quantum_info import SparsePauliOp
from qiskit.transpiler.preset_passmanagers import generate_preset_pass_manager
# Qiskit Runtime imports
from qiskit_ibm_runtime import QiskitRuntimeService
from qiskit_ibm_runtime import EstimatorV2 as Estimator
# Plotting routines
import matplotlib.pyplot as plt
import matplotlib.ticker as tck
Étape 1 : Formuler les entrées classiques en un problème quantique
Pour cette expérience, nous allons créer une paire intriquée sur laquelle nous mesurerons chaque qubit dans deux bases différentes. Nous désignerons les bases du premier qubit par et , et les bases du second qubit par et . Cela nous permet de calculer la quantité CHSH :
Chaque observable vaut soit , soit . De toute évidence, l'un des termes doit être , et l'autre doit être . Par conséquent, . La valeur moyenne de doit satisfaire l'inégalité :
En développant en fonction de , , et , on obtient :
Tu peux définir une autre quantité CHSH :
Cela conduit à une autre inégalité :
Si la mécanique quantique peut être décrite par des théories à variables cachées locales, les inégalités précédentes doivent être vérifiées. Cependant, comme le démontre ce tutoriel, ces inégalités peuvent être violées sur un ordinateur quantique. Par conséquent, la mécanique quantique n'est pas compatible avec les théories à variables cachées locales. Si tu souhaites approfondir la théorie, explore l'intrication en action avec John Watrous. Tu vas créer une paire intriquée entre deux qubits dans un ordinateur quantique en créant l'état de Bell . En utilisant la primitive Estimator, tu peux obtenir directement les valeurs d'espérance nécessaires ( et ) pour calculer les valeurs d'espérance des deux quantités CHSH et . Avant l'introduction de la primitive Estimator, il fallait construire les valeurs d'espérance à partir des résultats de mesure.
Tu mesureras le second qubit dans les bases et . Le premier qubit sera également mesuré dans des bases orthogonales, mais avec un angle par rapport au second qubit, que nous allons faire varier entre et . Comme tu le verras, la primitive Estimator rend l'exécution de circuits paramétrés très facile. Plutôt que de créer une série de circuits CHSH, tu n'as besoin de créer qu'un seul circuit CHSH avec un paramètre spécifiant l'angle de mesure et une série de valeurs de phase pour ce paramètre.
Enfin, tu analyseras les résultats et les traceras en fonction de l'angle de mesure. Tu verras que pour certaines plages d'angles de mesure, les valeurs d'espérance des quantités CHSH ou , ce qui démontre la violation de l'inégalité CHSH.
# To run on hardware, select the backend with the fewest number of jobs in the queue
service = QiskitRuntimeService()
backend = service.least_busy(
operational=True, simulator=False, min_num_qubits=127
)
backend.name
'ibm_kingston'
Créer un circuit CHSH paramétré
Tout d'abord, nous écrivons le circuit avec le paramètre , que nous appelons theta. La primitive Estimator peut considérablement simplifier la construction des circuits et l'analyse des résultats en fournissant directement les valeurs d'espérance des observables. De nombreux problèmes d'intérêt, en particulier pour les applications à court terme sur des systèmes bruités, peuvent être formulés en termes de valeurs d'espérance. La primitive Estimator (V2) peut automatiquement changer la base de mesure en fonction de l'observable fourni.
theta = Parameter("$\\theta$")
chsh_circuit = QuantumCircuit(2)
chsh_circuit.h(0)
chsh_circuit.cx(0, 1)
chsh_circuit.ry(theta, 0)
chsh_circuit.draw(output="mpl", idle_wires=False, style="iqp")
Créer une liste de valeurs de phase à assigner ultérieurement
Après avoir créé le circuit CHSH paramétré, tu vas créer une liste de valeurs de phase à assigner au circuit à l'étape suivante. Tu peux utiliser le code suivant pour créer une liste de 21 valeurs de phase allant de à avec un espacement régulier, c'est-à-dire , , , ..., , .
number_of_phases = 21
phases = np.linspace(0, 2 * np.pi, number_of_phases)
# Phases need to be expressed as list of lists in order to work
individual_phases = [[ph] for ph in phases]
Observables
Nous avons maintenant besoin d'observables à partir desquels calculer les valeurs d'espérance. Dans notre cas, nous examinons des bases orthogonales pour chaque qubit, en laissant la rotation paramétrée en du premier qubit balayer la base de mesure de manière quasi continue par rapport à la base du second qubit. Nous choisirons donc les observables , , et .
# <CHSH1> = <AB> - <Ab> + <aB> + <ab> -> <ZZ> - <ZX> + <XZ> + <XX>
observable1 = SparsePauliOp.from_list(
[("ZZ", 1), ("ZX", -1), ("XZ", 1), ("XX", 1)]
)
# <CHSH2> = <AB> + <Ab> - <aB> + <ab> -> <ZZ> + <ZX> - <XZ> + <XX>
observable2 = SparsePauliOp.from_list(
[("ZZ", 1), ("ZX", 1), ("XZ", -1), ("XX", 1)]
)
Étape 2 : Optimiser le problème pour l'exécution sur du matériel quantique
Pour réduire le temps total d'exécution des tâches, les primitives V2 n'acceptent que des circuits et des observables conformes aux instructions et à la connectivité prises en charge par le système cible (appelés circuits et observables ISA, pour Instruction Set Architecture).
Circuit ISA
target = backend.target
pm = generate_preset_pass_manager(target=target, optimization_level=3)
chsh_isa_circuit = pm.run(chsh_circuit)
chsh_isa_circuit.draw(output="mpl", idle_wires=False, style="iqp")
Observables ISA
De même, nous devons transformer les observables pour les rendre compatibles avec le backend avant d'exécuter les tâches avec Runtime Estimator V2. Nous pouvons effectuer cette transformation en utilisant la méthode apply_layout de l'objet SparsePauliOp.
isa_observable1 = observable1.apply_layout(layout=chsh_isa_circuit.layout)
isa_observable2 = observable2.apply_layout(layout=chsh_isa_circuit.layout)
Étape 3 : Exécuter à l'aide des primitives Qiskit
Afin d'exécuter l'ensemble de l'expérience en un seul appel à l'Estimator.
Nous pouvons créer une primitive Qiskit Runtime Estimator pour calculer nos valeurs d'espérance. La méthode EstimatorV2.run() prend un itérable de primitive unified blocs (PUBs). Chaque PUB est un itérable au format (circuit, observables, parameter_values: Optional, precision: Optional).
# To run on a local simulator:
# Use the StatevectorEstimator from qiskit.primitives instead.
estimator = Estimator(mode=backend)
pub = (
chsh_isa_circuit, # ISA circuit
[[isa_observable1], [isa_observable2]], # ISA Observables
individual_phases, # Parameter values
)
job_result = estimator.run(pubs=[pub]).result()
Étape 4 : Post-traiter et renvoyer le résultat dans le format classique souhaité
L'estimateur renvoie les valeurs d'espérance pour les deux observables, et .
chsh1_est = job_result[0].data.evs[0]
chsh2_est = job_result[0].data.evs[1]
fig, ax = plt.subplots(figsize=(10, 6))
# results from hardware
ax.plot(phases / np.pi, chsh1_est, "o-", label="CHSH1", zorder=3)
ax.plot(phases / np.pi, chsh2_est, "o-", label="CHSH2", zorder=3)
# classical bound +-2
ax.axhline(y=2, color="0.9", linestyle="--")
ax.axhline(y=-2, color="0.9", linestyle="--")
# quantum bound, +-2√2
ax.axhline(y=np.sqrt(2) * 2, color="0.9", linestyle="-.")
ax.axhline(y=-np.sqrt(2) * 2, color="0.9", linestyle="-.")
ax.fill_between(phases / np.pi, 2, 2 * np.sqrt(2), color="0.6", alpha=0.7)
ax.fill_between(phases / np.pi, -2, -2 * np.sqrt(2), color="0.6", alpha=0.7)
# set x tick labels to the unit of pi
ax.xaxis.set_major_formatter(tck.FormatStrFormatter("%g $\\pi$"))
ax.xaxis.set_major_locator(tck.MultipleLocator(base=0.5))
# set labels, and legend
plt.xlabel("Theta")
plt.ylabel("CHSH witness")
plt.legend()
plt.show()
Dans la figure, les lignes et les zones grises délimitent les bornes ; les lignes extérieures (en pointillés alternés) délimitent les bornes quantiques (), tandis que les lignes intérieures (en tirets) délimitent les bornes classiques (). Tu peux observer qu'il existe des régions où les quantités témoins CHSH dépassent les bornes classiques. Félicitations ! Tu as démontré avec succès la violation de l'inégalité CHSH dans un véritable système quantique !
Enquête sur le tutoriel
Réponds à cette courte enquête pour nous faire part de tes commentaires sur ce tutoriel. Tes retours nous aideront à améliorer notre contenu et l'expérience utilisateur.