Esquema

La forma más sencilla de construir un schedule común es utilizar las funciones auxiliares:

  • linear: Interpolación lineal entre dos Hamiltonianos.

  • quadratic: Interpolación cuadrática entre dos Hamiltonianos.

  • polynomial: Interpolación polinómica de grado arbitrario entre dos Hamiltonianos.

  • sinusoidal: Interpolación sinusoidal entre dos Hamiltonianos.

Por ejemplo, para crear un schedule lineal que interpola entre un Hamiltoniano conductor y un Hamiltoniano de problema durante un tiempo de 10 unidades:

from qilisdk.analog import Schedule, X, Z

H1 = X(0) + X(1)
H2 = Z(0) * Z(1)

schedule = Schedule.linear(H1, H2, 10.0)
schedule.draw()

Para schedules más complejos, puede utilizar la clase Schedule directamente, la cual ofrece una interfaz flexible para definir completamente los coeficientes del Hamiltoniano dependientes del tiempo. La clase Schedule mapea puntos temporales a coeficientes de Hamiltonian. Los coeficientes pueden ser números, parámetros/términos, o funciones invocables del tiempo, y pueden definirse en puntos discretos o sobre intervalos que se muestrean automáticamente.

Argumentos clave

  • dt (float): resolución de las muestras temporales. El valor predeterminado es 0.1.

  • hamiltonians (dict[str, Hamiltonian]): Mapa de etiquetas a instancias de Hamiltonian.

  • coefficients (dict[str, dict]): Mapeo de la etiqueta del Hamiltoniano a un diccionario de definición temporal. Cada clave es un punto temporal (float/parámetro/término) o una tupla de 2 elementos que define un intervalo; cada valor puede ser:
    • el coeficiente del Hamiltoniano en ese instante

    • o una función invocable que devuelva un coeficiente. Esta función puede recibir un parámetro t que será sustituido por el tiempo. Además, cualquier otro parámetro pasado a esta función debe tener un valor predeterminado o tener su valor especificado en los **kwargs.

  • interpolation (Interpolation): comportamiento LINEAR (predeterminado) o STEP entre los puntos proporcionados.

  • total_time (float | Parameter | Term | None): Tiempo máximo opcional que reescala todos los puntos temporales preservando sus posiciones relativas.

Nota

Cuando se colocan parámetros en el eje temporal (p. ej., como puntos temporales o extremos de intervalos), el schedule restringe automáticamente esos parámetros para que permanezcan entre sus puntos temporales vecinos, de modo que el orden de la línea temporal siga siendo válido.

Ejemplo 1: Coeficientes invocables con muestreo por intervalos

from qilisdk.analog import Schedule, X, Z
from qilisdk.analog.schedule import Interpolation

h_driver = X(0) + X(1)
h_problem = Z(0) * Z(1)

schedule = Schedule(
    hamiltonians={"driver": h_driver, "problem": h_problem},
    coefficients={
        "driver": {(0.0, 10.0): lambda t: 1 - t / 10.0},
        "problem": {(0.0, 10.0): lambda t: t / 10.0},
    },
    dt=0.5,
    interpolation=Interpolation.LINEAR,
)
schedule.draw()

Ejemplo 2: Interpolación por pasos y reescalado del tiempo máximo

from qilisdk.analog import Schedule, Z
from qilisdk.analog.schedule import Interpolation
from qilisdk.utils.visualization.style import ScheduleStyle

h = Z(0)
schedule = Schedule(
    hamiltonians={"h": h},
    coefficients={"h": {0.0: 1.0, 5.0: 0.2}},
    dt=0.01,
    interpolation=Interpolation.STEP,
)

# Later, shorten the experiment to 3s without redefining points
schedule.draw(ScheduleStyle(title="Before Time Scaling"))
schedule.scale_max_time(3.0)
schedule.draw(ScheduleStyle(title="After Time Scaling"))
print("Time grid:", schedule.tlist)
print("Coeff at t=1.5:", schedule.coefficients["h"][1.5])

Nota

La función draw muestrea 1/dt puntos del schedule; por lo tanto, para obtener mayor resolución en el gráfico se puede reducir dt.

Schedules Parametrizados

Los coeficientes de Schedule pueden ser simbólicos, lo que permite bucles de optimización clásica o experimentos que exploran una familia de perfiles temporales. Los coeficientes pueden ser instancias de Parameter o expresiones algebraicas (Term) construidas a partir de parámetros. El schedule registra cada parámetro que encuentra para que pueda consultarlos o modificarlos posteriormente.

from qilisdk.analog import Schedule, Z
from qilisdk.core import Parameter, GreaterThanOrEqual

gamma = Parameter("gamma", value=0.5, bounds=(0.0, 1.0))
T = Parameter("T", value=10.0, bounds=(1.0, 20.0))

schedule = Schedule(
    hamiltonians={"problem": Z(0)},
    coefficients={"problem": {(0.0, T): lambda t: gamma * t}},
    dt=0.1,
    total_time=T,
)

schedule.get_parameters()

schedule.set_parameters({"gamma": 0.7})
print(schedule.get_parameter_names())   # ['gamma', 'T']
print(schedule.get_constraints())       # [0 <= T]

Nota

Para schedules, Hamiltonianos e interpoladores, use get_parameters y los métodos de acceso relacionados para inspeccionar el estado de los parámetros.