Acelere sus cargas de trabajo híbridas con simuladores integrados de PennyLane - Amazon Braket

Las traducciones son generadas a través de traducción automática. En caso de conflicto entre la traducción y la version original de inglés, prevalecerá la version en inglés.

Acelere sus cargas de trabajo híbridas con simuladores integrados de PennyLane

Veamos cómo puedes usar los simuladores integrados de PennyLane Amazon Braket Hybrid Jobs para ejecutar cargas de trabajo híbridas. El simulador integrado basado en GPU de Pennylane utiliza la biblioteca Nvidia CuQuantum para acelerar las simulaciones de circuitos.lightning.gpu El simulador de GPU integrado viene preconfigurado en todos los contenedores de trabajo de Braket y los usuarios pueden utilizar de forma inmediata. En esta página, le mostramos cómo usarlightning.gpu para acelerar las cargas de trabajo híbridas.

Usolightning.gpu para cargas de trabajo del algoritmo de optimización aproximada cuántica

Considere los ejemplos del algoritmo de optimización aproximada cuántica (QAOA) de este cuaderno. Para seleccionar un simulador incrustado, especifique que eldevice argumento sea una cadena de la forma:"local:<provider>/<simulator_name>". Por ejemplo, configuraría"local:pennylane/lightning.gpu" paralightning.gpu. La cadena de dispositivos que se asigna a la Job híbrida cuando se inicia se pasa a la tarea como variable de entorno"AMZN_BRAKET_DEVICE_ARN".

device_string = os.environ["AMZN_BRAKET_DEVICE_ARN"] prefix, device_name = device_string.split("/") device = qml.device(simulator_name, wires=n_wires)

En esta página, comparemos los dos simuladores vectoriales de PennyLane estado integradoslightning.qubit (que están basados en la CPU) ylightning.gpu (que están basados en la GPU). Deberás proporcionar a los simuladores algunas descomposiciones de puertas personalizadas para poder calcular varios gradientes.

Ahora está listo para preparar el script de lanzamiento del trabajo. Ejecutará el algoritmo QAOA con dos tipos de instancias:m5.2xlarge yp3.2xlarge. El tipo dem5.2xlarge instancia es comparable a un portátil estándar para desarrolladores. Sep3.2xlarge trata de una instancia de computación acelerada que tiene una sola GPU NVIDIA Volta con 16 GB de memoria.

Elhyperparameters para todos tus trabajos será el mismo. Todo lo que necesitas hacer para probar diferentes instancias y simuladores es cambiar dos líneas de la siguiente manera.

# Specify device that the job will primarily be targeting device = "local:pennylane/lightning.qubit" # Run on a CPU based instance with about as much power as a laptop instance_config = InstanceConfig(instanceType='ml.m5.2xlarge')

o bien:

# Specify device that the job will primarily be targeting device = "local:pennylane/lightning.gpu" # Run on an inexpensive GPU based instance instance_config = InstanceConfig(instanceType='ml.p3.2xlarge')
nota

Si especificasinstance_config que usa una instancia basada en GPU, pero eligesdevice que sea el simulador integrado basado en la CPU (lightning.qubit), no se utilizará la GPU. ¡Asegúrate de utilizar el simulador integrado basado en la GPU si deseas apuntar a la GPU!

Primero, puedes crear dos trabajos y resolver Max-Cut con QAOA en un gráfico con 18 vértices. Esto se traduce en un circuito de 18 qubits, relativamente pequeño y factible de ejecutar rápidamente en su ordenador portátil o en lam5.2xlarge instancia.

num_nodes = 18 num_edges = 24 seed = 1967 graph = nx.gnm_random_graph(num_nodes, num_edges, seed=seed) # And similarly for the p3 job m5_job = AwsQuantumJob.create( device=device, source_module="qaoa_source", job_name="qaoa-m5-" + str(int(time.time())), image_uri=image_uri, # Relative to the source_module entry_point="qaoa_source.qaoa_algorithm_script", copy_checkpoints_from_job=None, instance_config=instance_config, # general parameters hyperparameters=hyperparameters, input_data={"input-graph": input_file_path}, wait_until_complete=True, )

El tiempo medio de iteración de lam5.2xlarge instancia es de unos 25 segundos, mientras que el de lap3.2xlarge instancia es de unos 12 segundos. Para este flujo de trabajo de 18 qubits, la instancia de GPU nos ofrece una aceleración del doble. Si consulta la página de precios de Amazon Braket Hybrid Jobs, verá que el coste por minuto de unam5.2xlarge instancia es de 0,00768 USD, mientras que el de lap3.2xlarge instancia es de 0,06375 USD. Ejecutar 5 iteraciones en total, como hiciste aquí, costaría 0,016 USD con la instancia de CPU o 0,06375 USD con la instancia de GPU, ¡ambas bastante económicas!

Ahora compliquemos el problema e intentemos resolver un problema de Max-Cut en un gráfico de 24 vértices, lo que se traducirá en 24 qubits. Vuelva a ejecutar los trabajos en las mismas dos instancias y compare el costo.

nota

¡Verá que el tiempo necesario para ejecutar este trabajo en la instancia de la CPU puede ser de unas cinco horas!

num_nodes = 24 num_edges = 36 seed = 1967 graph = nx.gnm_random_graph(num_nodes, num_edges, seed=seed) # And similarly for the p3 job m5_big_job = AwsQuantumJob.create( device=device, source_module="qaoa_source", job_name="qaoa-m5-big-" + str(int(time.time())), image_uri=image_uri, # Relative to the source_module entry_point="qaoa_source.qaoa_algorithm_script", copy_checkpoints_from_job=None, instance_config=instance_config, # general parameters hyperparameters=hyperparameters, input_data={"input-graph": input_file_path}, wait_until_complete=True, )

El tiempo medio de iteración de lam5.2xlarge instancia es de aproximadamente una hora, mientras que para lap3.2xlarge instancia es de aproximadamente dos minutos. Para este problema mayor, ¡la instancia de la GPU es un orden de magnitud más rápida! Todo lo que tenías que hacer para beneficiarte de esta aceleración era cambiar dos líneas de código, intercambiando el tipo de instancia y el simulador local utilizado. Ejecutar 5 iteraciones en total, como se hizo aquí, costaría unos 2.27072 USD con la instancia de CPU o unos 0.775625 USD con la instancia de GPU. El uso de la CPU no solo es más caro, sino que también requiere más tiempo de ejecución. Acelerar este flujo de trabajo con una instancia PennyLane de GPU disponible enAWS, mediante un simulador integrado respaldado por NVIDIA CuQuantum, permite ejecutar flujos de trabajo con recuentos de cúbits intermedios (entre 20 y 30) con un coste total inferior y en menos tiempo. Esto significa que puede experimentar con la computación cuántica incluso en el caso de problemas que sean demasiado grandes para ejecutarlos rápidamente en su portátil o en una instancia de tamaño similar.

Aprendizaje automático cuántico y paralelismo de datos

Si su tipo de carga de trabajo es el aprendizaje automático cuántico (QML) que se entrena en conjuntos de datos, puede acelerarla aún más mediante el paralelismo de datos. En QML, el modelo contiene uno o más circuitos cuánticos. El modelo también puede contener o no redes neuronales clásicas. Al entrenar el modelo con el conjunto de datos, los parámetros del modelo se actualizan para minimizar la función de pérdida. Por lo general, se define una función de pérdida para un solo punto de datos y la pérdida total para la pérdida promedio de todo el conjunto de datos. En QML, las pérdidas generalmente se calculan en serie antes de promediarlas hasta la pérdida total para los cálculos de gradiente. Este procedimiento lleva mucho tiempo, especialmente cuando hay cientos de puntos de datos.

Como la pérdida de un punto de datos no depende de otros puntos de datos, ¡las pérdidas se pueden evaluar en parallel! Las pérdidas y los gradientes asociados a diferentes puntos de datos se pueden evaluar al mismo tiempo. Esto se conoce como paralelismo de datos. Gracias a su biblioteca parallel SageMaker de datos distribuidos, Amazon Braket Hybrid Jobs le permite aprovechar mejor el paralelismo de datos para acelerar su entrenamiento.

Considere la siguiente carga de trabajo de QML para el paralelismo de datos, que utiliza el conjunto de datos Sonar del conocido repositorio de la UCI como ejemplo de clasificación binaria. El conjunto de datos Sonar tiene 208 puntos de datos, cada uno con 60 características que se recopilan a partir de las señales de sonar que rebotan en los materiales. Cada punto de datos está etiquetado como «M» para las minas o «R» para las rocas. Nuestro modelo QML consiste en una capa de entrada, un circuito cuántico como capa oculta y una capa de salida. Las capas de entrada y salida son redes neuronales clásicas implementadas en PyTorch. El circuito cuántico se integra con las redes PyTorch neuronales mediante PennyLane el módulo qml.qnn. Consulte nuestros cuadernos de ejemplo para obtener más información sobre la carga de trabajo. Al igual que en el ejemplo de QAOA anterior, puedes aprovechar la potencia de la GPU mediante el uso de simuladores integrados basados en GPU, como PennyLane los que se utilizanlightning.gpu para mejorar el rendimiento en comparación con los simuladores basados en CPU integradas.

Para crear un trabajo, puede llamarAwsQuantumJob.create y especificar el script del algoritmo, el dispositivo y otras configuraciones mediante sus argumentos de palabras clave.

instance_config = InstanceConfig(instanceType='ml.p3.2xlarge') hyperparameters={"nwires": "10", "ndata": "32", ... } job = AwsQuantumJob.create( device="local:pennylane/lightning.gpu", source_module="qml_source", entry_point="qml_source.train_single", hyperparameters=hyperparameters, instance_config=instance_config, ... )

Para utilizar el paralelismo de datos, debe modificar algunas líneas de código en el script del algoritmo de la biblioteca SageMaker distribuida para paralelizar correctamente el entrenamiento. Primero, importas elsmdistributed paquete que se encarga de la mayor parte del trabajo pesado de distribuir las cargas de trabajo entre varias GPU e instancias. Este paquete está preconfigurado en el freno PyTorch y TensorFlow los contenedores. Eldist módulo indica a nuestro script de algoritmo cuál es el número total de GPU para el entrenamiento (world_size)rank y el ancho del núcleolocal_rank de una GPU. rankes el índice absoluto de una GPU en todas las instancias, mientras quelocal_rank es el índice de una GPU dentro de una instancia. Por ejemplo, si hay cuatro instancias, cada una con ocho GPU asignadas para el entrenamiento, losrank rangos oscilan entre 0 y 31 ylocal_rank entre 0 y 7.

import smdistributed.dataparallel.torch.distributed as dist dp_info = { "world_size": dist.get_world_size(), "rank": dist.get_rank(), "local_rank": dist.get_local_rank(), } batch_size //= dp_info["world_size"] // 8 batch_size = max(batch_size, 1)

A continuación, define unDistributedSampler según elworld_sizerank y, a continuación, lo pasa al cargador de datos. Este muestreador evita que las GPU accedan a la misma porción de un conjunto de datos.

train_sampler = torch.utils.data.distributed.DistributedSampler( train_dataset, num_replicas=dp_info["world_size"], rank=dp_info["rank"] ) train_loader = torch.utils.data.DataLoader( train_dataset, batch_size=batch_size, shuffle=False, num_workers=0, pin_memory=True, sampler=train_sampler, )

A continuación, utiliza laDistributedDataParallel clase para habilitar el paralelismo de datos.

from smdistributed.dataparallel.torch.parallel.distributed import DistributedDataParallel as DDP model = DressedQNN(qc_dev).to(device) model = DDP(model) torch.cuda.set_device(dp_info["local_rank"]) model.cuda(dp_info["local_rank"])

Los cambios anteriores son los que necesita para utilizar el paralelismo de datos. En QML, a menudo desea guardar los resultados e imprimir el progreso del entrenamiento. Si cada GPU ejecuta el comando de guardar e imprimir, el registro se inundará con la información repetida y los resultados se sobrescribirán entre sí. Para evitarlo, solo puedes guardar e imprimir desde la GPU que tengarank 0.

if dp_info["rank"]==0: print('elapsed time: ', elapsed) torch.save(model.state_dict(), f"{output_dir}/test_local.pt") save_job_result({"last loss": loss_before})

Amazon Braket Hybrid Jobs admite tipos deml.p3.16xlarge instancias para la biblioteca parallel de datos SageMaker distribuidos. El tipo de instancia se configura mediante elInstanceConfig argumento de Hybrid Jobs. Para que la biblioteca parallel de datos SageMaker distribuidos sepa que el paralelismo de datos está activado, debe añadir dos hiperparámetros adicionales,"sagemaker_distributed_dataparallel_enabled" establecer"true" y"sagemaker_instance_type" configurar el tipo de instancia que esté utilizando. Estos dos hiperparámetros se utilizan porsmdistributed paquete. El script de su algoritmo no necesita utilizarlos de forma explícita. En el SDK de Amazon Braket, proporciona un argumento de palabra clave prácticodistribution. distribution="data_parallel"Al crear trabajos, el SDK de Amazon Braket inserta automáticamente los dos hiperparámetros por usted. Si utiliza la API de Amazon Braket, debe incluir estos dos hiperparámetros.

Con el paralelismo de instancias y datos configurado, ahora puede enviar su trabajo. Hay 8 GPU en unaml.p3.16xlarge instancia. Al configurarinstanceCount=1, la carga de trabajo se distribuye entre las 8 GPU de la instancia. Si configurasinstanceCount más de uno, la carga de trabajo se distribuye entre las GPU disponibles en todas las instancias. Al usar varias instancias, cada instancia incurre en un cargo en función del tiempo que la utilices. Por ejemplo, cuando usas cuatro instancias, el tiempo facturable es cuatro veces el tiempo de ejecución por instancia, ya que hay cuatro instancias que ejecutan tus cargas de trabajo al mismo tiempo.

instance_config = InstanceConfig(instanceType='ml.p3.16xlarge', instanceCount=1, ) hyperparameters={"nwires": "10", "ndata": "32", ..., } job = AwsQuantumJob.create( device="local:pennylane/lightning.gpu", source_module="qml_source", entry_point="qml_source.train_dp", hyperparameters=hyperparameters, instance_config=instance_config, distribution="data_parallel", ... )
nota

En la creación de trabajos anterior,train_dp.py se encuentra el script del algoritmo modificado para utilizar el paralelismo de datos. Tenga en cuenta que el paralelismo de datos solo funciona correctamente cuando modifica el script del algoritmo de acuerdo con la sección anterior. Si la opción de paralelismo de datos está habilitada sin un script de algoritmo modificado correctamente, el trabajo puede generar errores o que cada GPU procese repetidamente el mismo segmento de datos, lo que no es eficiente.

Comparemos el tiempo de ejecución y el costo en un ejemplo en el que se entrena un modelo con un circuito cuántico de 26 qubits para el problema de clasificación binaria mencionado anteriormente. Laml.p3.16xlarge instancia utilizada en este ejemplo cuesta 0,4692 USD por minuto. Sin paralelismo de datos, el simulador tarda unos 45 minutos en entrenar el modelo para una época (es decir, más de 208 puntos de datos) y cuesta unos 20 dólares. Con el paralelismo de datos entre 1 y 4 instancias, solo se necesitan 6 minutos y 1,5 minutos, respectivamente, lo que se traduce en aproximadamente 2,8 USD para ambas. Al utilizar el paralelismo de datos en 4 instancias, no solo mejora el tiempo de ejecución 30 veces, ¡sino que también reduce los costos en un orden de magnitud!