Ejecutar trabajos en una sesión
El código de esta página se ha desarrollado siguiendo los siguientes requisitos. Recomendamos utilizar estas versiones o posteriores.
qiskit[all]~=2.3.1 qiskit-ibm-runtime~=0.45.0 scipy~=1.17.1
Los usuarios de Open Plan no pueden enviar trabajos de sesión. Las cargas de trabajo deben ejecutarse en modo trabajo o por lotes.
Utilice las sesiones cuando necesite un acceso dedicado y exclusivo a la QPU.
Configurar para usar sesiones
Antes de iniciar una sesión, debes configurar Qiskit Runtime e inicializarlo como servicio:
from qiskit_ibm_runtime import (
QiskitRuntimeService,
Session,
SamplerV2 as Sampler,
EstimatorV2 as Estimator,
Executor,
)
service = QiskitRuntimeService()Abrir una sesión
Puede abrir una sesión en tiempo de ejecución utilizando el gestor de contexto with Session(...) o inicializando la clase Session clase Al iniciar una sesión, debe especificar una QPU pasando un objeto backend . La sesión se inicia cuando comienza la ejecución de su primer trabajo.
Si abre una sesión pero no le envía ningún trabajo durante 30 minutos, la sesión se cierra automáticamente.
Clase de sesión
El siguiente bloque de código devolverá un error para los usuarios en el Open Plan porque utiliza sesiones. Las cargas de trabajo en el Open Plan sólo pueden ejecutarse en modo trabajo o por lotes.
backend = service.least_busy(operational=True, simulator=False)
session = Session(backend=backend)
estimator = Estimator(mode=session)
sampler = Sampler(mode=session)
executor = Executor(mode=session)
# Close the session because no context manager was used.
session.close()Gestor de contexto
El gestor contextual abre y cierra automáticamente la sesión.
El siguiente bloque de código devolverá un error para los usuarios en el Open Plan porque utiliza sesiones. Las cargas de trabajo en el Open Plan sólo pueden ejecutarse en modo trabajo o por lotes.
from qiskit_ibm_runtime import (
Session,
SamplerV2 as Sampler,
EstimatorV2 as Estimator,
Executor,
)
backend = service.least_busy(operational=True, simulator=False)
with Session(backend=backend):
estimator = Estimator()
sampler = Sampler()
executor = Executor()Duración de la sesión
El tiempo máximo de vida de la sesión (TTL) determina cuánto tiempo puede durar una sesión. Puedes fijar este valor con el parámetro max_time . Esto debería superar el tiempo de ejecución del trabajo más largo.
Este temporizador se inicia cuando comienza la sesión. Cuando se alcanza el valor, se cierra la sesión. Los trabajos que se estén ejecutando finalizarán, pero los trabajos que sigan en cola fallarán.
El siguiente bloque de código devolverá un error para los usuarios en el Open Plan porque utiliza sesiones. Las cargas de trabajo en el Open Plan sólo pueden ejecutarse en modo trabajo o por lotes.
with Session(backend=backend, max_time="25m"):
...También hay un valor de tiempo de vida interactivo (TTL interactivo) que no se puede configurar. Si no hay trabajos de sesión en cola dentro de esa ventana, la sesión se desactiva temporalmente.
Valores predeterminados:
Tipo de instancia (Plan Open o Premium) | TTL interactivo | TTL máximo |
|---|---|---|
| Plan Premium | 60 sec* | 8 h* |
| * Algunas instancias del Plan Premium pueden estar configuradas para tener un valor diferente. |
Para determinar el TTL máximo o el TTL interactivo de una sesión, siga las instrucciones de Determinar los detalles de la sesión y busque el valor max_timeo interactive_timeout , respectivamente.
Finalizar una sesión
Una sesión finaliza en las siguientes circunstancias:
- Se alcanza el valor máximo de tiempo de espera (TTL), lo que provoca la cancelación de todos los trabajos en cola.
- La sesión se cancela manualmente, lo que provoca la cancelación de todos los trabajos en cola.
- La sesión se cierra manualmente. La sesión deja de aceptar nuevos trabajos pero sigue ejecutando los trabajos en cola con prioridad.
- Si utiliza Session como gestor de contexto, es decir,
with Session(), la sesión se cierra automáticamente cuando finaliza el contexto (el mismo comportamiento que utilizandosession.close()).
Cerrar sesión
Una sesión se cierra automáticamente al salir del gestor de contexto. Cuando se sale del gestor de contexto de sesión, la sesión pasa al estado "En curso, no acepta nuevos trabajos". Esto significa que la sesión termina de procesar todos los trabajos en ejecución o en cola hasta que se alcanza el valor máximo de tiempo de espera. Una vez finalizados todos los trabajos, la sesión se cierra inmediatamente. Esto permite al programador ejecutar el siguiente trabajo sin esperar a que se agote el tiempo de espera de la sesión interactiva, reduciendo así el tiempo medio de espera de los trabajos. No puede presentar trabajos a puerta cerrada.
El siguiente bloque de código devolverá un error para los usuarios en el Open Plan porque utiliza sesiones. Las cargas de trabajo en el Open Plan sólo pueden ejecutarse en modo trabajo o por lotes.
with Session(backend=backend) as session:
estimator = Estimator()
sampler = Sampler()
job1 = estimator.run([estimator_pub])
job2 = sampler.run([sampler_pub])
# The session is no longer accepting jobs but the submitted job will run to completion.
result = job1.result()
result2 = job2.result()Si no utiliza un gestor de contexto, cierre manualmente la sesión para evitar costes no deseados. Puedes cerrar una sesión en cuanto hayas terminado de enviarle trabajos. Cuando una sesión se cierra con session.close(), ya no acepta nuevos trabajos, pero los trabajos ya enviados seguirán ejecutándose hasta su finalización y se podrán recuperar sus resultados.
El siguiente bloque de código devolverá un error para los usuarios en el Open Plan porque utiliza sesiones. Las cargas de trabajo en el Open Plan sólo pueden ejecutarse en modo trabajo o por lotes.
session = Session(backend=backend)
# If using qiskit-ibm-runtime earlier than 0.24.0, change `mode=` to `session=`
estimator = Estimator(mode=session)
sampler = Sampler(mode=session)
job1 = estimator.run([estimator_pub])
job2 = sampler.run([sampler_pub])
print(f"Result1: {job1.result()}")
print(f"Result2: {job2.result()}")
# Manually close the session. Running and queued jobs will run to completion.
session.close()Output:
Result1: PrimitiveResult([PubResult(data=DataBin(evs=np.ndarray(<shape=(3, 2), dtype=float64>), stds=np.ndarray(<shape=(3, 2), dtype=float64>), ensemble_standard_error=np.ndarray(<shape=(3, 2), dtype=float64>), shape=(3, 2)), metadata={'shots': 4096, 'target_precision': 0.015625, 'circuit_metadata': {}, 'resilience': {}, 'num_randomizations': 32})], metadata={'dynamical_decoupling': {'enable': False, 'sequence_type': 'XX', 'extra_slack_distribution': 'middle', 'scheduling_method': 'alap'}, 'twirling': {'enable_gates': False, 'enable_measure': True, 'num_randomizations': 'auto', 'shots_per_randomization': 'auto', 'interleave_randomizations': True, 'strategy': 'active-accum'}, 'resilience': {'measure_mitigation': True, 'zne_mitigation': False, 'pec_mitigation': False}, 'version': 2})
Result2: PrimitiveResult([SamplerPubResult(data=DataBin(meas=BitArray(<shape=(3, 2), num_shots=4096, num_bits=2>), meas0=BitArray(<shape=(3, 2), num_shots=4096, num_bits=156>), shape=(3, 2)), metadata={'circuit_metadata': {}})], metadata={'execution': {'execution_spans': ExecutionSpans([DoubleSliceSpan(<start='2026-03-15 07:33:44', stop='2026-03-15 07:33:51', size=24576>)])}, 'version': 2})
Comprobar el estado de la sesión
Puede consultar el estado de una sesión para conocer su estado actual utilizando session.status() o consultando la página Cargas de trabajo.
El estado de la sesión puede ser uno de los siguientes
Pending: La sesión no se ha iniciado o se ha desactivado. El siguiente trabajo de sesión debe esperar en la cola como los demás trabajos.In progress, accepting new jobs: La sesión está activa y acepta nuevos trabajos.In progress, not accepting new jobs: La sesión está activa pero no acepta nuevos trabajos. Se rechaza el envío de trabajos a la sesión, pero los trabajos de sesión pendientes se ejecutarán hasta su finalización. La sesión se cierra automáticamente cuando finalizan todos los trabajos.Closed: Se ha alcanzado el tiempo máximo de espera de la sesión o se ha cerrado explícitamente.
Determinar los detalles de la sesión
Para obtener una visión general de la configuración y el estado de una sesión, utilice la página session.details() method.
El siguiente bloque de código devolverá un error para los usuarios en el Open Plan porque utiliza sesiones. Las cargas de trabajo en el Open Plan sólo pueden ejecutarse en modo trabajo o por lotes.
from qiskit_ibm_runtime import (
QiskitRuntimeService,
Session,
EstimatorV2 as Estimator,
)
service = QiskitRuntimeService()
backend = service.least_busy(operational=True, simulator=False)
with Session(backend=backend) as session:
print(session.details())Output:
{'id': 'a9fd2f9d-6239-4451-a19c-9b45aa6a0618', 'backend_name': 'ibm_torino', 'interactive_timeout': 60, 'max_time': 28800, 'active_timeout': 28800, 'state': 'open', 'accepting_jobs': True, 'last_job_started': None, 'last_job_completed': None, 'started_at': None, 'closed_at': None, 'activated_at': None, 'mode': 'dedicated', 'usage_time': None}
Patrones de uso
Las sesiones son especialmente útiles para algoritmos que requieren una comunicación frecuente entre recursos clásicos y cuánticos.
Ejemplo: Ejecute una carga de trabajo iterativa que utilice el optimizador clásico SciPy para minimizar una función de coste. En este modelo, SciPy utiliza la salida de la función de coste para calcular su próxima entrada.
El siguiente bloque de código devolverá un error para los usuarios en el Open Plan porque utiliza sesiones. Las cargas de trabajo en el Open Plan sólo pueden ejecutarse en modo trabajo o por lotes.
from scipy.optimize import minimize
from qiskit.circuit.library import efficient_su2
def cost_func(params, ansatz, hamiltonian, estimator):
# Return estimate of energy from estimator
energy = sum(
estimator.run([(ansatz, hamiltonian, params)]).result()[0].data.evs
)
return energy
hamiltonian = SparsePauliOp.from_list(
[("YZ", 0.3980), ("ZI", -0.3980), ("ZZ", -0.0113), ("XX", 0.1810)]
)
su2_ansatz = efficient_su2(hamiltonian.num_qubits)
pm = generate_preset_pass_manager(backend=backend, optimization_level=3)
ansatz = pm.run(su2_ansatz)
mapped_hamiltonian = [
operator.apply_layout(ansatz.layout) for operator in hamiltonian
]
num_params = ansatz.num_parameters
x0 = 2 * np.pi * np.random.random(num_params)
session = Session(backend=backend)
# If using qiskit-ibm-runtime earlier than 0.24.0, change `mode=` to `session=`
estimator = Estimator(mode=session, options={"default_shots": int(1e4)})
res = minimize(
cost_func,
x0,
args=(ansatz, mapped_hamiltonian, estimator),
method="cobyla",
options={"maxiter": 25},
)
# Close the session because no context manager was used.
session.close()Ejecuta dos algoritmos VQE en una sesión utilizando subprocesos
Puedes sacar más partido a una sesión ejecutando varias cargas de trabajo simultáneamente. El siguiente ejemplo muestra cómo puede ejecutar dos algoritmos VQE, cada uno con un optimizador clásico diferente, simultáneamente dentro de una misma sesión. Las etiquetas de trabajo también se utilizan para diferenciar los trabajos de cada carga de trabajo.
El siguiente bloque de código devolverá un error para los usuarios en el Open Plan porque utiliza sesiones. Las cargas de trabajo en el Open Plan sólo pueden ejecutarse en modo trabajo o por lotes.
from concurrent.futures import ThreadPoolExecutor
from qiskit_ibm_runtime import EstimatorV2 as Estimator
def minimize_thread(estimator, method):
return minimize(
cost_func,
x0,
args=(ansatz, mapped_hamiltonian, estimator),
method=method,
options={"maxiter": 25},
)
with Session(backend=backend), ThreadPoolExecutor() as executor:
estimator1 = Estimator()
estimator2 = Estimator()
# Use different tags to differentiate the jobs.
estimator1.options.environment.job_tags = ["cobyla"]
estimator2.options.environment.job_tags = ["nelder-mead"]
# Submit the two workloads.
cobyla_future = executor.submit(minimize_thread, estimator1, "cobyla")
nelder_mead_future = executor.submit(
minimize_thread, estimator2, "nelder-mead"
)
# Get workload results.
cobyla_result = cobyla_future.result()
nelder_mead_result = nelder_mead_future.result()Próximos pasos
- Pruebe un ejemplo en el tutorial Algoritmo de optimización aproximada cuántica (QAOA).
- Revise la referencia Session API.
- Comprender los límites del trabajo al enviar un trabajo a una QPU de IBM®.
- Revisar los modos de ejecución Preguntas frecuentes.