Notas de la versión de Qiskit SDK 1.3
1.3.3
Preludio
Qiskit 1.3.3 es una versión de corrección de errores menores para la serie 1.3.
Corrección de errores
-
Se ha corregido un error por el que las etiquetas de barrera se colocaban incorrectamente al utilizar el parámetro
reverse_bits = Trueen el métodoQuantumCircuit.draw()método. El error provocaba que las etiquetas de las operaciones de barrera estuvieran desalineadas, lo que podía crear confusión en las visualizaciones de circuitos. Corregido #13609. -
Aplicación de un pequeño factor de regularización contra matrices hermitianas mal condicionadas en representaciones de superoperadores.
-
Las comparaciones de
Delayde instrucciones, incluidas las que se realizan dentro de circuitos, requieren ahora que tanto las unidades como el valor de duración sean iguales. Correcciones #13812. -
Se ha corregido un error en el
CommutationCheckerque podía fallar al comprobar la relación de conmutación de una rotación Pauli de dos qubits con una puerta que no está en la caché de conmutación. Por ejemplo:import numpy as np from qiskit.circuit.library import RXXGate, RGate from qiskit.circuit.commutation_library import SessionCommutationChecker as scc res = scc.commute(RGate(2, 2), [1], [], RXXGate(np.pi / 2), [0, 1], [])Este comportamiento ya está resuelto y la relación de conmutación se calcula correctamente. Corregido #13742.
-
Se ha corregido un error por el que
QuantumCircuit.qubit_stop_time()yQuantumCircuit.qubit_duration()devolvían un tiempo (duración) incorrecto. El problema se producía cuando algunos qubits tenían instrucciones pero otros estaban inactivos. Corrige #8729. -
Se ha corregido un error en el
RemoveIdentityEquivalentpor el que se eliminaban del circuito las puertas cercanas a la identidad hasta una fase global, pero no se actualizaba la fase global del circuito. En particularRemoveIdentityEquivalentahora elimina las puertasGlobalPhaseGateno parametrizadas. Corrección #13778. -
Se ha corregido un error en
random_clifford()que impedía el muestreo del grupo Clifford completo. Correcciones #13606. -
Cuando
SabreLayoutse utiliza para realizar simultáneamente el trazado y el enrutamiento (como es el caso de las opciones por defecto detranspile()ygenerate_preset_pass_manager()) en unTargetoCouplingMapcon conectividad disjunta, y el circuito de entrada encaja en un solo componente del mapa de acoplamiento, la permutación de enrutamiento será ahora rastreada correctamente.Anteriormente, cualquier qubit del mapa de acoplamiento que no estuviera conectado, ni siquiera indirectamente, a un qubit utilizado por el circuito enrutado no se incluiría en la permutación de enrutamiento final. Esto podría causar un comportamiento sorprendente a gran distancia del punto de fallo, incluso si la compilación pareciera tener éxito, como llamadas a
TranspileLayout.final_index_layout()elevandoKeyError.Este fallo no afectaba a los backends que estaban totalmente conectados, como es el caso de la mayoría. Correcciones #13732.
1.3.2
Preludio
Qiskit 1.3.2 es una versión de corrección de errores menores para la serie 1.3.
Notas sobre la actualización de Synthesis
- Los plugins de síntesis de alto nivel para
LinearFunctionya no producen un error cuando se pasa un objeto distinto deLinearFunctionen el métodorun. En su lugar, ahora devuelvenNone, lo que es coherente con otros plugins. Si confía en que se produzca este error, puede realizar manualmente una comprobación de instancia.
Corrección de errores
-
Anteriormente, el
CommutationCheckeralmacenaba en caché las relaciones de conmutación deInstructions con float-onlyparamscomo clave para consultar la relación. Esto podría dar lugar a resultados incorrectos si la definición de la instrucción dependiera de información adicional más allá del atributoparamscomo, por ejemplo, en el caso de la instrucciónPauliEvolutionGate. Este comportamiento ya está corregido, y el comprobador de conmutaciones sólo almacena en caché las conmutaciones de las puertas estándar nativas de Qiskit. Para las puertas personalizadas, este cambio puede suponer un coste de rendimiento; sin embargo, garantiza resultados correctos al evitar el almacenamiento en caché inseguro. -
Se ha corregido un error en
CommutationCheckerpor el que se comprobaban las relaciones de conmutación de una instrucción con valores no numéricos en el atributoparams(como en el caso dePauliGate) podía dar lugar a un error. Corregido #13570. -
El sitio
CommutationCheckerno manejaba correctamente las conmutaciones deCRXGate,CRYGateyCRZGatepara ángulos de rotación de la forma , con . En estos casos, se asumía incorrectamente que estas puertas conmutaban con cualquier puerta. Este comportamiento ya está corregido, y estas puertas conmutan correctamente con cualquier puerta sólo cuando el ángulo de rotación es múltiplo de . -
Se ha corregido un error que provocaba que las siguientes funciones de la biblioteca de circuitos produjeran errores cuando se invocaban con
num_qubits=1:efficient_su2(),real_amplitudes(),excitation_preserving()ypauli_two_design()(para un solo qubit, estos circuitos no contienen ninguna puerta de 2 qubits). Corregido #13480. -
Se ha corregido un error por el que cualquier instrucción denominada
"mcmt"se pasaba incorrectamente a la rutina de síntesis de alto nivel para una instrucción de tipoMCMTGatelo que provocaba un fallo o un resultado no válido. Este problema podría ocurrir, por ejemplo, al manipular elMCMTcircuito, llamado"mcmt", y convertirlo implícitamente en una instrucción (por ejemplo, al agregarlo a otro circuito). Corregido #13563. -
Se ha corregido un error por el que la síntesis de fórmulas de producto por defecto para
PauliEvolutionGateno trataba correctamente todos los términos de identidad en el operador. El término de identidad total debería introducir una fase global igual a-evolution_time, pero estaba desviado por un factor de 2 y podría romperse para tiempos parametrizados. Corregido #13625. Corregido #13675. Corregido #13644. -
Corregida una inconsistencia en el circuito generado por la síntesis de evolución de Pauli usando
SuzukiTrotteroLieTrotter(el método por defecto). Para los tiempos de evolución parametrizados, los circuitos resultantes contenían parámetros con una parte compleja cero espuria, que afectaba a la salida deParameterExpression.sympify(). La salida ahora contiene correctamente sólo valores reales. Corregido #13642. -
Se ha corregido un error que provocaba que
PauliList.insert()conqubit=Trueprodujera un atributo de fase con la forma incorrecta cuando el objeto original era de longitud 1. Corregido #13623. -
Se ha corregido un error en
qasm3.Exporterque provocaba el bloqueo del exportador al manipular una puerta unitaria debido a un procesamiento incorrecto de su campoparams. Corregido #13362. -
Se ha corregido un error en el método
Target.instruction_supported()por el que los objetivos conself.num_qubits==Nonesiempre devolvíanFalseindependientemente del conjunto de bases admitido. -
Se ha corregido un error en el
UnitarySynthesistranspiler pass, por el que los bloques deUnitaryGates en 3 qubits o más no se sintetizaban correctamente. Esto provocaba, por ejemplo, que el circuito se sobrescribiera con el último bloque procesado o que se produjeran pánicos internos al encontrar mediciones después de dicho bloque. Corregido #13586. -
Se ha corregido un error en el
UnitarySynthesistranspiler pass por el que non-2-qubit gates se incluía en la base disponible de 2 qubits, provocando queTwoQubitWeylDecompositionentrara en pánico debido al desajuste de dimensiones. -
Se ha corregido un error por el que al inicializar
SparsePauliOpcon un gran número de términos Pauli-Y(típicamente ) y sincoeffsexplícito daba como resultado un coeficiente cercano a 1 pero con un error en coma flotante. El coeficiente es ahora correctamente 1 por defecto. Corregido #13522.
1.3.1
Preludio
Qiskit 1.3.1 es una versión de corrección de errores menores para la serie 1.3.
Notas sobre la actualización de circuitos
- El método de control genérico de las puertas evita ahora intentar traducir las puertas a una base compatible cuando la puerta ya es compatible. Esto puede cambiar ligeramente la síntesis de la puerta controlada, pero no debería aumentar el número de puertas de dos qubits.
Corrección de errores
-
Se ha corregido un error por el que la llamada a
QuantumCircuit.decompose()en una instrucción que no tenía definición dentro de un bloquec_ifprovocaba un error. Corregido #13493. -
Operaciones dentro de una operación de flujo de control (p. ej.
QuantumCircuit.for_loop()) no se descomponían correctamente al llamar aQuantumCircuit.decompose(). Corregido #13544. -
Se han añadido definiciones por defecto para
FullAdderGate,HalfAdderGate,ModularAdderGateyMultiplierGatelo que permite construirOperators a partir de circuitos cuánticos que contengan estas puertas. -
Corregido el número de qubits ancilla limpios requeridos por
FullAdderSynthesisV95,HalfAdderSynthesisV95yModularAdderSynthesisV95plugins. -
Añadido el
FullAdderSynthesisDefaultque elige la mejor descomposición paraFullAdderGatebasándose en el número de qubits ancilla limpios disponibles. -
Fijo
HalfAdderSynthesisDefaultyModularAdderSynthesisDefaultfijos, paraHalfAdderGateyModularAdderGaterespectivamente, para elegir la mejor descomposición en función del número de qubits ancilla limpios disponibles. -
Se ha corregido un comportamiento incorrecto de almacenamiento en caché durante la asignación de parámetros que podía dar lugar a que las definiciones dentro del
EquivalenceLibraryse corrompieran. Esto resuelve problemas inesperados cuando se ejecuta la traducción de bases en paralelo. Corregido #13504. -
Se han corregido una serie de errores al procesar circuitos con fases globales parametrizadas en los que la fase global no se asignaba correctamente durante la asignación de parámetros. Entre los casos conocidos a los que ha afectado se incluyen:
- asignar parámetros después de llamar
QuantumCircuit.decompose()en un circuito, donde la descomposición introduce una fase global - asignación de parámetros en un circuito construido a partir de un DAG mediante
dag_to_circuit() - asignación de parámetros en circuitos creados con
pauli_twirl_2q_gates()donde el circuito a girar tenía una fase global parametrizada
Corregido #13534.
- asignar parámetros después de llamar
-
Se ha corregido un error en
RZGate.control()para más de 1 qubit de control, que utilizaba una descomposición innecesariamente costosa. Corregido #13473.
1.3.0
Preludio
La versión 1.3.0 de Qiskit aporta importantes mejoras de rendimiento y calidad al transpilador. Se han introducido muchas novedades, correcciones y mejoras en esta nueva versión de Qiskit, las más destacadas son:
Las estructuras de datos centrales para la transpilación en Qiskit se han portado a Rust internamente. Esto incluye componentes como
DAGCircuit,Target,EquivalenceLibraryy otros. Las API públicas de todas estas estructuras de datos permanecen inalteradas, pero el rendimiento tras las reescrituras ha mejorado.La mayoría de los pases del transpilador utilizados por el gestor de pases predefinidos se han portado a Rust, lo que se traduce en una mejora media del tiempo de ejecución global de 6x en comparación con Qiskit 1.2.4 al ejecutar las pruebas de benchpress. Algunos de los pases especialmente impactantes que se beneficiaron enormemente de las reescrituras fueron el
BasisTranslator,CommutationAnalysis,ConsolidateBlocksyUnitarySynthesis. Puede consultar las notas de la versión de funciones para obtener una lista completa de los pases portados.Mejoras en la biblioteca de circuitos que aumentan la calidad de compilación y la velocidad de construcción de circuitos. Las operaciones se distinguen ahora en:
- Operaciones estructurales, que tienen una descomposición única, y se representan como funciones que devuelven un
QuantumCircuit(por ejemplo:real_amplitudes()). La mayoría de estas funciones se construyen en Rust, lo que resulta en un tiempo de ejecución de construcción de circuitos significativamente más rápido.- Las operaciones abstractas, que pueden implementarse utilizando diferentes descomposiciones, se representan como
GateoInstruction(por ejemplo:PauliEvolutionGate). Esto permite construir un circuito cuántico abstracto y dejar que el compilador elija la descomposición óptima.El uso de una descripción abstracta del circuito es especialmente potente en combinación con las mejoras del
HighLevelSynthesistranspiler pass, que ahora puede tener en cuenta los qubits auxiliares ociosos para encontrar la mejor descomposición disponible para una puerta determinada.La versión mínima soportada de Python es ahora 3.9 ya que Python 3.8 llegó al final de su vida útil en 2024-10. En esta versión también se ha añadido compatibilidad oficial con Python 3.13.
Características de los circuitos
-
Se ha mejorado la funcionalidad de
CommutationCheckerpara incluir soporte para las siguientes puertas parametrizadas con parámetros libres:RXXGate,RYYGate,RZZGate,RZXGate,RXGate,RYGate,RZGate,PhaseGate,U1Gate,CRXGate,CRYGate,CRZGate,CPhaseGate. Antes sólo se admitían con parámetros vinculados. -
Añadida una nueva función
quantum_volume()para generar un volumen cuánticoQuantumCircuitcomo se define en A. Cross et al. Validación de ordenadores cuánticos mediante circuitos modelo aleatorios, Phys. Rev. A 100, 032328 (2019). Esta nueva función difiere de la claseQuantumVolumeen que devuelve un objetoQuantumCircuiten lugar de construir un objeto subclase. La segunda es que esta nueva función es multihilo y está implementada en rust por lo que genera el circuito de salida ~10x más rápido que laQuantumVolumeclase -
Se ha mejorado el rendimiento en tiempo de ejecución de la construcción de la clase
QuantumVolumecon el argumentoclassical_permutationfijado enTrue. Internamente ahora llama a la funciónquantum_volume()que está escrita en Rust y es ~10x más rápida al generar un circuito de volumen cuántico. -
Añadida una nueva función de manipulación de circuitos
pauli_twirl_2q_gates()que puede utilizarse para aplicar el giro de Pauli a un circuito dado. Esto sólo funciona para girar un conjunto fijo de puertas de dos qubits, actualmenteCXGate,ECRGate,CZGate,iSwapGate. Por ejemplo:from qiskit.circuit import QuantumCircuit, pauli_twirl_2q_gates qc = QuantumCircuit(2) qc.cx(0, 1) twirled_circuit = pauli_twirl_2q_gates(qc, seed=123456) twirled_circuit.draw("mpl")
-
Se han añadido puertas aritméticas binarias para la suma in situ de dos registros -qubit, es decir . El
ModularAdderGateimplementa la suma módulo , elHalfAdderGateincluye un qubit de salida, y elFullAdderGateincluye tanto un qubit de entrada como uno de salida. Consulte la documentación correspondiente para más detalles y ejemplos.A diferencia de los circuitos de biblioteca existentes, como
CDKMRippleCarryAdderel manejo de la puerta abstracta permite al compilador (o al usuario) seleccionar la síntesis de puerta óptima, en función del contexto del circuito. -
Se ha añadido el
MultiplierGatepara la multiplicación de dos registros -qubit, es decir . Consulte la documentación de la clase para más detalles y ejemplos. -
Los circuitos cuánticos de lógica booleana en
qiskit.circuit.librarytienen ahora representaciones equivalentes como objetosGateobjetos que permiten su uso conHighLevelSynthesistranspiler pass y la infraestructura de plugins.AndGate, representando aAND,OrGate, representando aOR,BitwiseXorGate, representando aXOR,InnerProductGateque representaInnerProduct.
-
Se han añadido implementaciones especializadas de
__eq__()para todas las puertas de circuito de la biblioteca estándar. La mayoría de las puertas estándar ya estaban especializadas en este método, pero unas pocas no, y podían provocar ralentizaciones importantes en lugares inesperados. -
Añadido
evolved_operator_ansatz(),hamiltonian_variational_ansatz()yqaoa_ansatz()a la biblioteca de circuitos para implementar circuitos variacionales basados en evoluciones de operadores.evolved_operator_ansatz()yqaoa_ansatz()son funcionalmente equivalentes aEvolvedOperatorAnsatzyQAOAAnsatzpero, por lo general, son más eficaces.El sitio
hamiltonian_variational_ansatz()está diseñado para tomar un único Hamiltoniano y dividirlo automáticamente en términos conmutativos para implementar un ansatz variacional Hamiltoniano. Esto ya se podía conseguir manualmente utilizando el botónEvolvedOperatorAnsatzpero ahora es más cómodo de usar. -
Añadido
grover_operator()para construir un circuito operador de Grover, utilizado en el algoritmo de Grover y en la estimación/amplificación de amplitud, por ejemplo. Esta función es similar aGroverOperatorpero no requiere que elijas la implementación de la puerta X multicontrolada, sino que deja que el compilador determine la descomposición óptima. Además, no envuelve el circuito en una puerta opaca y es más rápido porque se necesitan menos descomposiciones para la transpilación.from qiskit.circuit import QuantumCircuit from qiskit.circuit.library import grover_operator oracle = QuantumCircuit(2) oracle.z(0) # good state = first qubit is |1> grover_op = grover_operator(oracle, insert_barriers=True) grover_op.draw('mpl')
-
Un nuevo atributo de datos,
qiskit.circuit.CONTROL_FLOW_OP_NAMESpara encontrar y comprobar fácilmente si una operaciónInstructiones una operación de flujo de control por su nombre. -
La biblioteca de equivalencias estándar (
SessionEquivalenceLibrary) ahora tiene reglas que pueden convertir directamente entre la biblioteca estándar de Qiskit 2q interacciones continuas de tipo Ising (por ejemplo.CPhaseGate,RZZGate,RZXGateetc.) utilizando relaciones de equivalencia locales. Antes, varias de estas conversiones pasaban por una forma 2-CX, lo que daba lugar a una generación de circuitos menos eficiente.NotaEn general, el
BasisTranslatorno garantiza que encuentre la "mejor" relación de equivalencia para un determinadoTargetpero siempre encontrará una equivalencia si existe. Dependemos de pases más caros de resíntesis y optimización de puertas en el transpilador para mejorar el resultado. Actualmente, estos pases no son tan eficaces para los conjuntos de bases con una interacción de dos qubits parametrizada de forma continua como lo son para las interacciones discretas de dos qubits supercontrolados. -
Se ha añadido un nuevo argumento
"apply_synthesis"aDecomposeque permite al pase de transpilador aplicar síntesis de alto nivel para descomponer objetos que sólo están definidos por una rutina de síntesis. Por ejemplo:from qiskit import QuantumCircuit from qiskit.quantum_info import Clifford from qiskit.transpiler.passes import Decompose cliff = Clifford(HGate()) circuit = QuantumCircuit(1) circuit.append(cliff, [0]) # Clifford has no .definition, it is only defined by synthesis nothing_happened = Decompose()(circuit) # this internally runs the HighLevelSynthesis pass to decompose the Clifford decomposed = Decompose(apply_synthesis=True)(circuit) -
Añadida la función
iqp()función para construir circuitos de tiempo polinómico cuántico instantáneo (IQP). Además de la claseIQPla función también permite construir circuitos IQP aleatorios:from qiskit.circuit.library import random_iqp random_iqp = random_iqp(num_qubits=4) random_iqp.draw('mpl')
-
Se ha añadido el
MCMTGatepara representar una operación multicontrol multiobjetivo como una puerta. Esta representación del circuitoMCMTpermite al compilador seleccionar la mejor implementación disponible en función del número y el estado de los qubits auxiliares presentes en el circuito.La implementación deseada puede elegirse especificando el plugin de síntesis de alto nivel:
from qiskit import QuantumCircuit, transpile from qiskit.circuit.library import MCMTGate, HGate from qiskit.transpiler.passes import HLSConfig # used for the synthesis config mcmt = MCMTGate(HGate(), num_ctrl_qubits=5, num_target_qubits=3) circuit = QuantumCircuit(20) circuit.append(mcmt, range(mcmt.num_qubits)) config = HLSConfig(mcmt=["vchain"]) # alternatively use the "noaux" method synthesized = transpile(circuit, hls_config=config)Además, el
MCMTGatetambién admite estados de control personalizados (es decir, abiertos) de los qubits de control. -
Como parte de la modernización de la biblioteca de circuitos, cada uno de los siguientes circuitos cuánticos se representa también como un
Gateo puede construirse mediante un método de síntesis:GraphStateestá representado porGraphStateGate,FourierCheckingpuede construirse utilizandofourier_checking(),UnitaryOverlappuede construirse utilizandounitary_overlap(),HiddenLinearFunctionpuede construirse utilizandohidden_linear_function(),PhaseEstimationpuede construirse utilizandophase_estimation().
-
La clase
CommutationCheckerha sido reescrita en Rust. Esta clase conserva la misma funcionalidad y API pública que antes, pero ahora es significativamente más rápida en la mayoría de los casos. -
PauliFeatureMapyZZFeatureMappermiten ahora especificar el entrelazamiento como un diccionario en el que las claves representan el número de qubits, y los valores son listas de tuplas enteras que definen qué qubits están entrelazados entre sí. Esto permite una mayor flexibilidad en la construcción de mapas de características adaptados a algoritmos cuánticos específicos. Ejemplo de uso:from qiskit.circuit.library import PauliFeatureMap entanglement = { 1: [(0,), (2,)], 2: [(0, 1), (1, 2)], 3: [(0, 1, 2)], } qc = PauliFeatureMap(3, reps=2, paulis=['Z', 'ZZ', 'ZZZ'], entanglement=entanglement, insert_barriers=True) qc.decompose().draw('mpl') -
El método
count_ops()enQuantumCircuitha sido reescrito en Rust. Ahora funciona entre 3 y 9 veces más rápido. -
Añadidas funciones de biblioteca de circuitos
pauli_feature_map(),z_feature_map(),zz_feature_map()para construir circuitos de mapas de características de Pauli. Estas funciones son aproximadamente 8x más rápidas que los objetos actuales de la biblioteca de circuitos,PauliFeatureMap,ZFeatureMapyZZFeatureMapy las sustituirán en el futuro.Las funciones se pueden utilizar como sustitución directa:
from qiskit.circuit.library import pauli_feature_map, PauliFeatureMap fm = pauli_feature_map(20, paulis=["z", "xx", "yyy"]) also_fm = PauliFeatureMap(20, paulis=["z", "xx", "yyy"]).decompose()
Características primitivas
-
Se ha añadido soporte para datos de nivel 1 a
BackendSamplerV2así como la posibilidad de pasar opciones al métodorun()del método envueltoBackendV2. Las opciones de ejecución pueden especificarse utilizando una entrada"run_options"dentro del diccionariooptionspasado aBackendSamplerV2. La entrada"run_options"debe ser un diccionario que asigne nombres de argumentos a valores que se pasarán al métodorun()del backend. Cuando se establece"meas_level = 1 "en las opciones de ejecución, los resultados del backend se tratarán como resultados de nivel 1 en lugar de matrices de bits (el formato de nivel 2). -
EstimatoryStatevectorEstimatordevolver valores de expectativas de forma estocástica si el circuito de entrada incluye un reinicio para algunos subsistemas. Antes el resultado no era reproducible, pero ahora puede reproducirse si se fija una semilla aleatoria. Por ejemplo:from qiskit.primitives import StatevectorEstimator estimator = StatevectorEstimator(seed=123)o:
from qiskit.primitives import Estimator estimator = Estimator(options={"seed":123})
OpenQASM Características
- La clase
qasm3.CustomGatees ahora inspeccionable mediante programación. Suconstructor,name,num_paramsynum_qubitspueden verse ahora desde Python una vez construido el objeto. Esto le permite inspeccionar el contenido de los atributos de datos proporcionados comoSTDGATES_INC_GATES.
Características de QPY
- Añadido un nuevo formato QPY versión 13 que añade una representación nativa Qiskit de
ParameterExpressionobjetos.
Características de la información cuántica
-
El rendimiento de
SparsePauliOp.from_operator()se ha optimizado a partir de los métodos de mejora de algoritmos introducidos en Qiskit 1.0. Ahora es aproximadamente cinco veces más rápido que antes para matrices totalmente densas, tardando aproximadamente 40ms en descomponer un operador 10q que incluya todos los términos de Pauli. -
Se ha añadido un nuevo argumento
assume_unitaryaqiskit.quantum_info.Operator.power(). CuandoTrue, utilizamos un método más rápido basado en la descomposición de Schur para elevar unOperatora una potencia fraccionaria. -
Se ha añadido
SparsePauliOp.to_sparse_list()para convertir un operador en un formato de lista dispersa. Esto funciona de forma inversa aSparsePauliOp.from_sparse_list(). Por ejemplo:from qiskit.quantum_info import SparsePauliOp op = SparsePauliOp(["XIII", "IZZI"], coeffs=[1, 2]) sparse = op.to_sparse_list() # [("X", [3], 1), ("ZZ", [1, 2], 2)] other = SparsePauliOp.from_sparse_list(sparse, op.num_qubits) print(other == op) # True -
El rendimiento de
Pauli.to_label()ha mejorado significativamente para Paulis grandes. -
El método
Operator.power()tiene un nuevo parámetrobranch_cut_rotation. Esto puede utilizarse para desplazar el punto de corte de la rama de la raíz, lo que puede afectar a qué matriz se elige como raíz principal. Por defecto, se establece en una pequeña rotación positiva para que las raíces de los operadores con un valor propio real negativo (como los operadores de Pauli) sean más estables frente a las diferencias de precisión numérica. -
Se ha añadido una nueva clase observable.
SparseObservablerepresenta los observables como una suma de términos, similar aSparsePauliOppero con dos diferencias fundamentales:- Cada término completo se almacena como (efectivamente) una serie de pares
(qubit, bit_term), sin almacenar qubits que sufran la identidad para ese término. Esto mejora significativamente el uso de memoria de observables como la suma ponderada de Paulis . - El alfabeto de términos de un solo qubit está sobrecompletado para el espacio de operadores; puede representar operadores de Pauli (como
SparsePauliOp), pero también proyectores sobre los estados propios de los operadores de Pauli, como . Dichos proyectores pueden medirse en hardware con la misma eficiencia que su correspondiente operador de Pauli, peroSparsePauliOprequeriría un número exponencial de términos para representar sobre qubits, mientras queSparseObservablesólo necesita un único término.
Puede construir y manipular
SparseObservableutilizando una interfaz familiar para los usuarios deSparsePauliOp:from qiskit.quantum_info import SparseObservable obs = SparseObservable.from_sparse_list([ ("XZY", (2, 1, 0), 1.5j), ("+-", (100, 99), 0.5j), ("01", (50, 49), 0.5), ])SparseObservableno se admite actualmente como formato de entrada para las primitivas (qiskit.primitives), pero esperamos ampliar estas interfaces para incluirlos en el futuro. - Cada término completo se almacena como (efectivamente) una serie de pares
Características de síntesis
-
Funciones de síntesis añadidas
synth_mcx_gray_code()ysynth_mcx_noaux_v24()que sintetizan compuertas X multicontroladas. Estas funciones no requieren qubits ancilla adicionales. -
Funciones de síntesis añadidas
synth_c3x()ysynth_c4x()que sintetizan puertas X de 3 y 4 controles respectivamente. -
Añadir una función de síntesis
synth_mcx_n_dirty_i15()que sintetiza una compuerta X multicontrolada con controles utilizando qubits auxiliares sucios produciendo un circuito con un máximo de compuertas CX, por Iten et. al. (arXiv:1501.06911). -
Añadir una función de síntesis
synth_mcx_n_clean_m15()que sintetiza una compuerta X multicontrolada con controles utilizando qubits auxiliares limpios produciendo un circuito con un máximo de compuertas CX, por Maslov ( arXiv:1508.03273 ). -
Añadir una función de síntesis
synth_mcx_1_clean_b95()que sintetiza una compuerta X multicontrolada con controles utilizando un único qubit auxiliar limpio produciendo un circuito con un máximo de compuertas CX, por Barenco et al. ( arXiv:quant-ph/9503016 ). -
Añadido
adder_qft_d00(),adder_ripple_c04()yadder_ripple_v95()para sintetizar las puertas del sumador,ModularAdderGate,HalfAdderGateyFullAdderGate. -
Añadido
multiplier_cumulative_h18()ymultiplier_qft_r17()para sintetizar elMultiplierGate. -
Añadido
synth_mcmt_vchain()para sintetizar la puerta multiobjetivo multi-control con un número lineal de puertas Toffoli y k-1 qubits auxiliares para k qubits de control, junto con el plugin de síntesis de alto nivelMCMTSynthesisVChain. -
Se ha añadido una estructura de plugin de síntesis de alto nivel para el módulo
MCMTGateincluyendo elMCMTSynthesisNoAux(sin qubits auxiliares), el ya mencionadoMCMTSynthesisVChain(usandonum_control - 1qubits auxiliares), y elMCMTSynthesisDefaultpara que el compilador elija la descomposición óptima. -
La función
random_clifford()fue portado a Rust, mejorando el tiempo de ejecución en un factor de 3. -
Añadido
ProductFormula.expand()que permite ver la expansión de una fórmula de producto en un formato Pauli disperso. Por ejemplo, podemos consultar el formato de una expansión Trotter de segundo orden de un Hamiltoniano como:from qiskit.quantum_info import SparsePauliOp from qiskit.circuit.library import PauliEvolutionGate from qiskit.synthesis.evolution import SuzukiTrotter hamiltonian = SparsePauliOp(["IX", "XI", "ZZ"], coeffs=[-1, -1, 1]) evo = PauliEvolutionGate(hamiltonian, time=3.14) trotter = SuzukiTrotter(order=2) print(trotter.expand(evo))que imprimirá
[('X', [0], -3.14), ('X', [1], -3.14), ('ZZ', [0, 1], 6.28), ('X', [1], -3.14), ('X', [0], -3.14)] -
Añadida la estructura del plugin
PauliEvolutionGate. El plugin por defecto,PauliEvolutionSynthesisDefaultconstruye el circuito como antes, pero más rápido, ya que internamente utiliza Rust. Cuanto mayor sea el circuito (por ejemplo. por el tamaño del hamiltoniano, el número de pasos temporales o el orden Suzuki-Trotter), mayor será la aceleración. Por ejemplo, un Hamiltoniano de Heisenberg de 100 qubits con 10 pasos de tiempo y una fórmula de Trotter de 4º orden se construye ahora ~9.4x más rápido. El nuevo plugin,PauliEvolutionSynthesisRustiqutiliza el algoritmo de síntesis descrito en el artículo " Faster and shorter synthesis of Hamiltonian simulation circuits" de (de) Brugière y Martiel " y está implementado en Rustiq. Por ejemplo:from qiskit.circuit import QuantumCircuit from qiskit.quantum_info import SparsePauliOp from qiskit.circuit.library import PauliEvolutionGate from qiskit.compiler import transpile from qiskit.transpiler.passes import HLSConfig op = SparsePauliOp(["XXX", "YYY", "IZZ"]) qc = QuantumCircuit(4) qc.append(PauliEvolutionGate(op), [0, 1, 3]) config = HLSConfig(PauliEvolution=[("rustiq", {"upto_phase": False})]) tqc = transpile(qc, basis_gates=["cx", "u"], hls_config=config) tqc.draw(output='mpl')
Este fragmento de código utiliza el plugin Rustiq para sintetizar
PauliEvolutionGateobjetos en el circuito cuántico qc. El plugin se llama con la opción adicionalupto_phase = False, lo que permite obtener circuitos más pequeños a costa de no conservar posiblemente la fase global. Para obtener la lista completa de opciones compatibles, consulte la documentación dePauliEvolutionSynthesisRustiq. -
Puerto
synth_cz_depth_line_mr()a Rust. Esta función sintetiza un circuito CZ para la conectividad lineal del vecino más próximo (LNN), basado en el método de Maslov y Roetteler. En una matriz binaria de 350x350, la implementación de Rust produce un aumento de velocidad de aproximadamente 30x. -
Port
synth_permutation_reverse_lnn_kms()a Rust, que sintetiza una permutación inversa para la arquitectura LNN utilizando el método Kutin, Moulton, Smithline. -
Añadido un nuevo argumento
preserve_orderaProductFormulaque permite reordenar los términos de Pauli en el Hamiltoniano antes de la expansión de la fórmula del producto, para comprimir la profundidad final del circuito. Fijando esto enFalse, un término de la forma
se reordenarán en
lo que hará que las rotaciones RZZ y RYY se apliquen en paralelo, en lugar de las tres rotaciones secuenciales de la primera parte.
Esta opción puede configurarse a través de la interfaz del plugin:
from qiskit import QuantumCircuit, transpile
from qiskit.circuit.library import PauliEvolutionGate
from qiskit.quantum_info import SparsePauliOp
from qiskit.synthesis.evolution import SuzukiTrotter
from qiskit.transpiler.passes import HLSConfig
op = SparsePauliOp(["XXII", "IYYI", "IIZZ"])
time, reps = 0.1, 1
synthesis = SuzukiTrotter(order=2, reps=reps)
hls_config = HLSConfig(PauliEvolution=[("default", {"preserve_order": False})])
circuit = QuantumCircuit(op.num_qubits)
circuit.append(PauliEvolutionGate(op, time), circuit.qubits)
tqc = transpile(circuit, basis_gates=["u", "cx"], hls_config=hls_config)
tqc.draw('mpl')
Características del transpilador
-
Añade el argumento
matrix_basedalCollectCliffordstranspiler pass. Si el nuevo parámetromatrix_based=True, elCollectCliffordstranspilador puede recoger puertas unitarias que son puertas Clifford para ciertos parámetros, por ejemploRZGatepuertas con ángulos múltiplos de . -
El
RemoveIdentityEquivalenttranspilador se ejecuta ahora como parte de los gestores de pases preestablecidos en los niveles de optimización 2 y 3. El pase se ejecuta durante las etapasinityoptimization, porque las optimizaciones que aplica son válidas en ambas etapas y el pase es rápido de ejecutar. -
Añadidos múltiples plugins de síntesis de alto nivel para sintetizar un
MCXGate:MCXSynthesisNCleanM15basado ensynth_mcx_n_clean_m15().MCXSynthesisNDirtyI15basado ensynth_mcx_n_dirty_i15().MCXSynthesis1CleanB95basado ensynth_mcx_1_clean_b95().MCXSynthesisNoAuxV24basado ensynth_mcx_noaux_v24().MCXSynthesisGrayCodebasado ensynth_mcx_gray_code().
Así como:
MCXSynthesisDefaultpara elegir el método de síntesis más eficiente en función del número de qubits ancilla limpios y sucios disponibles.
Como ejemplo, considere la transpilación del siguiente circuito:
from qiskit.circuit import QuantumCircuit from qiskit.compiler import transpile qc = QuantumCircuit(7) qc.x(0) qc.mcx([0, 1, 2, 3], [4]) qc.mcx([0, 1, 2, 3, 4], [5]) qc.mcx([0, 1, 2, 3, 4, 5], [6]) transpile(qc).draw('mpl', fold=-1)
Para la primera puerta MCX, los qubits
5y6pueden utilizarse como ancillas limpias, y se elegirá el mejor método de síntesis disponiblesynth_mcx_n_clean_m15. Para la segunda puerta MCX, el qubit6puede ser utilizado como una ancilla limpia, el métodosynth_mcx_n_clean_m15ya no se aplica, por lo que el métodosynth_mcx_1_clean_b95será elegido. Para la tercera puerta MCX, no hay qubits ancilla, y se elegirá el métodosynth_mcx_noaux_v24. -
El transpilador
SabreLayouttranspiler pass se ha actualizado para ejecutar dos o tres pruebas de diseño adicionales por defecto, independientemente del valor del argumento de la palabra clavelayout_trials. Se incluye un diseño trivial y su inverso para todos los backends, al igual que elDenseLayoutque se añadió en 1.2.0. Además, se añaden los anillos más grandes en un gráfico de conectividad de hexágonos pesados de backend IBM si los backends son de 127, 133 o 156 qubits. Esto puede proporcionar un buen punto de partida para algunos circuitos en estos backends de uso común, mientras que para todos los demás es sólo una "prueba aleatoria" adicional. -
La página
DAGCircuitse ha reimplementado en Rust. Esta reescritura de la clase Python debería ser totalmente compatible con la API de la anterior implementación de Python. Mientras que la clase fue implementada previamente usando rustworkx, para la cual la estructura de grafo de datos subyacente existe en Rust, la implementación de la clase y todos los datos se vivieron en Python. Esta nueva versión deDAGCircuitalmacena representaciones nativas de Rust para todos sus datos y es más eficiente en memoria gracias a la representación comprimida de qubits y clbits diseñada para instrucciones en reposo. También permite que los pases del transpilador manipulen completamente unDAGCircuitdesde Rust, lo que permite mejorar el rendimiento. -
Se ha añadido un nuevo argumento
qubits_initially_zeroaqiskit.compiler.transpile(),generate_preset_pass_manager()y aPassManagerConfig. Si se establece en el valor predeterminado deTrue, se supone que los qubits se encuentran inicialmente en el estado , lo que permite potencialmente oportunidades de optimización adicionales para pases individuales del transpilador. En particular, elHighLevelSynthesistranspiler pass elegirá una mejor descomposición para cadaMCXGatede un circuito cuando se disponga de un qubit auxiliar inactivo en el estado .Sin embargo, hay casos en los que
qubits_initially_zerodebe establecerse enFalse, como cuando se transpilan para backends que no inicializan correctamente los qubits, o cuando se llaman manualmente pases de transpilador en subcircuitos de un circuito cuántico mayor. -
El constructor para el
HighLevelSynthesistranspiler pass acepta ahora un argumento adicional:qubits_initially_zero. Si se establece enTrue, el pase asume que los qubits están inicialmente en el estado . Además, el pase realiza un seguimiento de los qubits auxiliares limpios y sucios a lo largo de la ejecución, y pasa esta información a los plugins utilizando los kwargsnum_clean_ancillasynum_dirty_ancillas. -
Mejora del tratamiento de los qubits ancilla en el
HighLevelSynthesistranspilador. Por ejemplo, un circuito puede tener puertas personalizadas cuyas definiciones incluyanMCXGates. Ahora los algoritmos de síntesis para las puertas internasMCXGates pueden utilizar los qubits ancilla disponibles en el circuito global pero fuera de las definiciones de las puertas personalizadas. -
Se ha añadido un nuevo método
DAGCircuit.control_flow_op_nodes()que proporciona una vía rápida para obtener todos losDAGOpNodeen unDAGCircuitque contienen aControlFlowOp. Esto era posible antes de utilizar el métodoDAGCircuit.op_nodes()y pasando la claseControlFlowOpcomo filtro, pero esta nueva función realizará la operación más rápidamente. -
La mayoría de los pases del transpilador utilizados en los gestores de pases predefinidos devueltos por
generate_preset_pass_manager()y utilizados internamente portranspile()fueron portados a Rust. Esto ha mejorado significativamente el rendimiento en tiempo de ejecución de cada pasada, lo que se ha traducido en una notable mejora de la eficacia operativa global del transpilador. La lista de pases portados a Rust en esta versión son:ConsolidateBlocksBasisTranslatorCommutationAnalysisCommutativeCancellationElidePermutationsOptimize1qGatesDecompositionUnitarySynthesisGateDirectionCheckGateDirectionRemoveDiagonalGatesBeforeMeasureCheckMapSplit2QUnitariesFilterOpNodesDepthSizeGatesInBasisInverseCancellationBarrierBeforeFinalMeasurements
-
Añadido un nuevo pase de transpilador
RemoveIdentityEquivalentque se utiliza para eliminar las puertas que son equivalentes a una identidad hasta cierta tolerancia. Por ejemplo, si tuvieras un circuito como
ejecutar el pase eliminaría el
CPhaseGate:from qiskit.circuit import QuantumCircuit from qiskit.transpiler.passes import RemoveIdentityEquivalent qc = QuantumCircuit(2) qc.cp(1e-20, 0, 1) removal_pass = RemoveIdentityEquivalent() result = removal_pass(qc) result.draw("mpl")
-
El pase
ConsolidateBlockspass ejecutará ahora el equivalente delCollect2qBlockspass internamente si no se ejecutó en un gestor de pass antes del pass. Anteriormente,Collect2qBlocksoCollect1qRunstenía que ejecutarse antesConsolidateBlockspara queConsolidateBlockshacer algo. Al realizar la recogida internamente, se reduce la sobrecarga del pase. SiCollect2qBlocksoCollect1qRunsse ejecutan antes queConsolidateBlocks, se utilizan las ejecuciones recogidas por esos pases del conjunto de propiedades y no se produce ningún cambio en el comportamiento del pase. -
El
RemoveDiagonalGatesBeforeMeasurese ha mejorado para incluir más puertas diagonales:PhaseGate,CPhaseGate,CSGate,CSdgGateyCCZGate. Además, el código delRemoveDiagonalGatesBeforeMeasurefue portado a Rust, y ahora es x20 más rápido para un circuito de 20 qubits.
Funciones de visualización
- La función de visualización
timeline_drawer()función de visualización tiene un nuevo argumentotarget, utilizado para especificar unTargetobjeto para la visualización. Por defecto, la función utiliza elInstruction.durationpara obtener la duración de una instrucción determinada, pero si se especifica el objetivo se aprovecharán los detalles de temporización dentro del objetivo.
Problemas conocidos
- Cuando se utilizan los formatos QPY 10, 11 ó 12 con circuitos que contienen
ParameterExpressions, si la versión del paquetesymengineinstalada en el entorno que generó la carga útil (qpy.dump()) no coincide con la versión desymengineinstalada en el entorno donde se carga la carga útil (qpy.load()), se producirá un error. Si se encuentra con este error, instale la versiónsymenginedel mensaje de error antes de llamar aqpy.load(). Las versiones de formato QPY 13 o posteriores (o anteriores a la 10) no tendrán este problema. Por lo tanto, si está serializandoParameterExpressionobjetos como parte de su circuito o cualquierScheduleBlockobjetos, se recomienda que utilice la versión 13 para evitar este problema en el futuro.
Notas de actualización
-
Las siguientes clases utilizan ahora la operación para diagonalizar el operador Pauli-Y:
PauliEvolutionGate,EvolvedOperatorAnsatzyPauliFeatureMap. Anteriormente, estas clases utilizaban o como transformación de base. El uso de la operación , representada por el símboloSXGatees más eficiente ya que utiliza una única puerta implementada como singleton.Si te basabas en el uso anterior de la puerta, te recomendamos construir los circuitos con Qiskit 1.2 y exportarlos con
qpy.dump()o escribir unTransformationPassque realice la traducción a la puerta de cambio de base deseada. -
La versión mínima compatible de Python es ahora 3.9, que ha pasado de la versión mínima anterior de 3.8. Este cambio ha sido necesario porque el proyecto cPython ya no es compatible con Python 3.8.
Notas sobre la actualización de circuitos
- La clase
QuantumVolumegenerará circuitos con diferentes matrices unitarias y permutaciones para un valor semilla dado de la versión anterior de Qiskit. Esto se debe a la utilización de un nuevo generador interno de números aleatorios para la generación de circuitos que generará el circuito más rápidamente. Si necesitas un circuito exacto con la misma semilla puedes usar la versión anterior de Qiskit y generar el circuito con el argumentoflatten=Truey exportar el circuito conqpy.dump()y luego cargarlo con esta versión.
Notas sobre la actualización de primitivas
- Cuando se utiliza
BackendSamplerV2los metadatos del circuito ya no se borran antes de pasar los circuitos al métodorun()de la instancia envueltaBackendV2envuelta. Si anteriormente confiaba en este comportamiento, puede borrar manualmente los metadatos antes de llamar aBackendSamplerV2.run()llamando acircuit.metadata.clear()
Notas sobre la actualización de QPY
- La función
qpy.dump()emite ahora la versión de formato 13 por defecto. Esto significa que las cargas útiles generadas con esta función por defecto sólo son compatibles con Qiskit 1.3.0 o posterior. Si la carga útil debe ser cargada por una versión anterior de Qiskit, utilice la banderaversionenqpy.dump()para emitir la versión apropiada. Consulte la sección Compatibilidad con QPY para obtener más información.
Notas sobre la actualización del transpilador
-
DAGNode(y sus subclasesDAGInNode,DAGOutNodeyDAGOpNode) ya no devuelven referencias al mismo objeto subyacente desde los métodosDAGCircuitmétodos. Nunca antes se había garantizado que todos los nodos devueltos compartieran una referencia al mismo objeto. Sin embargo, con la migración deDAGCircuita Rust, se genera una nueva instancia deDAGNodesobre la marcha cuando se devuelve un nodo a Python. Estos objetos se evaluarán como iguales utilizando==o comprobaciones similares que se basen en__eq__, pero ya no se identificarán como el mismo objeto. -
Las instancias
DAGOpNodedevueltas por el métodoDAGCircuitya no son referencias compartidas a los datos subyacentes almacenados en el DAG. En la versión anterior era posible hacer algo como:for node in dag.op_nodes(): node.op = new_opsin embargo, este tipo de mutación siempre ha sido poco sólida, ya que podría romper la caché interna del DAG y provocar la corrupción de la estructura de datos. En su lugar, debe utilizar la API proporcionada por
DAGCircuitpara mutaciones comoDAGCircuit.substitute_node()oDAGCircuit.substitute_node_with_dag(). Por ejemplo, el bloque de código anterior pasaría a serfor node in dag.op_nodes(): dag.substitute_node(node, new_op)Esto es similar a una nota de actualización de 1.2.0 donde esto se observó en para la mutación de la
DAGOpNode.opy no del atributoDAGOpNodemismo. Sin embargo, en 1.3 esto se extiende a todo el objeto, no sólo a su atributo internoop. En general, este tipo de mutación siempre ha sido poco sólida y no se ha apoyado, pero antes podría haber funcionado potencialmente en algunos casos. -
En
transpile()asume ahora que los qubits están inicialmente en el estado . Para evitar esta suposición, se puede establecer el argumentoqubits_initially_zeroenFalse.
Notas sobre características en desuso
-
El módulo
qiskit.pulsey todas sus funciones asociadas han quedado obsoletas y se eliminarán en Qiskit 2.0.0. Esto se debe a que el principal proveedor de backend con soporte de pulsos es IBM y el acceso a nivel de pulsos actualmente sólo es compatible con un subconjunto de backends de IBM no es compatible con sus arquitecturas más recientes. De manera similar, han anunciado que el acceso a nivel de pulso se eliminará en 2025. Sin que el proveedor más grande siga utilizando la función que admite el acceso a nivel de pulso, la importancia de la función para Qiskit se reduce significativamente y se compara con la sobrecarga de mantenimiento continuo del paquete por el que se está eliminando.La desaprobación incluye todo el código de pulse en
qiskit.pulseasí como la funcionalidad dependiente o relacionada con pulse, como la visualización de pulse, la serialización y el soporte de calibración personalizada. Para obtener más información, consulte las secciones de obsoletos más abajo.El paquete Pulse en su conjunto, junto con los componentes directamente relacionados en Qiskit, se trasladará al repositorio Qiskit Dynamics para facilitar aún más la simulación de pulsos y control de bajo nivel. Qiskit 1.x seguirá dando soporte al
qiskit.pulsehasta el final de su vida útil.
Circuitos obsoletos
-
Se ha suprimido el atributo
Instruction.conditiony el métodoInstruction.c_if()método. Se eliminarán en Qiskit 2.0, junto con cualquier uso en el modelo de datos de Qiskit. Esta funcionalidad ha sido sustituida por la claseIfElseOpque puede utilizarse para describir una condición clásica en un circuito. Por ejemplo, un circuito que utiliceInstruction.c_if()comofrom qiskit.circuit import QuantumCircuit qc = QuantumCircuit(2, 2) qc.h(0) qc.x(0).c_if(0, 1) qc.z(1.c_if(1, 0) qc.measure(0, 0) qc.measure(1, 1)Se puede volver a escribir de esta manera:
qc = QuantumCircuit(2, 2) qc.h(0) with qc.if_test((qc.clbits[0], True)): qc.x(0) with qc.if_test((qc.clbits[1], False)): qc.z(1) qc.measure(0, 0) qc.measure(1, 1)El ahora obsoleto
ConvertConditionsToIfOpspara automatizar esta conversión en los circuitos existentes. -
Como parte de la obsolescencia del paquete Qiskit Pulse, las siguientes dependencias también quedan obsoletas:
qiskit.circuit.QuantumCircuit.calibrationsqiskit.circuit.QuantumCircuit.has_calibration_for()qiskit.circuit.QuantumCircuit.add_calibration()qiskit.dagcircuit.DAGCircuit.calibrationsqiskit.dagcircuit.DAGCircuit.has_calibration_for()qiskit.dagcircuit.DAGCircuit.add_calibration()qiskit.dagcircuit.DAGDependency.calibrations
-
En
QuantumCircuit.unityQuantumCircuit.durationhan quedado obsoletos y se eliminarán en Qiskit 2.0.0. Estos atributos se utilizaron para rastrear la duración estimada y la unidad de esa duración para ejecutar en el circuito. Sin embargo, los valores de estos atributos eran siempre limitados, ya que sólo se rellenaban correctamente si el transpilador se ejecutaba con la configuración correcta. La duración también era sólo una suposición basada en el camino más largo en la suma de la duración deDAGCircuity nunca tendría en cuenta correctamente el flujo de control o los condicionales del circuito. -
En
DAGCircuit.unityDAGCircuit.durationhan quedado obsoletos y se eliminarán en Qiskit 2.0.0. Estos atributos se utilizaron para rastrear la duración estimada y la unidad de esa duración para ejecutar en el circuito. Sin embargo, los valores de estos atributos eran siempre limitados, ya que sólo se rellenaban correctamente si el transpilador se ejecutaba con la configuración correcta. La duración también era sólo una suposición basada en el camino más largo en la suma de la duración deDAGCircuity nunca tendría en cuenta correctamente el flujo de control o los condicionales del circuito. -
En
Instruction.durationyInstruction.unithan quedado obsoletos y se eliminarán en Qiskit 2.0.0. Esto incluye establecer los argumentosunitodurationpara cualquierqiskit.circuit.Instructiono subclase. Estos atributos se utilizaron para adjuntar una duración de ejecución personalizada y una unidad para esa duración a una instrucción individual. Sin embargo, la fuente de verdad de la duración de una puerta es elBackendV2Targetque contiene la duración de cada instrucción soportada en el backend. La duración de una instrucción no es algo que normalmente pueda ajustar el usuario y es una propiedad inmutable del backend. Si antes utilizaba esta función para experimentar con diferentes duraciones de puertas, puede mutar el campoInstructionProperties.durationen una instrucciónTargetpara establecer una duración personalizada para una instrucción en un backend (la unidad siempre está en segundos en el campoTarget).
Proveedores obsoletos
-
El método
BasicSimulator.configuration()está obsoleto y se eliminará en 2.0.0. Este método devuelve una instancia deproviders.models.BackendConfigurationheredada que forma parte del modelo obsoletoBackendV1. Este modelo se ha sustituido porBackendV2en el que las restricciones se almacenan directamente en la instancia de backend o en el archivo subyacenteTarget(backend.target).Esta es una guía rápida para acceder a los atributos más comunes de
BackendConfigurationen el modeloBackendV2modelo:BackendV1 model (deprecated) ------------> BackendV2 model ---------------------------- --------------- backend.configuration().backend_name backend.name backend.configuration().backend_version backend.backend_version backend.configuration().n_qubits backend.num_qubits backend.configuration().num_qubits backend.num_qubits backend.configuration().basis_gates backend.target.operation_names (*) backend.configuration().coupling_map backend.target.build_coupling_map() backend.configuration().local No representation backend.configuration().simulator No representation backend.configuration().conditional No representation backend.configuration().open_pulse No representation backend.configuration().memory No representation backend.configuration().max_shots No representation(*) Tenga en cuenta que
Backend.target.operation_namesincluyebasis_gatese instrucciones adicionales nogate, en algunas implementaciones puede ser necesario filtrar la salida.Consulte esta guía para obtener más información sobre la migración al modelo
BackendV2modelo. -
Como parte de la obsolescencia del paquete Qiskit Pulse, todas las funciones relacionadas con Pulse en
qiskit.providers.BackendV2la clase están quedando obsoletas. Esto incluye los siguientes métodos:En consecuencia, los métodos de canalización correspondientes en el
qiskit.providers.BackendV2Converteryqiskit.providers.fake_provider.GenericBackendV2también quedan obsoletos.Además, los argumentos
pulse_channelsycalibrate_instructionsdel métodoBackendV2quedan obsoletos. -
El argumento
defaultsestá obsoleto en la funciónqiskit.providers.convert_to_target()función.
QPY Obsolescencias
- Como parte del paquete Qiskit Pulse obsoleto, serializar
qiskit.pulse.ScheduleBlock-también está obsoleta. En particular, el paso deqiskit.pulse.ScheduleBlockobjetos a los programas argumento en elqiskit.qpy.dump().
Deprecaciones del transpilador
-
Obsoleto
StochasticSwapque ha sido sustituido porSabreSwap. Si la clase se llama desde la función transpile, el cambio sería, por ejemplo:from qiskit import transpile from qiskit.circuit import QuantumCircuit from qiskit.transpiler import CouplingMap from qiskit.providers.fake_provider import GenericBackendV2 qc = QuantumCircuit(4) qc.h(0) qc.cx(0, range(1, 4)) qc.measure_all() cmap = CouplingMap.from_heavy_hex(3) backend = GenericBackendV2(num_qubits=cmap.size(), coupling_map=cmap) tqc = transpile( qc, routing_method="stochastic", layout_method="dense", seed_transpiler=12342, target=backend.target )a:
tqc = transpile( qc, routing_method="sabre", layout_method="sabre", seed_transpiler=12342, target=backend.target )Mientras que para un gestor de pases, el cambio sería:
passmanager = PassManager(StochasticSwap(coupling, 20, 13)) new_qc = passmanager.run(qc)a:
passmanager = PassManager(SabreSwap(backend.target, "basic")) new_qc = passmanager.run(qc) -
El pass transpiler
ConvertConditionsToIfOpsha quedado obsoleto y se eliminará en Qiskit 2.0.0. Esta clase ha quedado obsoleta porque el modelo de datos subyacente al que convierte este pase ha quedado obsoletoInstruction.conditiondel que convierte este pase ha quedado obsoleto y se eliminará en 2.0.0. -
Proporcionar puertas personalizadas a través del argumento
basis_gatesestá obsoleto tanto paratranspile()ygenerate_preset_pass_manager(). Esta funcionalidad se eliminará en Qiskit 2.0. El modeloTargety se pueden proporcionar a través del argumentotarget. Se puede construir unaTargetdesde cero o utilizar el métodoTarget.from_configuration()con el argumentocustom_name_mapping. Por ejemplo:from qiskit.circuit.library import XGate from qiskit.transpiler.target import Target basis_gates = ["my_x", "cx"] custom_name_mapping = {"my_x": XGate()} target = Target.from_configuration( basis_gates=basis_gates, num_qubits=2, custom_name_mapping=custom_name_mapping ) -
Como parte de la obsolescencia del paquete Qiskit Pulse, los aspectos relacionados con el pulso en la
qiskit.transpiler.Targetclase están quedando obsoletos. Esto incluye:update_from_instruction_schedule_map()has_calibration()get_calibration()instruction_schedule_map()
Además, también se están dejando de utilizar las siguientes pasadas del transpilador:
-
El argumento
inst_mapengenerate_preset_pass_manager(),from_configuration(),PassManagerConfigygenerate_scheduling()está obsoleto. -
El argumento
calibrationen los métodosInstructionProperties()en los métodos inicializadores. -
Los siguientes
transpile()ygenerate_preset_pass_manager()quedan obsoletos en favor de la definición de un argumento personalizadoTarget:instruction_durations,timing_constraints, ybackend_properties. Estos argumentos pueden utilizarse para construir un objetivo conTarget.from_configuration():Target.from_configuration( ... backend_properties = backend_properties, instruction_durations = instruction_durations, timing_constraints = timing_constraints ) -
El método
PassManagerConfig.from_backend()dejará de admitir entradas de tipoBackendV1en el parámetro backend en una futura versión no anterior a 2.0.BackendV1está obsoleto y las implementaciones deben pasar aBackendV2.
Herramientas Características en desuso
-
El módulo
qiskit.result.mitigationha quedado obsoleto y se eliminará en Qiskit 2.0. La desaprobación incluye losLocalReadoutMitigatoryCorrelatedReadoutMitigatorasí como las funciones de utilidad asociadas. Su funcionalidad ha sido sustituida por el paquete mthree, que se encuentra en https://github.com/Qiskit/qiskit-addon-mthree. -
Como parte de la eliminación gradual del paquete Qiskit Pulse, las siguientes funciones y clases también quedarán obsoletas:
Corrección de errores
-
Corregida una regresión de rendimiento en
QuantumCircuit.assign_parameters()introducida en Qiskit 1.2.0 al llamar al método en un bucle cerrado, que provocaba que sólo un pequeño número de parámetros de un circuito muy paramétrico se ligaran en cada iteración. Si es posible, sigue siendo más eficaz llamar aassign_parameters()sólo una vez, con todas las asignaciones al mismo tiempo, ya que esto reduce la proporción de tiempo dedicado a la normalización de la entrada y la sobrecarga de comprobación de errores. -
Para
BasicSimulatorla entradabasis_gatesde la instancia de configuración devuelta por el métodoconfiguration()es ahora una lista en lugar de una instanciadict_keys, lo que coincide con el tipo esperado y permite copiar en profundidad la instancia de configuración. -
Se ha solucionado un problema con
DAGCircuit.apply_operation_back()yDAGCircuit.apply_operation_front()por el que si se introducía un objetoClbitcomo entrada para el argumentoqargs, se aceptaba silenciosamente. Esto se ha corregido para que la falta de correspondencia de tipos se identifique correctamente y se genere una excepción. -
Se ha corregido un decorador que faltaba en
C3SXGateque hacía que fallara siGate.to_matrix()era llamado. La matriz de la puerta ahora se devuelve como se esperaba. -
Se ha corregido un error en
QuantumCircuit.assign_parameters()que se producía al asignar parámetros a compuertas estándar cuya definición ya se había activado. En este caso, los nuevos valores no se propagaban correctamente a las instancias de la puerta. Aunque el circuito en sí seguía compilándose como se esperaba, al inspeccionar las operaciones individuales seguía apareciendo el parámetro antiguo.Por ejemplo:
from qiskit.circuit.library import EfficientSU2 circuit = EfficientSU2(2, flatten=True) circuit.assign_parameters([1.25] * circuit.num_parameters, inplace=True) print(circuit.data[0].operation.params) # would print θ[0] instead of 1.25Corregido #13478.
-
Corregido un error con el
"circular"y"sca"enredo paraNLocaly sus derivados. En el caso de los bloques de entrelazamiento de más de 2 qubits, antes faltaban algunas conexiones en el entrelazamiento circular. Por ejemplo, para 4 qubits y un tamaño de bloque de 3 el código utilizado anteriormente:[(2, 3, 0), (0, 1, 2), (1, 2, 3)]pero ahora está añadiendo correctamente las conexiones
(3, 0, 1), es decir:[(2, 3, 0), (3, 0, 1), (0, 1, 2), (1, 2, 3)]Así, los enredos
"circular"y"sca"utilizan bloques de enredonum_qubitspor capa. -
Añade más puertas Clifford al
CollectCliffordstranspiler pass. En particular, hemos añadido las puertasECRGate,DCXGate,iSwapGate,SXGateySXdgGatea este paso del transpilador. -
Se ha corregido un error en
QuantumCircuit.decompose()por el que los objetos que podían sintetizarse conHighLevelSynthesisse sintetizaban primero y luego se descomponían inmediatamente (es decir, se descomponían dos veces en lugar de una). Esto afectó a puertas comoMCXGateoCliffordentre otras. -
Se ha corregido un error en
QuantumCircuit.decompose()por el que los objetos de alto nivel sin definición no se descomponían si se establecían explícitamente mediante el argumento"gates_to_decompose". Por ejemplo, antes lo siguiente no realizaba una descomposición, pero ahora funciona como se espera:from qiskit import QuantumCircuit from qiskit.quantum_info import Clifford from qiskit.transpiler.passes import Decompose cliff = Clifford(HGate()) circuit = QuantumCircuit(1) circuit.append(cliff, [0]) decomposed = Decompose(gates_to_decompose=["clifford"])(circuit) -
Anteriormente, el
HighLevelSynthesistranspiler pass sintetizaba una instrucción para la que existía un plugin de síntesis, independientemente de si la instrucción ya era compatible con el destino o formaba parte de la instrucción pasada explícitamentebasis_gates. Ahora se ha corregido este comportamiento, de modo que ya no se sintetizan estas instrucciones ya soportadas. -
El paso de transpilación
InverseCancellationrecurrirá ahora aControlFlowOpoperaciones presentes en unQuantumCircuit. Anteriormente, el pase ignoraba los pares de puertas inversas dentro de los bloques de flujo de control que podrían haberse cancelado. Consulte el nº 13437 para más detalles. -
Corrección de un error en
Isometrydebido a una aserción innecesaria, que provocaba un error enUnitaryGate.control()cuandoUnitaryGatetenía más de dos qubits. -
El atributo
QuantumCircuit.parametersestará vacío cuando se utiliceQuantumCircuit.copy_empty_like()en un circuito paramétrico. Anteriormente, una caché interna se copiaba sin invalidarse. Corrección #12617. -
QuantumCircuit.depth()manejará ahora correctamente las operaciones que no tengan operandos, tales comoGlobalPhaseGate. -
QuantumCircuit.depth()contará ahora las variables y clbits utilizados en las expresiones en tiempo real como parte del cálculo de profundidad. -
Arreglar el
SolovayKitaeval cargar aproximaciones básicas a partir de un archivo existente en.npy. Anteriormente, cargar una aproximación almacenada que permitía reducciones adicionales (por ejemplo, debido a cancelaciones de puertas) podía provocar un fallo en tiempo de ejecución. Además, la diferencia de fase global del producto de compuerta U(2) y la representación SO(3) se perdió durante un procedimiento de guardar-recargar. Arregla Qiskit/qiskit#12576. -
Se ha corregido un error cuando
SparsePauliOp.paulisse establece como unPauliListcon fase distinta de cero, por el que las llamadas posteriores a varios métodosSparsePauliOpproducían resultados incorrectos. Ahora, cuandoSparsePauliOp.paulisse fija en unPauliListcon fase distinta de cero, la fase se absorbe enSparsePauliOp.coeffsy la fase de la entradaPauliListse pone a cero. -
Se ha corregido un error en
qiskit.visualization.pulse_v2.interface.drawque no dibujaba los programas de pulsos cuando se llamaba a la función dibujar con unBackendV2argumento. Dado que el backend V2 no informa de las frecuencias de los canales hardware, el dibujo generado mostrará 'no freq' debajo de cada etiqueta de canal. -
Se ha solucionado un problema con
dag_drawer()yDAGCircuit.draw()cuando se intentaba visualizar una instanciaDAGCircuitque conteníaVarcables, por lo que el visualizador lanzaba una excepción. Este comportamiento se ha corregido y se generará la visualización esperada. -
El pase
VF2Layoutpass lanzaría una excepción cuando se le proporcionara unaTargetsin restricciones de conectividad. Este sería el caso de los objetivos de Aer 0.13. El problema se ha solucionado. -
Corrige un error al llamar al método
Gate.repeat(). Consulte el nº 11990 para más detalles. -
Se ha corregido un error que provocaba que
Statevector.expectation_value()diera resultados incorrectos para el operador de identidad cuando el vector de estado no estaba normalizado. -
El constructor
GenericBackendV2estaba permitiendo crear backends malformados porque aceptaba puertas base que no podían ser asignadas en el tamaño de backend especificado. Es decir, un backend con un solo qubit no debería aceptar una base con puertas de dos qubits. -
ParameterExpressionse actualizó para que las instancias totalmente vinculadas que se comparan con instancias de los tipos numéricos incorporados de Python (comofloatyint) también tengan valores hash que coincidan con los de las otras instancias. Este cambio garantiza que estos tipos puedan utilizarse indistintamente como claves de diccionario. Ver #12488. -
El analizador OpenQASM 2 (
qiskit.qasm2) ahora puede manejar condicionales con enteros que no caben en un entero de 64 bits. Corregido #12773. -
Las compuertas personalizadas (aquellas derivadas de una sentencia
gate) en programas importados de OpenQASM 2 tendrán ahora unaGate.to_matrix()implementación. Antes no tenían definición de matriz, lo que significaba que los viajes de ida y vuelta a través de OpenQASM 2 podían perder innecesariamente la capacidad de derivar la matriz de la puerta. Nótese, sin embargo, que la matriz se calcula encontrando recursivamente las matrices de las definiciones de las puertas internas, como haceOperatorlo que puede ser menos eficaz que antes de la ida y vuelta. -
Anteriormente,
DAGCircuit.replace_block_with_op()permitía colocar una operaciónn-qubit en un bloque demqubits, dejando el DAG en un estado inválido. Este comportamiento se ha corregido y el intento generará un mensajeDAGCircuitError. -
Fijo
Operator.power()cuando se llama con potencias no enteras en una matriz cuya forma Schur no es diagonal (por ejemplo, la mayoría de las matrices no unitarias). -
Operator.power()devolverá ahora de forma más fiable el valor principal esperado de una matriz potencia fraccionaria de una matriz unitaria con un valor propio . Esto es delicado en general, porque los efectos de redondeo en coma flotante pueden hacer que una matriz tenga un valor propio en el lado negativo del corte de rama (incluso si su relación matemática exacta no lo haría), y la imprecisión en varias llamadas BLAS puede encontrar falsamente el lado equivocado del corte de rama.Operator.power()ahora desplaza la ubicación de corte de rama para potencias de matriz a una pequeña rotación compleja lejos de . Esto no resuelve el problema, sólo lo desplaza a un lugar donde es mucho menos probable que sea notable para los tipos de operadores que suelen aparecer. Utiliza el nuevo parámetrobranch_cut_rotationpara tener más control sobre esto.Ver #13305.
-
Corregido un no-determinismo por proceso en
SparsePauliOp.to_matrix(). El orden exacto de las operaciones de coma flotante en la suma variaba antes por proceso, pero ahora será idéntico entre distintas invocaciones del mismo script. Ver #13413. -
Target.has_calibration()se ha actualizado para que no lance una excepción para una instrucción que se ha añadido al objetivo conNonepara sus propiedades de instrucción. Correcciones #12525.