

本文為英文版的機器翻譯版本，如內容有任何歧義或不一致之處，概以英文版為準。

# 使用 Amazon Braket 混合任務
<a name="braket-jobs"></a>

Amazon Braket Hybrid Jobs 可讓您執行混合量子傳統演算法，同時需要傳統 AWS 資源和量子處理單元 (QPUs)。混合任務旨在啟動請求的傳統資源、執行演算法，並在完成後釋放執行個體，因此您只需支付*使用的費用*。

混合任務非常適合長時間執行、反覆運算的演算法，這些演算法涉及使用傳統運算資源和量子運算資源。透過混合任務，在提交演算法以執行之後，Raket 會在可擴展的容器化環境中執行您的演算法。演算法完成後，您就可以擷取結果。

此外，從混合任務建立的量子任務受益於目標 QPU 裝置的較高優先順序佇列。此優先順序可確保在佇列中等待的其他任務之前處理和執行您的量子運算。這對於疊代混合演算法特別有利，其中一個量子任務的結果取決於先前量子任務的結果。此類演算法的範例包括[量子近似最佳化演算法 (QAOA)](https://github.com/amazon-braket/amazon-braket-examples/blob/main/examples/hybrid_quantum_algorithms/QAOA/QAOA_braket.ipynb)、[變化量子 eigensolver](https://github.com/amazon-braket/amazon-braket-examples/blob/main/examples/hybrid_quantum_algorithms/VQE_Chemistry/VQE_chemistry_braket.ipynb) [ 或量子機器學習](https://github.com/amazon-braket/amazon-braket-examples/blob/main/examples/hybrid_jobs/1_Quantum_machine_learning_in_Amazon_Braket_Hybrid_Jobs/Quantum_machine_learning_in_Amazon_Braket_Hybrid_Jobs.ipynb)。您也可以近乎即時地監控演算法進度，讓您追蹤成本、預算或自訂指標，例如訓練損失或期望值。

您可以使用下列方式存取 Braket 中的混合式任務：
+ [Amazon Braket Python SDK](https://github.com/aws/amazon-braket-sdk-python)。
+ [Amazon Braket 主控台](https://console.aws.amazon.com/braket/home)。
+ Amazon Braket API。

**Topics**
+ [何時使用 Amazon Braket 混合任務](#braket-jobs-use)
+ [使用 Amazon Braket 混合任務執行混合任務](#braket-jobs-works)
+ [混合任務的主要概念](braket-jobs-concepts.md)
+ [先決條件](braket-jobs-prerequisites.md)
+ [建立混合任務](braket-jobs-first.md)
+ [取消混合任務](braket-jobs-cancel.md)
+ [自訂您的混合任務](braket-jobs-customize.md)
+ [搭配 Amazon Braket 使用 PennyLane](hybrid.md)
+ [搭配 Amazon Braket 使用 CUDA-Q](braket-using-cuda-q.md)

## 何時使用 Amazon Braket 混合任務
<a name="braket-jobs-use"></a>

 Amazon Braket 混合任務可讓您執行混合式量子傳統演算法，例如變量量子 Eigensolver (VQE) 和量子近似最佳化演算法 (QAOA)，其結合傳統運算資源與量子運算裝置，以最佳化現今量子系統的效能。Amazon Braket Hybrid Jobs 提供三個主要優點：

1.  **效能**：Amazon Braket Hybrid Jobs 的效能優於從您自己的環境執行混合式演算法。當您的任務執行時，它會優先存取選取的目標 QPU。任務會在裝置上排入佇列的其他任務之前執行。這會導致混合演算法的執行時間較短且更可預測。Amazon Braket Hybrid Jobs 也支援參數編譯。您可以使用免費參數提交電路，而 Braket 會編譯一次電路，而不需要重新編譯以對相同電路進行後續參數更新，進而加快執行時間。

1.  **便利性**：Amazon Braket 混合任務可簡化設定和管理運算環境，並在混合演算法執行時保持執行狀態。您只需提供演算法指令碼，然後選取要在其中執行的量子裝置 （量子處理單元或模擬器）。Amazon Braket 會等待目標裝置變成可用、啟動傳統資源、在預先建置的容器環境中執行工作負載、將結果傳回 Amazon Simple Storage Service (Amazon S3)，並釋出運算資源。

1.  **指標**：Amazon Braket Hybrid Jobs 提供on-the-fly洞見，並近乎即時地將可自訂的演算法指標交付給 Amazon CloudWatch 和 Amazon Braket 主控台，讓您可以追蹤演算法的進度。

## 使用 Amazon Braket 混合任務執行混合任務
<a name="braket-jobs-works"></a>

若要使用 Amazon Braket 混合任務執行混合任務，您必須先定義演算法。您可以編寫*演算法指令碼*，也可以選擇使用 [Amazon Braket Python SDK ](https://github.com/aws/amazon-braket-sdk-python)或 [PennyLane](https://pennylane.ai) 來定義它。如果您想要使用其他 （開放原始碼或專屬） 程式庫，您可以使用 Docker 定義自己的自訂容器映像，其中包含這些程式庫。如需詳細資訊，請參閱[使用您自己的容器 (BYOC)](braket-jobs-byoc.md)。

在任一情況下，接下來您使用 Amazon Braket 建立混合任務API，並在其中提供演算法指令碼或容器，選取混合任務要使用的目標量子裝置，然後從各種選用設定中選擇。這些選用設定的預設值適用於大多數使用案例。若要讓目標裝置執行混合任務，您可以選擇 QPU、隨需模擬器 （例如 SV1DM1或 TN1) 或傳統混合任務執行個體本身。透過隨需模擬器或 QPU，您的混合任務容器會對遠端裝置進行 API 呼叫。使用內嵌模擬器時，模擬器會內嵌在與演算法指令碼相同的容器中。PennyLane [的閃電模擬器](https://github.com/PennyLaneAI/pennylane-lightning)內嵌預設預先建置的混合作業容器，供您使用。如果您使用內嵌 PennyLane 模擬器或自訂模擬器執行程式碼，您可以指定執行個體類型，以及您想要使用的執行個體數量。如需每個選擇的相關成本，請參閱 [Amazon Braket 定價頁面](https://aws.amazon.com/braket/pricing/)。

![\[流程圖顯示使用者與 Amazon Braket 元件、API、任務執行個體和模擬器的互動，適用於混合、QPU、隨需和內嵌任務。結果存放在 Amazon Simple Storage Service 儲存貯體中，並在 Amazon Braket 主控台上使用 Amazon CloudWatch 進行分析。 Amazon Braket\]](http://docs.aws.amazon.com/zh_tw/braket/latest/developerguide/images/braket-hybrid-job-run.png)


如果您的目標裝置是隨需或內嵌模擬器，Amazon Braket 會立即開始執行混合任務。它會啟動混合任務執行個體 （您可以在 API 呼叫中自訂執行個體類型）、執行演算法、將結果寫入 Amazon S3，以及釋出資源。此資源版本可確保您只需支付使用量的費用。

每個量子處理單元 (QPU) 的並行混合任務總數受到限制。今天，任何指定時間只能有一個混合任務在 QPU 上執行。佇列用於控制允許執行的混合任務數量，以免超過允許的限制。如果您的目標裝置是 QPU，您的混合任務會先進入所選 QPU *的任務佇列*。Amazon Braket 會啟動所需的混合任務執行個體，並在裝置上執行您的混合任務。在演算法期間，您的混合任務具有優先順序存取，這表示混合任務中的量子任務在裝置上排入佇列的其他 Braket 量子任務之前執行，前提是任務量子任務每隔幾分鐘提交一次至 QPU。一旦混合任務完成，就會釋出資源，這表示您只需支付使用量的費用。

**注意**  
裝置是區域性的，您的混合任務在 AWS 區域 與主要裝置相同的 中執行。

在模擬器和 QPU 目標案例中，您可以選擇定義自訂演算法指標，例如 Hamiltonian 的能量，作為演算法的一部分。這些指標會自動回報給 Amazon CloudWatch，並從那裡，在 Amazon Braket 主控台中以近乎即時的方式顯示。

**注意**  
如果您想要使用 GPU 型執行個體，請務必使用其中一個 GPU 型模擬器搭配 Braket 上的內嵌模擬器 （例如 `lightning.gpu`)。如果您選擇其中一個 CPU 型內嵌模擬器 （例如 `lightning.qubit`或 `braket:default-simulator`)，則不會使用 GPU，而且可能會產生不必要的成本。

# 混合任務的主要概念
<a name="braket-jobs-concepts"></a>

本節說明 Amazon Braket Python SDK 所提供`AwsQuantumJob.create`函數的主要概念，以及與容器檔案結構的映射。

除了構成完整演算法指令碼的檔案之外，您的混合任務還可以有額外的輸入和輸出。當您的混合任務開始時，AmazonRaket 會將作為混合任務建立一部分而提供的輸入複製到執行演算法指令碼的容器中。當混合任務完成時，演算法期間定義的所有輸出都會複製到指定的 Amazon S3 位置。

**注意**  
 *演算法指標*會即時回報，且不遵循此輸出程序。

Amazon Braket 也提供數個環境變數和協助程式函數，以簡化與容器輸入和輸出的互動。如需詳細資訊，請參閱 [Amazon Braket SDK 中的 braket.jobs 套件](https://amazon-braket-sdk-python.readthedocs.io/en/latest/_apidoc/braket.jobs.html)。 *Amazon Braket * 

**Topics**
+ [輸入](#braket-jobs-inputs)
+ [輸出](#braket-jobs-outputs)
+ [環境變數](#braket-jobs-environmental-variables)
+ [協助程式函數](#braket-jobs-helper-functions)

## 輸入
<a name="braket-jobs-inputs"></a>

 **輸入資料**：使用 `input_data`引數指定設定為字典的輸入資料檔案，即可將輸入資料提供給混合式演算法。使用者在 SDK 的 `AwsQuantumJob.create`函數中定義`input_data`引數。這會將輸入資料複製到環境變數 提供的位置的容器檔案系統`"AMZN_BRAKET_INPUT_DIR"`。如需如何在混合式演算法中使用輸入資料的幾個範例，請參閱 [Amazon Braket 混合式任務中的 QAOA，以及 Amazon Braket 混合式任務 Jupyter 筆記本中的 PennyLane](https://github.com/amazon-braket/amazon-braket-examples/blob/main/examples/hybrid_jobs/2_Using_PennyLane_with_Braket_Hybrid_Jobs/Using_PennyLane_with_Braket_Hybrid_Jobs.ipynb) 和 Quantum 機器學習。 [ Amazon Braket ](https://github.com/amazon-braket/amazon-braket-examples/blob/main/examples/hybrid_jobs/1_Quantum_machine_learning_in_Amazon_Braket_Hybrid_Jobs/Quantum_machine_learning_in_Amazon_Braket_Hybrid_Jobs.ipynb) 

**注意**  
當輸入資料很大 (>1GB) 時，提交混合任務之前會有很長的等待時間。這是因為本機輸入資料會先上傳至 S3 儲存貯體，然後將 S3 路徑新增至混合式任務請求，最後將混合式任務請求提交至 Braket 服務。

 **超參數**：如果您傳入 `hyperparameters`，它們可在環境變數 下使用`"AMZN_BRAKET_HP_FILE"`。

**注意**  
如需如何建立超參數和輸入資料，然後將此資訊傳遞至混合式任務指令碼的詳細資訊，請參閱[使用超參數](braket-jobs-hyperparameters.md)區段和此 github [頁面](https://github.com/amazon-braket/amazon-braket-examples/blob/main/examples/hybrid_jobs/1_Quantum_machine_learning_in_Amazon_Braket_Hybrid_Jobs/qcbm/qcbm.py)。

 **檢查點**：若要指定您想要在新混合任務中使用的`job-arn`檢查點，請使用 `copy_checkpoints_from_job`命令。此命令會透過檢查點資料複製到新混合任務`checkpoint_configs3Uri`的 ，使其可在任務執行`AMZN_BRAKET_CHECKPOINT_DIR`時環境變數指定的路徑中使用。預設值為 `None`，表示來自另一個混合任務的檢查點資料不會用於新的混合任務。

## 輸出
<a name="braket-jobs-outputs"></a>

 **Quantum 任務**：Quantum 任務結果存放在 S3 位置 `s3://amazon-braket-<region>-<accountID>/jobs/<job-name>/tasks`。

 **任務結果**：您的演算法指令碼儲存至環境變數所提供目錄的所有內容`"AMZN_BRAKET_JOB_RESULTS_DIR"`都會複製到 中指定的 S3 位置`output_data_config`。如果未指定值，則預設為 `s3://amazon-braket-<region>-<accountID>/jobs/<job-name>/<timestamp>/data`。我們提供 SDK 協助程式函數 ** `save_job_result` **，當您從演算法指令碼呼叫 時，您可以使用它以字典的形式方便地存放結果。

 **檢查點**：如果您想要使用檢查點，您可以將它們儲存在環境變數 提供的目錄中`"AMZN_BRAKET_CHECKPOINT_DIR"`。您也可以`save_job_checkpoint`改用 SDK 協助程式函數。

 **演算法指標**：您可以將演算法指標定義為演算法指令碼的一部分，該指令碼會在混合任務執行時即時傳送到 Amazon CloudWatch，並在 Amazon Braket 主控台中顯示。如需如何使用演算法指標的範例，請參閱[使用 Amazon Braket 混合任務來執行 QAOA 演算法](braket-jobs-run-qaoa-algorithm.md)。

如需儲存任務輸出的詳細資訊，請參閱混合任務文件中的[儲存結果](https://docs.aws.amazon.com/braket/latest/developerguide/braket-jobs-first.html#braket-jobs-save-results)。

## 環境變數
<a name="braket-jobs-environmental-variables"></a>

Amazon Braket 提供數個環境變數，以簡化與容器輸入和輸出的互動。以下程式碼列出 Braket 使用的環境變數。
+ `AMZN_BRAKET_INPUT_DIR` – 輸入資料目錄 opt/braket/input/data。
+ `AMZN_BRAKET_JOB_RESULTS_DIR` – 要寫入任務結果的輸出目錄 opt/braket/model。
+ `AMZN_BRAKET_JOB_NAME` – 任務的名稱。
+ `AMZN_BRAKET_CHECKPOINT_DIR` – 檢查點目錄。
+ `AMZN_BRAKET_HP_FILE` – 包含超參數的檔案。
+ `AMZN_BRAKET_DEVICE_ARN` – 裝置 ARN (AWS 資源名稱）。
+ `AMZN_BRAKET_OUT_S3_BUCKET` – 輸出 Amazon S3 儲存貯體，如`CreateJob`請求的 中所指定`OutputDataConfig`。
+ `AMZN_BRAKET_SCRIPT_ENTRY_POINT` – `CreateJob`請求的 中指定的進入點`ScriptModeConfig`。
+ `AMZN_BRAKET_SCRIPT_COMPRESSION_TYPE` – `CreateJob`請求的 中指定的壓縮類型`ScriptModeConfig`。
+ `AMZN_BRAKET_SCRIPT_S3_URI` – 使用者指令碼的 Amazon S3 位置，如`CreateJob`請求的 中所指定`ScriptModeConfig`。
+ `AMZN_BRAKET_TASK_RESULTS_S3_URI` – SDK 預設會存放任務量子任務結果的 Amazon S3 位置。
+ `AMZN_BRAKET_JOB_RESULTS_S3_PATH` – 存放任務結果的 Amazon S3 位置，如`CreateJob`請求的 中所指定`OutputDataConfig`。
+ `AMZN_BRAKET_JOB_TOKEN` – 對於任務容器中建立的量子任務，應該傳遞至 `CreateQuantumTask`的 `jobToken` 參數的字串。

## 協助程式函數
<a name="braket-jobs-helper-functions"></a>

Amazon Braket 提供多種協助程式函數，可簡化與容器輸入和輸出的互動。這些協助程式函數會從用來執行混合任務的演算法指令碼中呼叫。下列範例示範如何使用它們。

```
from braket.jobs import get_checkpoint_dir, get_hyperparameters, get_input_data_dir, get_job_device_arn, get_job_name, get_results_dir, save_job_result, save_job_checkpoint, load_job_checkpoint

get_checkpoint_dir() # Get the checkpoint directory
get_hyperparameters() # Get the hyperparameters as strings
get_input_data_dir() # Get the input data directory
get_job_device_arn() # Get the device specified by the hybrid job
get_job_name() # Get the name of the hybrid job.
get_results_dir() # Get the path to a results directory
save_job_result(result_data='data') # Save hybrid job results
save_job_checkpoint(checkpoint_data={'key': 'value'}) # Save a checkpoint
load_job_checkpoint() # Load a previously saved checkpoint
```

# 先決條件
<a name="braket-jobs-prerequisites"></a>

執行第一個混合任務之前，您必須確定您有足夠的許可以繼續此任務。若要判斷您擁有正確的許可，請從 Braket 主控台左側的選單中選取**許可**。**Amazon Braket 的許可管理**頁面可協助您驗證其中一個現有角色是否具有足以執行混合任務的許可，或引導您建立預設角色，以便在您尚未擁有此類角色時用來執行混合任務。

![\[Amazon Braket 服務的許可和設定頁面顯示服務連結角色，以及驗證混合任務執行角色現有角色的選項。\]](http://docs.aws.amazon.com/zh_tw/braket/latest/developerguide/images/braket-jobs-first-permissions.png)


若要驗證您的角色是否具有執行混合任務的足夠許可，請選取**驗證現有角色**按鈕。如果您這麼做，您會收到找到角色的訊息。若要查看角色的名稱及其角色 ARNs，請選取**顯示角色**按鈕。

![\[Amazon Braket 許可和設定畫面顯示找到的服務連結角色，以及具有足夠執行混合任務許可的現有角色。\]](http://docs.aws.amazon.com/zh_tw/braket/latest/developerguide/images/braket-jobs-first-permissions-verify-yes.png)


如果您沒有具有執行混合任務足夠許可的角色，您會收到一則訊息，指出找不到該角色。選取**建立預設角色**按鈕，以取得具有足夠許可的角色。

![\[Amazon Braket 許可和設定頁面顯示找到的服務連結角色，而找不到混合任務執行角色。\]](http://docs.aws.amazon.com/zh_tw/braket/latest/developerguide/images/braket-jobs-first-permissions-verify-no.png)


如果角色已成功建立，您會收到確認此訊息。

![\[Amazon Braket 許可和設定頁面顯示找到的服務連結角色，以及成功建立的混合任務執行角色。\]](http://docs.aws.amazon.com/zh_tw/braket/latest/developerguide/images/braket-jobs-first-permissions-verify-created.png)


如果您沒有進行此查詢的許可，則會拒絕您存取。在這種情況下，請聯絡您的內部 AWS 管理員。

![\[AccessDenied 錯誤訊息，指出使用者無權在AmazonBraketJobsExecutionRole具有明確拒絕的 上執行 iam：ListAttachedRolePolicies。\]](http://docs.aws.amazon.com/zh_tw/braket/latest/developerguide/images/braket-jobs-first-permissions-access-denied.png)


# 建立混合任務
<a name="braket-jobs-first"></a>

 本節說明如何使用 Python 指令碼建立混合任務。或者，若要從本機 Python 程式碼建立混合任務，例如您偏好的整合開發環境 (IDE) 或 Braket 筆記本，請參閱 [將本機程式碼執行為混合式任務](braket-hybrid-job-decorator.md)。

**Topics**
+ [建立並執行](#braket-jobs-first-create)
+ [監控您的結果](#braket-jobs-first-monitor-results)
+ [儲存結果](#braket-jobs-save-results)
+ [使用檢查點](#braket-jobs-checkpoints)
+ [將本機程式碼執行為混合式任務](braket-hybrid-job-decorator.md)
+ [搭配混合任務使用 API](braket-jobs-api.md)
+ [使用本機模式建立混合式任務並進行偵錯](braket-jobs-local-mode.md)

## 建立並執行
<a name="braket-jobs-first-create"></a>

一旦您有具有執行混合任務許可的角色，您就可以繼續進行。第一個 Braket 混合任務的關鍵部分是*演算法指令碼*。它定義了您想要執行的演算法，並包含屬於演算法一部分的傳統邏輯和量子任務。除了演算法指令碼之外，您還可以提供其他相依性檔案。演算法指令碼及其相依性稱為*來源模組*。*進入點*定義混合任務開始時，要在來源模組中執行的第一個檔案或函數。

![\[圖表顯示使用主控台或筆記本建立量子任務、在量子裝置上執行演算法指令碼，以及分析結果的工作流程。\]](http://docs.aws.amazon.com/zh_tw/braket/latest/developerguide/images/braket-jobs-first-workflow.jpg)


首先，請考慮以下演算法指令碼的基本範例，該指令碼會建立五個鐘狀態並列印對應的測量結果。

```
import os

from braket.aws import AwsDevice
from braket.circuits import Circuit


def start_here():

    print("Test job started!")

    # Use the device declared in the job script
    device = AwsDevice(os.environ["AMZN_BRAKET_DEVICE_ARN"])

    bell = Circuit().h(0).cnot(0, 1)
    for count in range(5):
        task = device.run(bell, shots=100)
        print(task.result().measurement_counts)

    print("Test job completed!")
```

在 Braket 筆記本或本機環境的目前工作目錄中，使用名稱 *algorithm\$1script.py* 儲存此檔案。algorithm\$1script.py 檔案具有 `start_here()`作為計劃的進入點。

接著，在與 algorithm\$1script.py 檔案相同的目錄中建立 Python 檔案或 Python 筆記本。此指令碼會啟動混合任務，並處理任何非同步處理，例如列印我們感興趣的狀態或關鍵結果。此指令碼至少需要指定混合任務指令碼和主要裝置。

**注意**  
如需如何在與筆記本相同的目錄中建立 Braket 筆記本或上傳檔案的詳細資訊，例如 *algorithm\$1script.py* 檔案，請參閱[使用 Amazon Braket Python SDK 執行您的第一個電路](braket-get-started-run-circuit.md) 

在這個基本的第一個案例中，您會以模擬器為目標。無論您以哪種類型的量子裝置、模擬器或實際量子處理單元 (QPU) 為目標，您在下列指令碼`device`中指定的裝置都會用來排程混合式任務，並可供演算法指令碼做為環境變數 使用`AMZN_BRAKET_DEVICE_ARN`。

**注意**  
您只能使用混合任務 AWS 區域 的 中可用的裝置。Amazon Braket SDK 會自動選取此選項 AWS 區域。例如，us-east-1 中的混合任務可以使用 IonQ、DM1、 SV1和 TN1 裝置，但不能使用 Rigetti 裝置。

如果您選擇量子電腦而非模擬器，則 Braket 會排程您的混合式任務，以執行其具有優先順序存取的所有量子任務。

```
from braket.aws import AwsQuantumJob
from braket.devices import Devices

job = AwsQuantumJob.create(
    Devices.Amazon.SV1,
    source_module="algorithm_script.py",
    entry_point="algorithm_script:start_here",
    wait_until_complete=True
)
```

參數會`wait_until_complete=True`設定詳細模式，讓您的任務在執行時列印來自實際任務的輸出。您應該會看到類似下列範例的輸出。

```
Initializing Braket Job: arn:aws:braket:us-west-2:111122223333:job/braket-job-default-123456789012
Job queue position: 1
Job queue position: 1
Job queue position: 1
..............
.
.
.
Beginning Setup
Checking for Additional Requirements
Additional Requirements Check Finished
Running Code As Process
Test job started!
Counter({'00': 58, '11': 42})
Counter({'00': 55, '11': 45})
Counter({'11': 51, '00': 49})
Counter({'00': 56, '11': 44})
Counter({'11': 56, '00': 44})
Test job completed!
Code Run Finished
2025-09-24 23:13:40,962 sagemaker-training-toolkit INFO     Reporting training SUCCESS
```

**注意**  
您也可以將自訂模組與 [AwsQuantumJob.create](https://amazon-braket-sdk-python.readthedocs.io/en/latest/_apidoc/braket.aws.aws_quantum_job.html#braket.aws.aws_quantum_job.AwsQuantumJob.create) 方法搭配使用，方法是傳遞其位置 （本機目錄或檔案的路徑，或 tar.gz 檔案的 S3 URI)。如需工作範例，請參閱 [Amazon Braket 範例 Github 儲存](https://github.com/amazon-braket/amazon-braket-examples/tree/main)庫中混合任務資料夾中的 [Parallelize\$1training\$1for\$1QML.ipynb](https://github.com/amazon-braket/amazon-braket-examples/blob/main/examples/hybrid_jobs/5_Parallelize_training_for_QML/Parallelize_training_for_QML.ipynb) 檔案。

## 監控您的結果
<a name="braket-jobs-first-monitor-results"></a>

或者，您可以從 Amazon CloudWatch 存取日誌輸出。若要這樣做，請前往任務詳細資訊頁面左側選單上的**日誌群組**索引標籤，選取日誌群組 `aws/braket/jobs`，然後選擇包含任務名稱的日誌串流。在上述範例中，即為 `braket-job-default-1631915042705/algo-1-1631915190`。

![\[CloudWatch 日誌群組顯示日誌事件的清單，其中包含 Amazon Braket SDK Python 測試的檔案路徑和時間戳記。\]](http://docs.aws.amazon.com/zh_tw/braket/latest/developerguide/images/braket-jobs-first-cw-log.png)


您也可以在主控台中選取混合任務頁面，然後選擇**設定**，以檢視**混合任務**的狀態。

![\[Amazon Braket 混合任務詳細資訊顯示摘要、事件時間、原始程式碼和執行個體組態，以及停止條件。\]](http://docs.aws.amazon.com/zh_tw/braket/latest/developerguide/images/braket-jobs-first-console-status.png)


您的混合任務在執行時會在 Amazon S3 中產生一些成品。預設 S3 儲存貯體名稱為 ，`amazon-braket-<region>-<accountid>`且內容位於 `jobs/<jobname>/<timestamp>`目錄中。您可以使用 Braket Python SDK 建立混合任務`code_location`時，指定不同的 ，以設定存放這些成品的 S3 位置。

**注意**  
此 S3 儲存貯體必須與 AWS 區域 任務指令碼位於相同的 中。

`jobs/<jobname>/<timestamp>` 目錄包含一個子資料夾，其中包含`model.tar.gz`檔案中進入點指令碼的輸出。還有一個名為 的目錄`script`，其中包含`source.tar.gz`檔案中的演算法指令碼成品。您實際量子任務的結果位於名為 的目錄中`jobs/<jobname>/tasks`。

## 儲存結果
<a name="braket-jobs-save-results"></a>

您可以儲存演算法指令碼產生的結果，以便從混合任務指令碼中的混合任務物件以及 Amazon S3 中的輸出資料夾 （在名為 model.tar.gz 的 tar 壓縮檔案中） 中使用這些結果。

輸出必須使用 JavaScript 物件標記法 (JSON) 格式儲存在檔案中。如果資料無法輕易序列化為文字，如同使用凹凸陣列的情況，您可以傳入 選項，以使用挑選的資料格式序列化。如需詳細資訊，請參閱 [braket.jobs.data\$1persistence 模組。](https://amazon-braket-sdk-python.readthedocs.io/en/latest/_apidoc/braket.jobs.data_persistence.html#braket.jobs.data_persistence.save_job_result)

若要儲存混合任務的結果，請將以下以 \$1ADD 註解的行新增至 algorithm\$1script.py 檔案。

```
import os

from braket.aws import AwsDevice
from braket.circuits import Circuit
from braket.jobs import save_job_result  # ADD


def start_here():

    print("Test job started!")

    device = AwsDevice(os.environ['AMZN_BRAKET_DEVICE_ARN'])

    results = []  # ADD

    bell = Circuit().h(0).cnot(0, 1)
    for count in range(5):
        task = device.run(bell, shots=100)
        print(task.result().measurement_counts)
        results.append(task.result().measurement_counts)  # ADD

        save_job_result({"measurement_counts": results})  # ADD

    print("Test job completed!")
```

然後，您可以透過附加加上 \$1ADD ** `print(job.result())` ** 註解的行來顯示任務指令碼中的任務結果。

```
import time
from braket.aws import AwsQuantumJob

job = AwsQuantumJob.create(
    source_module="algorithm_script.py",
    entry_point="algorithm_script:start_here",
    device="arn:aws:braket:::device/quantum-simulator/amazon/sv1",
)

print(job.arn)
while job.state() not in AwsQuantumJob.TERMINAL_STATES:
    print(job.state())
    time.sleep(10)

print(job.state())
print(job.result())   # ADD
```

在此範例中，我們移除 `wait_until_complete=True`來隱藏詳細輸出。您可以在 中新增它以進行偵錯。當您執行此混合任務時，它會輸出識別符 和 `job-arn`，然後每 10 秒輸出一次混合任務的狀態，直到混合任務為 為止`COMPLETED`，之後會顯示鐘形電路的結果。請參閱以下範例。

```
arn:aws:braket:us-west-2:111122223333:job/braket-job-default-123456789012
INITIALIZED
RUNNING
RUNNING
RUNNING
RUNNING
RUNNING
RUNNING
RUNNING
RUNNING
RUNNING
RUNNING
...
RUNNING
RUNNING
COMPLETED
{'measurement_counts': [{'11': 53, '00': 47},..., {'00': 51, '11': 49}]}
```

## 使用檢查點
<a name="braket-jobs-checkpoints"></a>

您可以使用檢查點儲存混合任務的中繼反覆運算。在上一節的演算法指令碼範例中，您可以新增以下以 \$1ADD 註解的行來建立檢查點檔案。

```
from braket.aws import AwsDevice
from braket.circuits import Circuit
from braket.jobs import save_job_checkpoint  # ADD
import os


def start_here():

    print("Test job starts!")

    device = AwsDevice(os.environ["AMZN_BRAKET_DEVICE_ARN"])

    # ADD the following code
    job_name = os.environ["AMZN_BRAKET_JOB_NAME"]
    save_job_checkpoint(checkpoint_data={"data": f"data for checkpoint from {job_name}"}, checkpoint_file_suffix="checkpoint-1")  # End of ADD

    bell = Circuit().h(0).cnot(0, 1)
    for count in range(5):
        task = device.run(bell, shots=100)
        print(task.result().measurement_counts)

    print("Test hybrid job completed!")
```

當您執行混合任務時，它會使用預設`/opt/jobs/checkpoints`路徑在檢查點目錄中的混合任務成品中建立檔案 *<jobname>-checkpoint-1.json。*除非您想要變更此預設路徑，否則混合任務指令碼保持不變。

如果您想要從先前混合任務產生的檢查點載入混合任務，演算法指令碼會使用 `from braket.jobs import load_job_checkpoint`。要載入演算法指令碼的邏輯如下。

```
from braket.jobs import load_job_checkpoint

checkpoint_1 = load_job_checkpoint(
    "previous_job_name",
    checkpoint_file_suffix="checkpoint-1",
)
```

載入此檢查點之後，您可以根據載入 的內容繼續邏輯`checkpoint-1`。

**注意**  
*checkpoint\$1file\$1suffix* 必須符合先前在建立檢查點時指定的尾碼。

您的協同運作指令碼需要指定先前混合工作`job-arn`中的 ，並使用 \$1ADD 加上註解的行。

```
from braket.aws import AwsQuantumJob

job = AwsQuantumJob.create(
    source_module="source_dir",
    entry_point="source_dir.algorithm_script:start_here",
    device="arn:aws:braket:::device/quantum-simulator/amazon/sv1",
    copy_checkpoints_from_job="<previous-job-ARN>", #ADD
    )
```

# 將本機程式碼執行為混合式任務
<a name="braket-hybrid-job-decorator"></a>

Amazon Braket Hybrid Jobs 提供混合量子傳統演算法的全受管協調，結合 Amazon EC2 運算資源與 Amazon Braket Quantum Processing Unit (QPU) 存取。在混合任務中建立的量子任務具有個別量子任務的優先順序佇列，因此您的演算法不會因量子任務佇列中的波動而中斷。每個 QPU 都會維護個別的混合式任務佇列，確保任何指定時間只能執行一個混合式任務。

**Topics**
+ [從本機 Python 程式碼建立混合任務](#create-hybrid-job-from-local-python-code)
+ [安裝其他 Python 套件和原始程式碼](#install-python-packages-and-code)
+ [將資料儲存並載入混合任務執行個體](#save-load-data-into-instance)
+ [混合式任務裝飾項目的最佳實務](#best-practices)

## 從本機 Python 程式碼建立混合任務
<a name="create-hybrid-job-from-local-python-code"></a>

您可以執行本機 Python 程式碼做為 Amazon Braket 混合任務。您可以透過使用`@hybrid_job`裝飾項目註釋程式碼來執行此操作，如下列程式碼範例所示。對於自訂環境，您可以選擇使用來自 Amazon Elastic Container Registry (ECR) [的自訂](braket-jobs-byoc.md)容器。

**注意**  
預設僅支援 Python 3.12。

 您可以使用`@hybrid_job`裝飾項目來註釋函數。Braket 會將裝飾項目內的程式碼轉換為 Braket 混合任務[演算法指令碼](braket-jobs-first.md)。然後，混合任務會在 Amazon EC2 執行個體的裝飾項目內叫用 函數。您可以使用 `job.state()`或 Braket 主控台來監控任務的進度。下列程式碼範例示範如何在 上執行五個狀態的序列State Vector Simulator (SV1) device。

```
from braket.aws import AwsDevice
from braket.circuits import Circuit, FreeParameter, Observable
from braket.devices import Devices
from braket.jobs.hybrid_job import hybrid_job
from braket.jobs.metrics import log_metric

device_arn = Devices.Amazon.SV1


@hybrid_job(device=device_arn)  # Choose priority device
def run_hybrid_job(num_tasks=1):
    device = AwsDevice(device_arn)  # Declare AwsDevice within the hybrid job

    # Create a parametric circuit
    circ = Circuit()
    circ.rx(0, FreeParameter("theta"))
    circ.cnot(0, 1)
    circ.expectation(observable=Observable.X(), target=0)

    theta = 0.0  # Initial parameter

    for i in range(num_tasks):
        task = device.run(circ, shots=100, inputs={"theta": theta})  # Input parameters
        exp_val = task.result().values[0]

        theta += exp_val  # Modify the parameter (possibly gradient descent)

        log_metric(metric_name="exp_val", value=exp_val, iteration_number=i)

    return {"final_theta": theta, "final_exp_val": exp_val}
```

您可以像一般 Python 函數一樣叫用 函數來建立混合任務。不過，裝飾項目函數會傳回混合式任務控點，而不是函數的結果。若要在結果完成後擷取結果，請使用 `job.result()`。

```
job = run_hybrid_job(num_tasks=1)
result = job.result()
```

`@hybrid_job` 裝飾項目中的裝置引數會指定混合任務可優先存取的裝置 - 在此情況下為SV1模擬器。若要取得 QPU 優先順序，您必須確保函數中使用的裝置 ARN 符合裝飾項目中指定的 ARN。為了方便起見，您可以使用 協助程式函數`get_job_device_arn()`來擷取 中宣告的裝置 ARN`@hybrid_job`。

**注意**  
每個混合任務至少都有一分鐘的啟動時間，因為它會在 Amazon EC2 上建立容器化環境。因此，對於非常短的工作負載，例如單一電路或一批電路，它可能就足以讓您使用量子任務。

**超參數** 

`run_hybrid_job()` 函數會採用 引數`num_tasks`來控制建立的量子任務數量。混合任務會自動將此擷取為[超參數](braket-jobs-hyperparameters.md)。

**注意**  
超參數會在 Braket 主控台中顯示為字串，限制為 2500 個字元。

**指標和記錄** 

在 `run_hybrid_job()`函數中，來自反覆運算演算法的指標會以 記錄`log_metrics`。指標會自動繪製在混合任務索引標籤下的 Braket 主控台頁面中。您可以使用 指標，在混合式任務執行期間，使用 [Braket 成本追蹤器近乎即時地追蹤量子任務成本](braket-pricing.md)。上述範例使用指標名稱「機率」，記錄[結果類型](braket-result-types.md)的第一個機率。

**擷取結果** 

混合任務完成後，您可以使用 `job.result()` 擷取混合任務結果。傳回陳述式中的任何物件都會由 Braket 自動擷取。請注意，函數傳回的物件必須是元組，且每個元素皆可序列化。例如，下列程式碼顯示運作中和失敗的範例。

```
import numpy as np


# Working example
@hybrid_job(device=Devices.Amazon.SV1)
def passing():
    np_array = np.random.rand(5)
    return np_array  # Serializable

# # Failing example
# @hybrid_job(device=Devices.Amazon.SV1)
# def failing():
#     return MyObject() # Not serializable
```

**任務名稱** 

根據預設，此混合任務的名稱會從函數名稱推斷。您也可以指定長度上限為 50 個字元的自訂名稱。例如，在下列程式碼中，任務名稱為 "my-job-name"。

```
@hybrid_job(device=Devices.Amazon.SV1, job_name="my-job-name")
def function():
    pass
```

**本機模式** 

[本機任務](braket-jobs-local-mode.md)是透過將 引數`local=True`新增至裝飾項目來建立。這會在本機運算環境的容器化環境中執行混合任務，例如您的筆記型電腦。本機任務**沒有**量子任務的優先順序佇列。對於多節點或 MPI 等進階案例，本機任務可以存取必要的 Braket 環境變數。下列程式碼會使用裝置做為 SV1 模擬器來建立本機混合任務。

```
@hybrid_job(device=Devices.Amazon.SV1, local=True)
def run_hybrid_job(num_tasks=1):
    return ...
```

支援所有其他混合任務選項。如需選項清單，請參閱 [braket.jobs.quantum\$1job\$1creation 模組。](https://amazon-braket-sdk-python.readthedocs.io/en/stable/_apidoc/braket.jobs.quantum_job_creation.html)

## 安裝其他 Python 套件和原始程式碼
<a name="install-python-packages-and-code"></a>

您可以自訂執行時間環境，以使用您偏好的 Python 套件。您可以使用`requirements.txt`檔案、套件名稱清單，或[自備容器 (BYOC)](braket-jobs-byoc.md)。例如， `requirements.txt` 檔案可能包含要安裝的其他套件。

```
qiskit 
pennylane >= 0.31
mitiq == 0.29
```

若要使用 `requirements.txt` 檔案自訂執行期環境，請參閱下列程式碼範例。

```
@hybrid_job(device=Devices.Amazon.SV1, dependencies="requirements.txt")
def run_hybrid_job(num_tasks=1):
    return ...
```

或者，您可以提供套件名稱做為 Python 清單，如下所示。

```
@hybrid_job(device=Devices.Amazon.SV1, dependencies=["qiskit", "pennylane>=0.31", "mitiq==0.29"])
def run_hybrid_job(num_tasks=1):
    return ...
```

其他來源碼可以指定為模組清單，也可以指定單一模組，如下列程式碼範例所示。

```
@hybrid_job(device=Devices.Amazon.SV1, include_modules=["my_module1", "my_module2"])
def run_hybrid_job(num_tasks=1):
    return ...
```

## 將資料儲存並載入混合任務執行個體
<a name="save-load-data-into-instance"></a>

**指定輸入訓練資料**

建立混合任務時，您可以透過指定 Amazon Simple Storage Service (Amazon S3) 儲存貯體來提供輸入訓練資料集。您也可以指定本機路徑，然後 Braket 會自動將資料上傳至`s3://<default_bucket_name>/jobs/<job_name>/<timestamp>/data/<channel_name>`位於 的 Amazon S3。如果您指定本機路徑，則頻道名稱預設為「輸入」。下列程式碼顯示來自本機路徑 的 numpy 檔案`data/file.npy`。

```
import numpy as np


@hybrid_job(device=Devices.Amazon.SV1, input_data="data/file.npy")
def run_hybrid_job(num_tasks=1):
    data = np.load("data/file.npy")
    return ...
```

對於 S3，您必須使用`get_input_data_dir()`協助程式 funciton。

```
import numpy as np
from braket.jobs import get_input_data_dir

s3_path = "s3://amazon-braket-us-east-1-123456789012/job-data/file.npy"


@hybrid_job(device=None, input_data=s3_path)
def job_s3_input():
    np.load(get_input_data_dir() + "/file.npy")


@hybrid_job(device=None, input_data={"channel": s3_path})
def job_s3_input_channel():
    np.load(get_input_data_dir("channel") + "/file.npy")
```

您可以透過提供頻道值和 S3 URIs或本機路徑的字典來指定多個輸入資料來源。

```
import numpy as np
from braket.jobs import get_input_data_dir

input_data = {
    "input": "data/file.npy",
    "input_2": "s3://amzn-s3-demo-bucket/data.json"
}


@hybrid_job(device=None, input_data=input_data)
def multiple_input_job():
    np.load(get_input_data_dir("input") + "/file.npy")
    np.load(get_input_data_dir("input_2") + "/data.json")
```

**注意**  
當輸入資料很大 (>1GB) 時，在建立任務之前會有很長的等待時間。這是因為本機輸入資料第一次上傳至 S3 儲存貯體時，S3 路徑會新增至任務請求。最後，任務請求會提交至 Braket 服務。

**將結果儲存至 S3**

若要儲存未包含在裝飾函數的傳回陳述式中的結果，您必須將正確的目錄附加至所有檔案寫入操作。下列範例顯示儲存 numpy 陣列和 matplotlib 圖。

```
import matplotlib.pyplot as plt
import numpy as np


@hybrid_job(device=Devices.Amazon.SV1)
def run_hybrid_job(num_tasks=1):
    result = np.random.rand(5)

    # Save a numpy array
    np.save("result.npy", result)

    # Save a matplotlib figure
    plt.plot(result)
    plt.savefig("fig.png")
    return ...
```

所有結果都會壓縮為名為 的檔案`model.tar.gz`。您可以使用 Python `job.result()` 函數 下載結果，或從 Braket 管理主控台的混合任務頁面導覽至結果資料夾。

**從檢查點儲存和繼續**

對於長時間執行的混合任務，建議定期儲存演算法的中繼狀態。您可以使用內建`save_job_checkpoint()`協助程式函數，或將檔案儲存至`AMZN_BRAKET_JOB_RESULTS_DIR`路徑。稍後的 可與 協助程式函數 搭配使用`get_job_results_dir()`。

以下是使用混合式任務裝飾工具儲存和載入檢查點的最低工作範例：

```
from braket.jobs import save_job_checkpoint, load_job_checkpoint, hybrid_job


@hybrid_job(device=None, wait_until_complete=True)
def function():
    save_job_checkpoint({"a": 1})


job = function()
job_name = job.name
job_arn = job.arn


@hybrid_job(device=None, wait_until_complete=True, copy_checkpoints_from_job=job_arn)
def continued_function():
    load_job_checkpoint(job_name)


continued_job = continued_function()
```

在第一個混合任務中， `save_job_checkpoint()` 會使用包含要儲存之資料的字典來呼叫 。根據預設，每個值都必須可序列化為文字。若要檢查點更複雜的 Python 物件，例如 numpy 陣列，您可以設定 `data_format = PersistedJobDataFormat.PICKLED_V4`。此程式碼會在稱為「檢查點」的子資料夾下，以混合任務成品`<jobname>.json`中的預設名稱建立和覆寫檢查點檔案。

若要建立新的混合任務以從檢查點繼續，我們需要傳遞 `copy_checkpoints_from_job=job_arn`，其中 `job_arn`是先前任務的混合任務 ARN。然後`load_job_checkpoint(job_name)`，我們使用 從檢查點載入 。

## 混合式任務裝飾項目的最佳實務
<a name="best-practices"></a>

**接受非同步性**

使用裝飾項目註釋建立的混合任務是非同步的 - 它們會在傳統和量子資源可用時執行。您可以使用 Braket Management Console或 Amazon CloudWatch 監控演算法的進度。當您提交演算法以執行時，Raket 會在可擴展的容器化環境中執行演算法，並在演算法完成時擷取結果。

**執行反覆變化演算法**

混合任務為您提供執行反覆式量子傳統演算法的工具。對於純量子問題，請使用[量子任務](braket-submit-tasks.md)或一[批量子任務](braket-batching-tasks.md)。對特定 QPUs優先順序存取，對於需要對 QPUs 進行多次反覆呼叫並對其進行傳統處理的長時間執行變化演算法最有利。

**使用本機模式進行偵錯**

在 QPU 上執行混合任務之前，建議您先在模擬器 SV1 上執行，以確認它如預期般執行。對於小規模測試，您可以使用本機模式執行 ，以進行快速反覆運算和偵錯。

**使用[自有容器 (BYOC)](braket-jobs-byoc.md) 改善重現性**

在容器化環境中封裝您的軟體及其相依性，以建立可重現的實驗。透過在容器中封裝所有程式碼、相依性和設定，您可以防止潛在的衝突和版本控制問題。

**多執行個體分散式模擬器**

若要執行大量電路，請考慮使用內建的 MPI 支援，在單一混合任務中的多個執行個體上執行本機模擬器。如需詳細資訊，請參閱[內嵌模擬器](pennylane-embedded-simulators.md)。

**使用參數電路**

您從混合任務提交的參數電路會在特定 QPUs 上使用[參數編譯自動編譯](braket-jobs-parametric-compilation.md)，以改善演算法的執行時間。

**定期檢查點 **

對於長時間執行的混合任務，建議定期儲存演算法的中繼狀態。

**如需進一步的範例、使用案例和最佳實務，請參閱 [Amazon Braket 範例 GitHub](https://github.com/amazon-braket/amazon-braket-examples)。**

# 搭配混合任務使用 API
<a name="braket-jobs-api"></a>

您可以使用 直接存取 Amazon Braket 混合任務並與之互動API。不過，API直接使用 時，無法使用預設值和便利方法。

**注意**  
我們強烈建議您使用 Amazon Braket [Python SDK 與 Amazon Braket ](https://github.com/aws/amazon-braket-sdk-python)混合任務互動。它提供方便的預設值和保護，協助您的混合式任務成功執行。

本主題涵蓋使用 的基本概念API。如果您選擇使用 API，請記住，此方法可能更為複雜，並準備好進行多次反覆運算，讓您的混合式任務得以執行。

若要使用 API，您的帳戶應該具有具有 `AmazonBraketFullAccess`受管政策的角色。

**注意**  
如需如何使用 `AmazonBraketFullAccess`受管政策取得角色的詳細資訊，請參閱[啟用 Amazon Braket ](braket-enable-overview.md) 頁面。

此外，您需要 **執行角色**。此角色將傳遞給 服務。您可以使用 **Amazon Braket 主控台**建立角色。使用**許可和設定**頁面上的**執行角色**索引標籤來建立混合任務的預設角色。

`CreateJob` API 需要您指定混合任務的所有必要參數。若要使用 Python，請將演算法指令碼檔案壓縮為 tar 套件，例如 input.tar.gz 檔案，然後執行下列指令碼。更新角括號 (`<>`) 中的程式碼部分，以符合您的帳戶資訊和指定混合任務啟動路徑、檔案和方法的進入點。

```
from braket.aws import AwsDevice, AwsSession
import boto3
from datetime import datetime

s3_client = boto3.client("s3")
client = boto3.client("braket")

project_name = "job-test"
job_name = project_name + "-" + datetime.strftime(datetime.now(), "%Y%m%d%H%M%S")
bucket = "amazon-braket-<your_bucket>"
s3_prefix = job_name

job_script = "input.tar.gz"
job_object = f"{s3_prefix}/script/{job_script}"
s3_client.upload_file(job_script, bucket, job_object)

input_data = "inputdata.csv"
input_object = f"{s3_prefix}/input/{input_data}"
s3_client.upload_file(input_data, bucket, input_object)

job = client.create_job(
    jobName=job_name,
    roleArn="arn:aws:iam::<your_account>:role/service-role/AmazonBraketJobsExecutionRole",  # https://docs.aws.amazon.com/braket/latest/developerguide/braket-manage-access.html#about-amazonbraketjobsexecution
    algorithmSpecification={
        "scriptModeConfig": {
            "entryPoint": "<your_execution_module>:<your_execution_method>",
            "containerImage": {"uri": "292282985366.dkr.ecr.us-west-1.amazonaws.com/amazon-braket-base-jobs:1.0-cpu-py37-ubuntu18.04"},   # Change to the specific region you are using
            "s3Uri": f"s3://{bucket}/{job_object}",
            "compressionType": "GZIP"
        }
    },
    inputDataConfig=[
        {
            "channelName": "hellothere",
            "compressionType": "NONE",
            "dataSource": {
                "s3DataSource": {
                    "s3Uri": f"s3://{bucket}/{s3_prefix}/input",
                    "s3DataType": "S3_PREFIX"
                }
            }
        }
    ],
    outputDataConfig={
        "s3Path": f"s3://{bucket}/{s3_prefix}/output"
    },
    instanceConfig={
        "instanceType": "ml.m5.large",
        "instanceCount": 1,
        "volumeSizeInGb": 1
    },
    checkpointConfig={
        "s3Uri":  f"s3://{bucket}/{s3_prefix}/checkpoints",
        "localPath": "/opt/omega/checkpoints"
    },
    deviceConfig={
        "priorityAccess": {
            "devices": [
                "arn:aws:braket:us-west-1::device/qpu/rigetti/Ankaa-3"
            ]
        }
    },
    hyperParameters={
        "hyperparameter key you wish to pass": "<hyperparameter value you wish to pass>",
    },
    stoppingCondition={
        "maxRuntimeInSeconds": 1200,
        "maximumTaskLimit": 10
    },
)
```

建立混合任務後，您可以透過 `GetJob`API或 主控台存取混合任務詳細資訊。若要從執行`createJob`程式碼的 Python 工作階段取得混合式任務詳細資訊，如先前範例所示，請使用下列 Python 命令。

```
getJob = client.get_job(jobArn=job["jobArn"])
```

若要取消混合任務，`CancelJob`API請使用任務Amazon Resource Name的 () 呼叫 'JobArn'。

```
cancelJob = client.cancel_job(jobArn=job["jobArn"])
```

您可以使用 `checkpointConfig` 參數`createJob`API將檢查點指定為 的一部分。

```
    checkpointConfig = {
        "localPath" : "/opt/omega/checkpoints",
        "s3Uri": f"s3://{bucket}/{s3_prefix}/checkpoints"
    },
```

**注意**  
localPath `checkpointConfig`不能以下列任一預留路徑開頭：`/opt/ml`、`/tmp`、 `/opt/braket`或 `/usr/local/nvidia`。

# 使用本機模式建立混合式任務並進行偵錯
<a name="braket-jobs-local-mode"></a>

當您建立新的混合演算法時，本機模式可協助您偵錯和測試演算法指令碼。本機模式是一項功能，可讓您執行計劃在 Amazon Braket 混合任務中使用的程式碼，但不需要 Braket 來管理執行混合任務的基礎設施。相反地，請在 Amazon Braket 筆記本執行個體或偏好的用戶端本機上執行混合式任務，例如筆記型電腦或桌上型電腦。

在本機模式中，您仍可將量子任務傳送至實際裝置，但在本機模式中針對實際的 Quantum 處理單元 (QPU) 執行 時，不會獲得效能優勢。

若要使用本機模式，請將 修改`AwsQuantumJob`為程式內發生`LocalQuantumJob`的任何位置。例如，若要從[建立您的第一個混合任務](braket-jobs-first.md)執行範例，請在程式碼中編輯混合任務指令碼，如下所示。

```
from braket.jobs.local import LocalQuantumJob

job = LocalQuantumJob.create(
    device="arn:aws:braket:::device/quantum-simulator/amazon/sv1",
    source_module="algorithm_script.py",
    entry_point="algorithm_script:start_here",
)
```

**注意**  
已在 Amazon Braket 筆記本中預先安裝的 Docker 需要安裝在您的本機環境中，才能使用此功能。您可以在 Get Docker 頁面上找到安裝 [Docker ](https://docs.docker.com/get-started/get-docker/)的說明。此外，本機模式中不支援所有參數。

# 取消混合任務
<a name="braket-jobs-cancel"></a>

您可能需要取消處於非終端狀態的混合式任務。這可以在 主控台或使用程式碼來完成。

若要在主控台中取消混合任務，請從**混合任務**頁面選取要取消的混合任務，然後從**動作**下拉式功能表中選取**取消混合任務**。

![\[具有 4 個任務的 Amazon Braket 混合任務表，顯示其名稱、狀態、裝置資訊和時間戳記。動作下拉式清單包含檢視新混合任務、取消或管理標籤的選項。\]](http://docs.aws.amazon.com/zh_tw/braket/latest/developerguide/images/braket-hybrid-cancel-job.png)


若要確認取消，請在出現提示時在輸入欄位中輸入*取消*，然後選取**確定**。

![\[用於取消特定任務的對話方塊，其中包含有關取消程序的警告，以及輸入「取消」進行確認的文字輸入欄位。\]](http://docs.aws.amazon.com/zh_tw/braket/latest/developerguide/images/braket-hybrid-cancel-job-confirm.png)


若要使用 Braket Python SDK 的程式碼取消混合任務，請使用 `job_arn` 來識別混合任務，然後呼叫其上的 `cancel`命令，如下列程式碼所示。

```
job = AwsQuantumJob(arn=job_arn)
job.cancel()
```

`cancel` 命令會立即終止傳統混合任務容器，並盡最大努力取消所有仍處於非終端狀態的相關量子任務。

# 自訂您的混合任務
<a name="braket-jobs-customize"></a>

Amazon Braket 提供多種方法來自訂混合任務的執行方式，讓您可以根據特定需求量身打造環境。本節探索自訂混合任務的選項，從定義演算法指令碼環境到自有容器。您將了解如何使用超參數最佳化工作流程、設定任務執行個體，以及利用參數編譯來改善效能。這些自訂技術可協助您在 Amazon Braket 上最大化混合量子運算的潛力。

**Topics**
+ [定義演算法指令碼的環境](braket-jobs-script-environment.md)
+ [使用超參數](braket-jobs-hyperparameters.md)
+ [設定您的混合任務執行個體](braket-jobs-configure-job-instance-for-script.md)
+ [使用參數編譯來加速混合式任務](braket-jobs-parametric-compilation.md)

# 定義演算法指令碼的環境
<a name="braket-jobs-script-environment"></a>

Amazon Braket 支援演算法指令碼容器定義的環境：
+ 基礎容器 （預設，如果未指定`image_uri`)
+ CUDA-Q 容器
+ 具有 Tensorflow 和 PennyLane 的容器
+ 具有 PyTorch、PennyLane 和 CUDA-Q 的容器

下表提供有關容器及其包含的程式庫的詳細資訊。


**Amazon Braket 容器**  

| Type | Base | CUDA-Q | TensorFlow | PyTorch | 
| --- | --- | --- | --- | --- | 
|   **映像 URI**   |  292282985366.dkr.ecr.us-west-2.amazonaws.com/amazon-braket-base-jobs:latest  |  292282985366.dkr.ecr.us-west-2.amazonaws.com/amazon-braket-cudaq-jobs:latest  |  292282985366.dkr.ecr.us-east-1.amazonaws.com/amazon-braket-tensorflow-jobs:latest  |  292282985366.dkr.ecr.us-west-2.amazonaws.com/amazon-braket-pytorch-jobs:latest  | 
|   **繼承的程式庫**   |  |  [\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/zh_tw/braket/latest/developerguide/braket-jobs-script-environment.html)  |  [\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/zh_tw/braket/latest/developerguide/braket-jobs-script-environment.html)  |  [\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/zh_tw/braket/latest/developerguide/braket-jobs-script-environment.html)  | 
|   **其他程式庫**   |  [\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/zh_tw/braket/latest/developerguide/braket-jobs-script-environment.html)  |  [\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/zh_tw/braket/latest/developerguide/braket-jobs-script-environment.html)  |  [\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/zh_tw/braket/latest/developerguide/braket-jobs-script-environment.html)  |  [\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/zh_tw/braket/latest/developerguide/braket-jobs-script-environment.html)  | 

您可以在 [aws/amazon-braket-containers](https://github.com/aws/amazon-braket-containers) 中檢視和存取開放原始碼容器定義。選擇最符合您使用案例的容器。您可以使用 Braket 中的任何可用 AWS 區域 (us-east-1、us-west-1、us-west-2、eu-north-1、eu-west-2)，但容器區域必須符合混合任務的區域。當您在混合任務指令碼中將下列三個引數之一新增至您的`create(…​)`呼叫，以指定容器映像。您可以將其他相依性安裝到您在執行時間選擇的容器 （啟動或執行時間的成本），因為 Amazon Braket 容器具有網際網路連線能力。下列範例適用於 us-west-2 區域。
+  **基礎映像：**image\$1uri="292282985366.dkr.ecr.us-west-2.amazonaws.com/amazon-braket-base-jobs:latest"
+  **CUDA-Q 映像：**image\$1uri="292282985366.dkr.ecr.us-west-2.amazonaws.com/amazon-braket-cudaq-jobs:latest"
+  **Tensorflow 影像：**image\$1uri="292282985366.dkr.ecr.us-west-2.amazonaws.com/amazon-braket-tensorflow-jobs:latest"
+  **PyTorch 影像：**image\$1uri="292282985366.dkr.ecr.us-west-2.amazonaws.com/amazon-braket-pytorch-jobs:latest"

`image-uris` 也可以使用 Amazon Braket SDK 中的 `retrieve_image()`函數來擷取 。下列範例示範如何從 us-west-2 擷取它們 AWS 區域。

```
from braket.jobs.image_uris import retrieve_image, Framework

image_uri_base = retrieve_image(Framework.BASE, "us-west-2")
image_uri_cudaq = retrieve_image(Framework.CUDAQ, "us-west-2")
image_uri_tf = retrieve_image(Framework.PL_TENSORFLOW, "us-west-2")
image_uri_pytorch = retrieve_image(Framework.PL_PYTORCH, "us-west-2")
```

# 使用自有容器 (BYOC)
<a name="braket-jobs-byoc"></a>

Amazon Braket Hybrid Jobs 提供三個預先建置的容器，用於在不同環境中執行程式碼。如果其中一個容器支援您的使用案例，您只需在建立混合任務時提供演算法指令碼。您可以從演算法指令碼或使用 從 `requirements.txt` 檔案新增次要缺少的相依性`pip`。

如果這些容器都不支援您的使用案例，或者如果您想要擴展這些容器，則 Braket Hybrid Jobs 支援使用您自己的自訂Docker容器映像執行混合任務，或自備容器 (BYOC)。請確定這是適合您使用案例的正確功能。

**Topics**
+ [何時將我自己的容器帶入正確的決策？](#bring-own-container-decision)
+ [自備容器的配方](bring-own-container-recipe.md)
+ [在您自己的容器中執行 Braket 混合任務](running-hybrid-jobs-in-own-container.md)

## 何時將我自己的容器帶入正確的決策？
<a name="bring-own-container-decision"></a>

將您自己的容器 (BYOC) 帶到 Braket Hybrid Jobs，可讓您在封裝環境中安裝自己的軟體，藉此靈活地使用自己的軟體。根據您的特定需求，可能有方法可以實現相同的彈性，而無需完成完整的BYOC Docker建置 - Amazon ECR 上傳 - 自訂映像 URI 週期。

**注意**  
如果您想要新增少量可公開取得的其他 Python 套件 （通常少於 10 個），BYOC 可能不是正確的選擇。例如，如果您使用的是 PyPi。

在這種情況下，您可以使用其中一個預先建置的 Braket 映像，然後在任務提交時將`requirements.txt`檔案包含在來源目錄中。檔案會自動讀取，並正常`pip`安裝具有指定版本的套件。如果您要安裝大量套件，任務的執行時間可能會大幅增加。檢查 Python，如果適用，檢查您要用來測試軟體是否可運作的預先建置容器 CUDA 版本。

當您想要為任務指令碼使用非 Python 語言 （例如 C\$1\$1 或 Rust)，或想要使用透過 Braket 預先建置容器無法使用的 Python 版本時，BYOC 是必要的。如果出現下列情況，這也是不錯的選擇：
+ 您正在搭配授權金鑰使用軟體，而且您需要針對授權伺服器驗證該金鑰，才能執行軟體。使用 BYOC，您可以在Docker映像中嵌入授權金鑰，並包含要驗證授權金鑰的程式碼。
+ 您使用的軟體無法公開取得。例如，軟體託管在您需要特定 SSH 金鑰才能存取的私有 GitLab 或 GitHub 儲存庫上。
+ 您需要安裝未封裝在 Braket 提供的容器中的大型軟體套件。由於軟體安裝，BYOC 可讓您消除混合任務容器的長啟動時間。

BYOC 也可讓您透過使用軟體建置Docker容器並提供給使用者，讓自訂 SDK 或演算法可供客戶使用。您可以在 Amazon ECR 中設定適當的許可來執行此操作。

**注意**  
您必須遵守所有適用的軟體授權。

# 自備容器的配方
<a name="bring-own-container-recipe"></a>

在本節中，我們提供step-by-step指南，說明您需要bring your own container (BYOC)執行的 Braket 混合任務：指令碼、檔案，以及結合這些指令碼、檔案和步驟，以啟動和執行您的自訂Docker映像。兩個常見案例的配方：

1. 在Docker映像中安裝其他軟體，並在任務中僅使用 Python 演算法指令碼。

1. 使用非 Python 語言撰寫的演算法指令碼搭配混合任務，或 x86 以外的 CPU 架構。

對於案例 2，定義*容器項目指令碼*更為複雜。

當 Braket 執行您的混合任務時，它會啟動請求的 Amazon EC2 執行個體數量和類型，然後執行Docker映像 URI 輸入指定的映像，以在其上建立任務。使用 BYOC 功能時，您可以指定私有 [Amazon ECR 儲存庫](https://docs.aws.amazon.com/AmazonECR/latest/userguide/Repositories.html)中託管的映像 URI，而此儲存庫具有讀取存取權。Braket Hybrid Jobs 使用該自訂映像來執行任務。

建置可與混合任務搭配使用之Docker映像所需的特定元件。如果您不熟悉撰寫和建置 `Dockerfiles`，請參閱 [Dockerfile 文件](https://docs.docker.com/reference/dockerfile/)和 [Amazon ECR CLI 文件](https://docs.aws.amazon.com/AmazonECR/latest/userguide/getting-started-cli.html)。

**Topics**
+ [Dockerfile 的基礎映像](#base-image-dockerfile)
+ [（選用） 修改過的容器進入點指令碼](#modified-container-entry-point)
+ [使用 安裝所需的軟體和容器指令碼 `Dockerfile`](#install-docketfile)

## Dockerfile 的基礎映像
<a name="base-image-dockerfile"></a>

如果您使用的是 Python，並且想要在 Braket 提供的容器中提供的軟體上安裝軟體，則基礎映像的選項是託管於 [GitHub 儲存庫](https://github.com/amazon-braket/amazon-braket-containers)和 Amazon ECR 上的其中一個 Braket 容器映像。您需要[向 Amazon ECR 進行身分驗證](https://docs.aws.amazon.com/AmazonECR/latest/userguide/getting-started-cli.html#cli-authenticate-registry)，才能提取映像並在其上建置。例如，BYOC Docker 檔案的第一行可以是： `FROM [IMAGE_URI_HERE]`

接著，填寫其餘的 Dockerfile來安裝和設定您要新增至容器的軟體。預先建置的 Braket 映像將已包含適當的容器進入點指令碼，因此您不需要擔心是否包含該指令碼。

如果您想要使用非 Python 語言，例如 C\$1\$1、Rust 或 Julia，或者想要為非 x86 CPU 架構建置映像，例如 ARM，您可能需要在裸機公有映像之上建置 。您可以在 [Amazon Elastic Container Registry Public Gallery](https://gallery.ecr.aws/) 找到許多這類影像。請務必選擇適用於 CPU 架構的 GPU，並視需要選擇您要使用的 GPU。

## （選用） 修改過的容器進入點指令碼
<a name="modified-container-entry-point"></a>

**注意**  
如果您只將其他軟體新增至預先建置的 Braket 映像，則可以略過本節。

若要在混合任務中執行非 Python 程式碼，請修改定義容器進入點的 Python 指令碼。例如，[`braket_container.py`Amazon Braket Github 上的 python 指令碼](https://github.com/amazon-braket/amazon-braket-containers/blob/main/src/braket_container.py)。這是 Braket 預先建置的映像用來啟動演算法指令碼並設定適當環境變數的指令碼。容器進入點指令碼本身**必須使用** Python，但可以啟動非 Python 指令碼。在預先建置的範例中，您可以看到 Python 演算法指令碼是以 [Python 子程序](https://github.com/amazon-braket/amazon-braket-containers/blob/main/src/braket_container.py#L274)或[全新的程序](https://github.com/amazon-braket/amazon-braket-containers/blob/main/src/braket_container.py#L257)啟動。透過修改此邏輯，您可以啟用進入點指令碼來啟動非 Python 演算法指令碼。例如，您可以修改 [https://github.com/amazon-braket/amazon-braket-containers/blob/main/src/braket_container.py#L139](https://github.com/amazon-braket/amazon-braket-containers/blob/main/src/braket_container.py#L139) 函數，根據副檔名結尾啟動 Rust 程序。

您也可以選擇撰寫全新的 `braket_container.py`。它應該將輸入資料、來源封存和其他必要的檔案從 Amazon S3 複製到容器中，並定義適當的環境變數。

## 使用 安裝所需的軟體和容器指令碼 `Dockerfile`
<a name="install-docketfile"></a>

**注意**  
如果您使用預先建置的 Braket 映像作為Docker基礎映像，則容器指令碼已存在。

如果您在上一個步驟中建立了修改過的容器指令碼，則需要將其複製到容器中，**並將**環境變數定義為 `SAGEMAKER_PROGRAM` `braket_container.py`，或您已命名為新容器進入點指令碼的內容。

以下是`Dockerfile`可讓您在 GPU 加速任務執行個體上使用 Julia 的 範例：

```
FROM nvidia/cuda:12.2.0-devel-ubuntu22.04

    
 ARG DEBIAN_FRONTEND=noninteractive
 ARG JULIA_RELEASE=1.8
 ARG JULIA_VERSION=1.8.3


 ARG PYTHON=python3.11 
 ARG PYTHON_PIP=python3-pip
 ARG PIP=pip


 ARG JULIA_URL = https://julialang-s3.julialang.org/bin/linux/x64/${JULIA_RELEASE}/
 ARG TAR_NAME = julia-${JULIA_VERSION}-linux-x86_64.tar.gz


 ARG PYTHON_PKGS = # list your Python packages and versions here


 RUN curl -s -L ${JULIA_URL}/${TAR_NAME} | tar -C /usr/local -x -z --strip-components=1 -f -


 RUN apt-get update \

    && apt-get install -y --no-install-recommends \

    build-essential \

    tzdata \

    openssh-client \

    openssh-server \

    ca-certificates \

    curl \

    git \

    libtemplate-perl \

    libssl1.1 \

    openssl \

    unzip \ 

    wget \

    zlib1g-dev \

    ${PYTHON_PIP} \

    ${PYTHON}-dev \




 RUN ${PIP} install --no-cache --upgrade ${PYTHON_PKGS}


 RUN ${PIP} install --no-cache --upgrade sagemaker-training==4.1.3


 # Add EFA and SMDDP to LD library path
 ENV LD_LIBRARY_PATH="/opt/conda/lib/python${PYTHON_SHORT_VERSION}/site-packages/smdistributed/dataparallel/lib:$LD_LIBRARY_PATH"
 ENV LD_LIBRARY_PATH=/opt/amazon/efa/lib/:$LD_LIBRARY_PATH


 # Julia specific installation instructions
 COPY Project.toml /usr/local/share/julia/environments/v${JULIA_RELEASE}/
 RUN JULIA_DEPOT_PATH=/usr/local/share/julia \

    julia -e 'using Pkg; Pkg.instantiate(); Pkg.API.precompile()'
 # generate the device runtime library for all known and supported devices
 RUN JULIA_DEPOT_PATH=/usr/local/share/julia \

    julia -e 'using CUDA; CUDA.precompile_runtime()'


 # Open source compliance scripts
 RUN HOME_DIR=/root \

 && curl -o ${HOME_DIR}/oss_compliance.zip https://aws-dlinfra-utilities.s3.amazonaws.com/oss_compliance.zip \

 && unzip ${HOME_DIR}/oss_compliance.zip -d ${HOME_DIR}/ \

 && cp ${HOME_DIR}/oss_compliance/test/testOSSCompliance /usr/local/bin/testOSSCompliance \

 && chmod +x /usr/local/bin/testOSSCompliance \

 && chmod +x ${HOME_DIR}/oss_compliance/generate_oss_compliance.sh \

 && ${HOME_DIR}/oss_compliance/generate_oss_compliance.sh ${HOME_DIR} ${PYTHON} \

 && rm -rf ${HOME_DIR}/oss_compliance*


 # Copying the container entry point script
 COPY braket_container.py /opt/ml/code/braket_container.py
 ENV SAGEMAKER_PROGRAM braket_container.py
```

此範例會下載並執行 提供的指令碼 AWS ，以確保符合所有相關開放原始碼授權。例如，透過正確歸因由 管理的任何已安裝程式碼MIT license。

如果您需要包含非公有程式碼，例如託管在私有 GitHub 或 GitLab 儲存庫中的程式碼，**請勿**在Docker映像中嵌入 SSH 金鑰來存取它。相反地，請在建置Docker Compose時使用 ，以允許 Docker 存取其建置所在的主機電腦上的 SSH。如需詳細資訊，請參閱 [Docker 中的安全使用 SSH 金鑰存取私有 Github 儲存庫](https://www.fastruby.io/blog/docker/docker-ssh-keys.html)指南。

**建置和上傳Docker映像**

使用正確定義的 `Dockerfile`，您現在可以依照步驟[建立私有 Amazon ECR 儲存庫](https://docs.aws.amazon.com/AmazonECR/latest/userguide/repository-create.html)，如果其中尚未存在的話。您也可以建置、標記容器映像並將其上傳至儲存庫。

您已準備好建置、標記和推送映像。如需 選項的完整說明`docker build`和一些範例，請參閱 [Docker 建置文件](https://docs.docker.com/reference/cli/docker/buildx/build/)。

對於上述定義的範例檔案，您可以執行：

```
aws ecr get-login-password --region ${your_region} | docker login --username AWS --password-stdin ${aws_account_id}.dkr.ecr.${your_region}.amazonaws.com
 docker build -t braket-julia .
 docker tag braket-julia:latest ${aws_account_id}.dkr.ecr.${your_region}.amazonaws.com/braket-julia:latest
 docker push ${aws_account_id}.dkr.ecr.${your_region}.amazonaws.com/braket-julia:latest
```

**指派適當的 Amazon ECR 許可**

Braket Hybrid Jobs Docker 映像必須託管在私有 Amazon ECR 儲存庫中。根據預設，私有 Amazon ECR 儲存庫**不會**提供對 Braket Hybrid Jobs IAM role或任何其他要使用您映像的使用者的讀取存取權，例如協作者或學生。您必須[設定儲存庫政策](https://docs.aws.amazon.com/AmazonECR/latest/userguide/set-repository-policy.html)來授予適當的許可。一般而言，只將許可授予您想要存取映像的特定使用者和IAM角色，而不是允許具有 的任何人image URI提取它們。

# 在您自己的容器中執行 Braket 混合任務
<a name="running-hybrid-jobs-in-own-container"></a>

若要使用您自己的容器建立混合任務，`AwsQuantumJob.create()`請使用`image_uri`指定的引數呼叫 。您可以使用 QPU、隨需模擬器，或在 Braket Hybrid Jobs 提供的傳統處理器上執行您的程式碼。我們建議您先在 SV1, DM1，然後再在真實的 QPU 上執行。 TN1 

若要在傳統處理器上執行程式碼，請更新 來指定`instanceCount`您使用的 `instanceType`和 `InstanceConfig`。請注意，如果您指定 `instance_count` > 1，則需要確保您的程式碼可以在多個主機上執行。您可以選擇的執行個體數量上限為 5。例如：

```
job = AwsQuantumJob.create(
    source_module="source_dir",
    entry_point="source_dir.algorithm_script:start_here",
    image_uri="111122223333.dkr.ecr.us-west-2.amazonaws.com/my-byoc-container:latest",
    instance_config=InstanceConfig(instanceType="ml.g4dn.xlarge", instanceCount=3),
    device="local:braket/braket.local.qubit",
    # ...)
```

**注意**  
使用裝置 ARN 來追蹤您用作混合任務中繼資料的模擬器。可接受的值必須遵循格式 `device = "local:<provider>/<simulator_name>"`。請記住， `<provider>`和 `<simulator_name>` 只能包含字母、數字、`_`、 `-`和 `.` 。字串限制為 256 個字元。  
如果您計劃使用 BYOC 且未使用 Braket 開發套件來建立量子任務，您應該將環境變數的值傳遞`AMZN_BRAKET_JOB_TOKEN`給`CreateQuantumTask`請求中的 `jobToken` 參數。如果沒有，則量子任務不會獲得優先順序，並以一般獨立量子任務計費。

# 使用超參數
<a name="braket-jobs-hyperparameters"></a>

您可以在建立混合任務時定義演算法所需的超參數，例如學習率或步進大小。超參數值通常用於控制演算法的各個層面，並且通常可以進行調校以最佳化演算法的效能。若要在 Braket 混合任務中使用超參數，您需要將其名稱和值明確指定為字典。指定在搜尋最佳值集時要測試的超參數值。使用超參數的第一步是將超參數設定為字典並將其定義為字典，如下列程式碼所示。

```
from braket.devices import Devices

device_arn = Devices.Amazon.SV1

hyperparameters = {"shots": 1_000}
```

然後傳遞上述程式碼片段中定義的超參數，以便在您選擇的演算法中使用。若要執行下列程式碼範例，請在與超參數檔案相同的路徑中建立名為「src」的目錄。在 "src" 目錄內，新增 [0\$1Getting\$1started\$1papermill.ipynb](https://github.com/amazon-braket/amazon-braket-examples/blob/main/examples/hybrid_jobs/7_Running_notebooks_as_hybrid_jobs/src/0_Getting_started_papermill.ipynb)、[bookbook\$1runner.py](https://github.com/amazon-braket/amazon-braket-examples/blob/main/examples/hybrid_jobs/7_Running_notebooks_as_hybrid_jobs/src/notebook_runner.py) 和 [requirements.txt ](https://github.com/amazon-braket/amazon-braket-examples/blob/main/examples/hybrid_jobs/7_Running_notebooks_as_hybrid_jobs/src/requirements.txt)程式碼檔案。

```
import time
from braket.aws import AwsQuantumJob

job = AwsQuantumJob.create(
    device=device_arn,
    source_module="src",
    entry_point="src.notebook_runner:run_notebook",
    input_data="src/0_Getting_started_papermill.ipynb",
    hyperparameters=hyperparameters,
    job_name=f"papermill-job-demo-{int(time.time())}",
)

# Print job to record the ARN
print(job)
```

若要從混合任務指令碼*中*存取超參數，請參閱 [notebook\$1runner.py](https://github.com/amazon-braket/amazon-braket-examples/blob/main/examples/hybrid_jobs/7_Running_notebooks_as_hybrid_jobs/src/notebook_runner.py) python 檔案中的 `load_jobs_hyperparams()`函數。若要在混合任務指令碼*之外*存取超參數，請執行下列程式碼。

```
from braket.aws import AwsQuantumJob

# Get the job using the ARN
job_arn = "arn:aws:braket:us-east-1:111122223333:job/5eabb790-d3ff-47cc-98ed-b4025e9e296f"  # Replace with your job ARN
job = AwsQuantumJob(arn=job_arn)

# Access the hyperparameters
job_metadata = job.metadata()
hyperparameters = job_metadata.get("hyperParameters", {})
print(hyperparameters)
```

如需了解如何使用超參數的詳細資訊，請參閱 [Amazon Braket 混合任務教學中的 QAOA 和 Amazon Braket 混合任務以及 PennyLane](https://github.com/amazon-braket/amazon-braket-examples/blob/main/examples/hybrid_jobs/2_Using_PennyLane_with_Braket_Hybrid_Jobs/Using_PennyLane_with_Braket_Hybrid_Jobs.ipynb) 和 Quantum 機器學習。 [ Amazon Braket ](https://github.com/amazon-braket/amazon-braket-examples/blob/main/examples/hybrid_jobs/1_Quantum_machine_learning_in_Amazon_Braket_Hybrid_Jobs/Quantum_machine_learning_in_Amazon_Braket_Hybrid_Jobs.ipynb) 

# 設定您的混合任務執行個體
<a name="braket-jobs-configure-job-instance-for-script"></a>

根據您的演算法，您可能有不同的需求。根據預設，Amazon Braket 會在`ml.m5.large`執行個體上執行您的演算法指令碼。不過，您可以在使用下列匯入和組態引數建立混合任務時自訂此執行個體類型。

```
from braket.jobs.config import InstanceConfig

job = AwsQuantumJob.create(
    ...
    instance_config=InstanceConfig(instanceType="ml.g4dn.xlarge"), # Use NVIDIA T4 instance with 4 GPUs.
    ...
    ),
```

如果您正在執行內嵌模擬，並在裝置組態中指定了本機裝置，您可以另外在 中指定 `instanceCount`並將它設定為大於一個`InstanceConfig`，以請求多個執行個體。上限為 5。例如，您可以選擇 3 個執行個體，如下所示。

```
from braket.jobs.config import InstanceConfig
job = AwsQuantumJob.create(
    ...
    instance_config=InstanceConfig(instanceType="ml.g4dn.xlarge", instanceCount=3), # Use 3 NVIDIA T4 instances
    ...
    ),
```

當您使用多個執行個體時，請考慮使用資料平行功能分發混合任務。如需如何查看此 [QML 範例平行化訓練](https://github.com/amazon-braket/amazon-braket-examples/blob/main/examples/hybrid_jobs/5_Parallelize_training_for_QML/Parallelize_training_for_QML.ipynb)的詳細資訊，請參閱下列範例筆記本。

下列三個資料表列出標準、高效能和 GPU 加速執行個體的可用執行個體類型和規格。

**注意**  
若要檢視混合任務的預設傳統運算執行個體配額，請參閱 [Amazon Braket Quotas](braket-quotas.md) 頁面。


| 標準執行個體 | vCPU | 記憶體 (GiB) | 
| --- | --- | --- | 
|  ml.m5.large （預設）  |  4  |  16  | 
|  ml.m5.xlarge  |  4  |  16  | 
|  ml.m5.2xlarge  |  8  |  32  | 
|  ml.m5.4xlarge  |  16  |  64  | 
|  ml.m5.12xlarge  |  48  |  192  | 
|  ml.m5.24xlarge  |  96  |  384  | 


| 高效能執行個體 | vCPU | 記憶體 (GiB) | 
| --- | --- | --- | 
|  ml.c5.xlarge  |  4  |  8  | 
|  ml.c5.2xlarge  |  8  |  16  | 
|  ml.c5.4xlarge  |  16  |  32  | 
|  ml.c5.9xlarge  |  36  |  72  | 
|  ml.c5.18xlarge  |  72  |  144  | 
|  ml.c5n.xlarge  |  4  |  10.5  | 
|  ml.c5n.2xlarge  |  8  |  21  | 
|  ml.c5n.4xlarge  |  16  |  32  | 
|  ml.c5n.9xlarge  |  36  |  72  | 
|  ml.c5n.18xlarge  |  72  |  192  | 


| GPU 加速執行個體 | GPU | vCPU | 記憶體 (GiB) | GPU 記憶體 (GiB) | 
| --- | --- | --- | --- | --- | 
|  ml.p4d.24xlarge  |  8  |  96  |  1152  |  320  | 
|  ml.g4dn.xlarge  |  1  |  4  |  16  |  16  | 
|  ml.g4dn.2xlarge  |  1  |  8  |  32  |  16  | 
|  ml.g4dn.4xlarge  |  1  |  16  |  64  |  16  | 
|  ml.g4dn.8xlarge  |  1  |  32  |  128  |  16  | 
|  ml.g4dn.12xlarge  |  4  |  48  |  192  |  64  | 
|  ml.g4dn.16xlarge  |  1  |  64  |  256  |  16  | 

每個執行個體使用 30 GB 的資料儲存 (SSD) 預設組態。但是，您可以使用與設定 相同的方式來調整儲存體`instanceType`。下列範例示範如何將總儲存體增加到 50 GB。

```
from braket.jobs.config import InstanceConfig

job = AwsQuantumJob.create(
    ...
    instance_config=InstanceConfig(
        instanceType="ml.g4dn.xlarge",
        volumeSizeInGb=50,
    ),
    ...
    ),
```

## 在 中設定預設儲存貯體 `AwsSession`
<a name="braket-jobs-configure-default-bucket"></a>

利用您自己的`AwsSession`執行個體可為您提供增強的彈性，例如能夠為您的預設 Amazon S3 儲存貯體指定自訂位置。根據預設， `AwsSession`具有預先設定的 Amazon S3 儲存貯體位置`"amazon-braket-{id}-{region}"`。不過，您可以選擇在建立 時覆寫預設的 Amazon S3 儲存貯體位置`AwsSession`。使用者可以選擇性地將`AwsSession`物件傳入 `AwsQuantumJob.create()`方法，方法是提供 `aws_session` 參數，如下列程式碼範例所示。

```
aws_session = AwsSession(default_bucket="amazon-braket-s3-demo-bucket")

# Then you can use that AwsSession when creating a hybrid job
job = AwsQuantumJob.create(
    ...
    aws_session=aws_session
)
```

# 使用參數編譯來加速混合式任務
<a name="braket-jobs-parametric-compilation"></a>

 Amazon Braket 支援特定 QPUs上的參數編譯。這可讓您只編譯電路一次，而不是混合演算法中的每次反覆運算，以減少與運算昂貴編譯步驟相關的額外負荷。這可以大幅改善混合任務的執行時間，因為您不必在每個步驟重新編譯電路。只需將參數化電路提交到我們支援的其中一個 QPUs 做為 Braket 混合任務。對於長時間執行的混合任務，Raket 會在編譯電路時自動使用硬體提供者的更新校正資料，以確保最高品質的結果。

若要建立參數電路，您必須先在演算法指令碼中提供參數做為輸入。在此範例中，我們使用小型參數電路，並忽略每次反覆運算之間的任何傳統處理。對於典型工作負載，您可以批次提交許多電路，並執行傳統處理，例如更新每個反覆運算中的參數。

```
import os

from braket.aws import AwsDevice
from braket.circuits import Circuit, FreeParameter

def start_here():

    print("Test job started.")

    # Use the device declared in the job script
    device = AwsDevice(os.environ["AMZN_BRAKET_DEVICE_ARN"])

    circuit = Circuit().rx(0, FreeParameter("theta"))
    parameter_list = [0.1, 0.2, 0.3]
    
    for parameter in parameter_list:
        result = device.run(circuit, shots=1000, inputs={"theta": parameter})

    print("Test job completed.")
```

您可以使用下列任務指令碼，提交演算法指令碼以混合任務的形式執行。在支援參數編譯的 QPU 上執行混合任務時，只會在第一次執行時編譯電路。在下列執行中，會重複使用編譯的電路，增加混合任務的執行時間效能，而不需要任何額外的程式碼行。

```
from braket.aws import AwsQuantumJob

job = AwsQuantumJob.create(
    device=device_arn,
    source_module="algorithm_script.py",
)
```

**注意**  
除了脈衝層級程式Rigetti Computing之外， 的所有超執行、以閘道為基礎的 QPUs都支援參數編譯。

# 搭配 Amazon Braket 使用 PennyLane
<a name="hybrid"></a>

混合演算法是同時包含傳統和量子指示的演算法。傳統說明是在傳統硬體 (EC2 執行個體或筆記型電腦） 上執行，而量子說明是在模擬器或量子電腦上執行。我們建議您使用混合任務功能執行混合演算法。如需詳細資訊，請參閱[何時使用 Amazon Braket 任務](braket-jobs.md#braket-jobs-use)。

Amazon Braket 可讓您在 ** Amazon Braket PennyLane 外掛程式**或 ** Amazon Braket Python SDK** 和範例筆記本儲存庫的協助下，設定和執行混合式量子演算法。Amazon Braket 範例筆記本以 SDK 為基礎，可讓您在沒有 PennyLane 外掛程式的情況下設定和執行特定混合式演算法。不過，我們建議使用 PennyLane，因為它可提供更豐富的體驗。

 **關於混合量子演算法** 

混合量子演算法對現今的產業來說很重要，因為現代量子運算裝置通常會產生雜訊，因此會產生錯誤。每個新增至運算的量子閘道都會提高增加雜訊的機會；因此，長時間執行的演算法可能會因為雜訊而不堪重負，從而導致運算錯誤。

純量子演算法，例如 Shor 的 [（量子階段估算範例）](https://github.com/amazon-braket/amazon-braket-examples/tree/main/examples/advanced_circuits_algorithms/Quantum_Phase_Estimation) 或 Grover 的 [(Grover 範例）](https://github.com/aws/amazon-braket-examples/tree/main/examples/advanced_circuits_algorithms/Grover)，需要數千或數百萬個操作。因此，它們對於現有的量子裝置可能不切實際，通常稱為*雜訊中階量子 *(NISQ) 裝置。

在混合量子演算法中，量子處理單元 (QPUs) 可做為傳統 CPUs 的共同處理器，特別是在傳統演算法中加速特定計算。在現今裝置的功能範圍內，電路執行會縮短許多。

**Topics**
+ [Amazon Braket 搭配 PennyLane](#pennylane-option)
+ [Amazon Braket 範例筆記本中的混合演算法](#braket-hybrid-workflow)
+ [具有內嵌 PennyLane 模擬器的混合演算法](#hybrid-alorithms-pennylane)
+ [PennyLane 上的聯結漸層搭配 Amazon Braket 模擬器](#adjoint-gradient-pennylane)
+ [使用混合任務和 PennyLane 執行 QAOA 演算法](braket-jobs-run-qaoa-algorithm.md)
+ [使用 PennyLane 內嵌模擬器執行混合工作負載](pennylane-embedded-simulators.md)

## Amazon Braket 搭配 PennyLane
<a name="pennylane-option"></a>

Amazon Braket 支援 [PennyLane](https://pennylane.ai)，這是一種以*量子可區分程式設計*概念為基礎的開放原始碼軟體架構。您可以使用此架構，以訓練神經網路的方式訓練量子電路，以尋找量子化學、量子機器學習和最佳化中運算問題的解決方案。

PennyLane 程式庫提供熟悉的機器學習工具介面，包括 PyTorch 和 TensorFlow，讓訓練量子電路快速且直覺。
+  **PennyLane 程式庫** – PennyLane 已預先安裝在 Amazon Braket 筆記本中。若要從 PennyLane 存取 Amazon Braket 裝置，請開啟筆記本並使用下列命令匯入 PennyLane 程式庫。

```
import pennylane as qml
```

教學筆記本可協助您快速入門。或者，您可以從您選擇的 IDE 在 Amazon Braket 上使用 PennyLane。
+  **Amazon Braket PennyLane 外掛程式** — 若要使用您自己的 IDE，您可以手動安裝 Amazon Braket PennyLane 外掛程式。外掛程式會將 PennyLane 與 [Amazon Braket Python SDK](https://github.com/aws/amazon-braket-sdk-python) 連接，因此您可以在 Amazon Braket 裝置上在 PennyLane 中執行電路。若要安裝 PennyLane 外掛程式，請使用下列命令。

```
pip install amazon-braket-pennylane-plugin
```

下列範例示範如何在 PennyLane 中設定對 Amazon Braket 裝置的存取權：

```
# to use SV1
import pennylane as qml
sv1 = qml.device("braket.aws.qubit", device_arn="arn:aws:braket:::device/quantum-simulator/amazon/sv1", wires=2)

# to run a circuit:
@qml.qnode(sv1)
def circuit(x):
    qml.RZ(x, wires=0)
    qml.CNOT(wires=[0,1])
    qml.RY(x, wires=1)
    return qml.expval(qml.PauliZ(1))

result = circuit(0.543)


#To use the local sim:
local = qml.device("braket.local.qubit", wires=2)
```

如需教學課程範例和 PennyLane 的詳細資訊，請參閱 [Amazon Braket 範例儲存庫](https://github.com/aws/amazon-braket-examples/tree/main/examples/pennylane)。

Amazon Braket PennyLane 外掛程式可讓您使用單行程式碼在 PennyLane 中的 Amazon Braket QPU 和內嵌模擬器裝置之間切換。它提供兩個用於 PennyLane 的 Amazon Braket 量子裝置：
+  `braket.aws.qubit` 使用 Amazon Braket 服務的量子裝置執行，包括 QPUs 和模擬器
+  `braket.local.qubit` 使用 Amazon Braket SDK 的本機模擬器執行

Amazon Braket PennyLane 外掛程式是開放原始碼。您可以從 [PennyLane 外掛程式 GitHub 儲存庫](https://github.com/aws/amazon-braket-pennylane-plugin-python)安裝它。

如需 PennyLane 的詳細資訊，請參閱 [PennyLane 網站上的](https://pennylane.ai)文件。

## Amazon Braket 範例筆記本中的混合演算法
<a name="braket-hybrid-workflow"></a>

Amazon Braket 確實提供各種範例筆記本，這些筆記本不依賴 PennyLane 外掛程式來執行混合式演算法。您可以開始使用任何說明*變化方法*[的 Amazon Braket 混合式範例筆記本](https://github.com/aws/amazon-braket-examples/tree/main/examples/hybrid_quantum_algorithms)，例如 Quantum 近似最佳化演算法 (QAOA) 或變化量 Eigensolver (VQE)。

Amazon Braket 範例筆記本依賴 [Amazon Braket Python SDK](https://github.com/aws/amazon-braket-sdk-python)。SDK 提供框架，可透過 Amazon Braket 與量子運算硬體裝置互動。這是一個開放原始碼程式庫，旨在協助您處理混合工作流程的量子部分。

您可以使用我們的[範例筆記本](https://github.com/aws/amazon-braket-examples)進一步探索 Amazon Braket。

## 具有內嵌 PennyLane 模擬器的混合演算法
<a name="hybrid-alorithms-pennylane"></a>

Amazon Braket 混合任務現在隨附 [PennyLane](https://github.com/PennyLaneAI/pennylane-lightning) 的高效能 CPU 型和 GPU 型內嵌模擬器。此系列的內嵌模擬器可以直接嵌入混合任務容器中，並包含快速狀態向量`lightning.qubit`模擬器、使用 NVIDIA 的 [cuQuantum 程式庫](https://developer.nvidia.com/cuquantum-sdk)加速的`lightning.gpu`模擬器等。這些內嵌模擬器非常適合各種演算法，例如量子機器學習，這些演算法可以從[輔助差異化方法](https://docs.pennylane.ai/en/stable/introduction/interfaces.html#simulation-based-differentiation)等進階方法中受益。您可以在一或多個 CPU 或 GPU 執行個體上執行這些內嵌模擬器。

使用混合任務，您現在可以使用傳統協同處理器和 QPU 的組合、例如 的 Amazon Braket 隨需模擬器SV1，或直接從 PennyLane 使用內嵌模擬器來執行變化演算法程式碼。

內嵌模擬器已與混合任務容器搭配使用，您需要使用`@hybrid_job`裝飾器裝飾您的主要 Python 函數。若要使用 PennyLane `lightning.gpu` 模擬器，您也需要在 中指定 GPU 執行個體`InstanceConfig`，如下列程式碼片段所示：

```
import pennylane as qml
from braket.jobs import hybrid_job
from braket.jobs.config import InstanceConfig


@hybrid_job(device="local:pennylane/lightning.gpu", instance_config=InstanceConfig(instanceType="ml.g4dn.xlarge"))
def function(wires):
    dev = qml.device("lightning.gpu", wires=wires)
    ...
```

請參閱[範例筆記本](https://github.com/aws/amazon-braket-examples/blob/main/examples/hybrid_jobs/4_Embedded_simulators_in_Braket_Hybrid_Jobs/Embedded_simulators_in_Braket_Hybrid_Jobs.ipynb)，以開始使用 PennyLane 內嵌模擬器搭配混合任務。

## PennyLane 上的聯結漸層搭配 Amazon Braket 模擬器
<a name="adjoint-gradient-pennylane"></a>

使用 Amazon Braket 的PennyLane外掛程式，您可以在本機狀態向量模擬器或 SV1 上執行時，使用並行差異化方法來計算漸層。

 **注意：**若要使用聯結差異化方法，您必須在 `diff_method='device'`中指定 `qnode`，**而不是** `diff_method='adjoint'`。請參閱以下範例。

```
device_arn = "arn:aws:braket:::device/quantum-simulator/amazon/sv1"
dev = qml.device("braket.aws.qubit", wires=wires, shots=0, device_arn=device_arn)
                
@qml.qnode(dev, diff_method="device")
def cost_function(params):
    circuit(params)
    return qml.expval(cost_h)

gradient = qml.grad(circuit)
initial_gradient = gradient(params0)
```

**注意**  
目前， PennyLane會運算 QAOA Hamiltonians 的分組索引，並使用它們將 Hamiltonian 分割為多個預期值。如果您想要在從 執行 QAOA 時使用 SV1 的聯結差異化功能PennyLane，則需要移除分組索引來重建 Hamiltonian 的成本，如下所示： `cost_h, mixer_h = qml.qaoa.max_clique(g, constrained=False) cost_h = qml.Hamiltonian(cost_h.coeffs, cost_h.ops)`

# 使用混合任務和 PennyLane 執行 QAOA 演算法
<a name="braket-jobs-run-qaoa-algorithm"></a>

在本節中，您將使用學到的知識，使用 PennyLane 搭配參數編譯來撰寫實際的混合式程式。您可以使用演算法指令碼來解決 Quantum 近似最佳化演算法 (QAOA) 問題。程式會建立與傳統 Max Cut 最佳化問題對應的成本函數，指定參數化量子電路，並使用梯度下降方法來最佳化參數，以將成本函數降至最低。在此範例中，為了簡單起見，我們在演算法指令碼中產生問題圖表，但對於更典型的使用案例，最佳實務是透過輸入資料組態中的專用管道提供問題規格。旗標`parametrize_differentiable`預設為 ，`True`因此您可以從支援的 QPUs 上的參數編譯中自動獲得改善執行時間效能的優勢。

```
import os
import json
import time

from braket.jobs import save_job_result
from braket.jobs.metrics import log_metric

import networkx as nx
import pennylane as qml
from pennylane import numpy as np
from matplotlib import pyplot as plt

def init_pl_device(device_arn, num_nodes, shots, max_parallel):
    return qml.device(
        "braket.aws.qubit",
        device_arn=device_arn,
        wires=num_nodes,
        shots=shots,
        # Set s3_destination_folder=None to output task results to a default folder
        s3_destination_folder=None,
        parallel=True,
        max_parallel=max_parallel,
        parametrize_differentiable=True, # This flag is True by default.
    )

def start_here():
    input_dir = os.environ["AMZN_BRAKET_INPUT_DIR"]
    output_dir = os.environ["AMZN_BRAKET_JOB_RESULTS_DIR"]
    job_name = os.environ["AMZN_BRAKET_JOB_NAME"]
    checkpoint_dir = os.environ["AMZN_BRAKET_CHECKPOINT_DIR"]
    hp_file = os.environ["AMZN_BRAKET_HP_FILE"]
    device_arn = os.environ["AMZN_BRAKET_DEVICE_ARN"]

    # Read the hyperparameters
    with open(hp_file, "r") as f:
        hyperparams = json.load(f)

    p = int(hyperparams["p"])
    seed = int(hyperparams["seed"])
    max_parallel = int(hyperparams["max_parallel"])
    num_iterations = int(hyperparams["num_iterations"])
    stepsize = float(hyperparams["stepsize"])
    shots = int(hyperparams["shots"])

    # Generate random graph
    num_nodes = 6
    num_edges = 8
    graph_seed = 1967
    g = nx.gnm_random_graph(num_nodes, num_edges, seed=graph_seed)

    # Output figure to file
    positions = nx.spring_layout(g, seed=seed)
    nx.draw(g, with_labels=True, pos=positions, node_size=600)
    plt.savefig(f"{output_dir}/graph.png")

    # Set up the QAOA problem
    cost_h, mixer_h = qml.qaoa.maxcut(g)

    def qaoa_layer(gamma, alpha):
        qml.qaoa.cost_layer(gamma, cost_h)
        qml.qaoa.mixer_layer(alpha, mixer_h)

    def circuit(params, **kwargs):
        for i in range(num_nodes):
            qml.Hadamard(wires=i)
        qml.layer(qaoa_layer, p, params[0], params[1])

    dev = init_pl_device(device_arn, num_nodes, shots, max_parallel)

    np.random.seed(seed)
    cost_function = qml.ExpvalCost(circuit, cost_h, dev, optimize=True)
    params = 0.01 * np.random.uniform(size=[2, p])

    optimizer = qml.GradientDescentOptimizer(stepsize=stepsize)
    print("Optimization start")

    for iteration in range(num_iterations):
        t0 = time.time()

        # Evaluates the cost, then does a gradient step to new params
        params, cost_before = optimizer.step_and_cost(cost_function, params)
        # Convert cost_before to a float so it's easier to handle
        cost_before = float(cost_before)

        t1 = time.time()

        if iteration == 0:
            print("Initial cost:", cost_before)
        else:
            print(f"Cost at step {iteration}:", cost_before)

        # Log the current loss as a metric
        log_metric(
            metric_name="Cost",
            value=cost_before,
            iteration_number=iteration,
        )

        print(f"Completed iteration {iteration + 1}")
        print(f"Time to complete iteration: {t1 - t0} seconds")

    final_cost = float(cost_function(params))
    log_metric(
        metric_name="Cost",
        value=final_cost,
        iteration_number=num_iterations,
    )

    # We're done with the hybrid job, so save the result.
    # This will be returned in job.result()
    save_job_result({"params": params.numpy().tolist(), "cost": final_cost})
```

**注意**  
除了脈衝層級程式Rigetti Computing之外， 的所有超執行、以閘道為基礎的 QPUs都支援參數編譯。

# 使用 PennyLane 內嵌模擬器執行混合工作負載
<a name="pennylane-embedded-simulators"></a>

讓我們來看看如何在 Amazon Braket 混合任務上使用來自 PennyLane 的內嵌模擬器來執行混合工作負載。Pennylane 的 GPU 型內嵌模擬器 `lightning.gpu`使用 [Nvidia cuQuantum 程式庫](https://developer.nvidia.com/cuquantum-sdk)來加速電路模擬。嵌入式 GPU 模擬器已預先在所有 Braket [任務容器中](https://github.com/amazon-braket/amazon-braket-containers)設定，使用者可以立即使用。在此頁面上，我們會示範如何使用 `lightning.gpu` 來加速混合式工作負載。

## 將 `lightning.gpu`用於 QAOA 工作負載
<a name="lightning-gpu-qaoa"></a>

考慮此[筆記本](https://github.com/amazon-braket/amazon-braket-examples/tree/main/examples/hybrid_jobs/2_Using_PennyLane_with_Braket_Hybrid_Jobs)中的 Quantum 近似最佳化演算法 (QAOA) 範例。若要選取內嵌模擬器，請將引`device`數指定為格式的字串：`"local:<provider>/<simulator_name>"`。例如，您會`"local:pennylane/lightning.gpu"`為 設定 `lightning.gpu`。您在啟動時提供給混合任務的裝置字串會以環境變數 的形式傳遞給任務`"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)
```

在此頁面上，比較兩個內嵌的 PennyLane 狀態向量模擬器 `lightning.qubit`（以 CPU 為基礎） 和 `lightning.gpu`（以 GPU 為基礎）。為模擬器提供自訂閘道分解，以計算各種漸層。

現在您已準備好準備混合任務啟動指令碼。使用兩種執行個體類型執行 QAOA 演算法： `ml.m5.2xlarge`和 `ml.g4dn.xlarge`。`ml.m5.2xlarge` 執行個體類型與標準開發人員筆記型電腦相當。`ml.g4dn.xlarge` 是具有單一 NVIDIA T4 GPU 和 16GB 記憶體的加速運算執行個體。

若要執行 GPU，我們首先需要指定相容的映像和正確的執行個體 （預設為`ml.m5.2xlarge`執行個體）。

```
from braket.aws import AwsSession
from braket.jobs.image_uris import Framework, retrieve_image

image_uri = retrieve_image(Framework.PL_PYTORCH, AwsSession().region)
instance_config = InstanceConfig(instanceType="ml.g4dn.xlarge")
```

然後，我們需要將這些輸入混合任務裝飾項目，以及系統和混合任務引數中的更新裝置參數。

```
@hybrid_job(
        device="local:pennylane/lightning.gpu",
        input_data=input_file_path,
        image_uri=image_uri,
        instance_config=instance_config)
def run_qaoa_hybrid_job_gpu(p=1, steps=10):
    params = np.random.rand(2, p)

    braket_task_tracker = Tracker()

    graph = nx.read_adjlist(input_file_path, nodetype=int)
    wires = list(graph.nodes)
    cost_h, _mixer_h = qaoa.maxcut(graph)

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

**注意**  
如果您將 指定`instance_config`為使用 GPU 型執行個體，但選擇 `device`做為內嵌的 CPU 型模擬器 (`lightning.qubit`)，則不會使用 GPU。如果您想要以 GPU 為目標，請務必使用嵌入式 GPU 型模擬器！

`m5.2xlarge` 執行個體的平均反覆運算時間約為 73 秒，而`ml.g4dn.xlarge`執行個體的反覆運算時間約為 0.6 秒。對於此 21 qubit 工作流程，GPU 執行個體可提供 100 倍的速度。如果您查看 Amazon Braket Hybrid Jobs [定價頁面](https://aws.amazon.com/braket/pricing/)，您可以看到`m5.2xlarge`執行個體的每分鐘成本為 0.00768 USD，而`ml.g4dn.xlarge`執行個體的每分鐘成本為 0.01227 USD。在此執行個體中，在 GPU 執行個體上執行會更快且更便宜。

## Quantum 機器學習和資料平行處理
<a name="quantumML-data-parallelism"></a>

如果您的工作負載類型是在資料集上訓練的量子機器學習 (QML)，您可以使用資料平行處理進一步加速工作負載。在 QML 中，模型包含一或多個量子電路。模型可能也可能不包含傳統神經網路。使用資料集訓練模型時，模型中的參數會更新，以將損失函數降至最低。損失函數通常針對單一資料點定義，以及整個資料集平均損失的總損失。在 QML 中，損失通常會先以序列方式計算，再平均至梯度運算的總損失。此程序耗時，特別是有數百個資料點時。

由於某個資料點的損失不取決於其他資料點，因此可以平行評估損失！您可以同時評估與不同資料點相關聯的損失和梯度。這稱為資料平行處理。使用 SageMaker 的分散式資料平行程式庫，Amazon Braket Hybrid Jobs 可讓您更輕鬆地使用資料平行處理來加速訓練。

請考慮下列資料平行處理的 QML 工作負載，其使用來自已知 UCI 儲存庫的 [Sonar 資料集](https://archive.ics.uci.edu/dataset/151/connectionist+bench+sonar+mines+vs+rocks)作為二進位分類的範例。聲納資料集具有 208 個資料點，每個資料點具有 60 個功能，這些功能是從聲納訊號從材料中彈射而來。每個資料點都標記為「M」表示礦區，或「R」表示石頭。我們的 QML 模型包含輸入層、做為隱藏層的量子電路，以及輸出層。輸入和輸出層是在 PyTorch 中實作的傳統神經網路。量子電路使用 PennyLane 的 qml.qnn 模組與 PyTorch 神經網路整合。如需工作負載的詳細資訊，請參閱我們的[範例筆記本](https://github.com/aws/amazon-braket-examples)。如同上述的 QAOA 範例，您可以使用 PennyLane 等嵌入式 GPU 型模擬器來利用 GPU 的強大功能`lightning.gpu`，以改善與嵌入式 CPU 型模擬器相比的效能。

若要建立混合任務，您可以透過其關鍵字引數呼叫`AwsQuantumJob.create`並指定演算法指令碼、裝置和其他組態。

```
instance_config = InstanceConfig(instanceType='ml.g4dn.xlarge')

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,
    ...
)
```

若要使用資料平行處理，您需要修改 SageMaker 分散式程式庫演算法指令碼中的幾行程式碼，以正確平行化訓練。首先，您會匯入 套件，該`smdistributed`套件會處理將工作負載分散到多個 GPUs 和多個執行個體的大部分繁重工作。此套件已在 Braket PyTorch 和 TensorFlow 容器中預先設定。`dist` 模組會告知我們的演算法指令碼，訓練的 GPUs 總數 (`world_size`) 以及 GPU 核心`local_rank`的 `rank`和 。 `rank` 是 GPU 在所有執行個體的絕對索引，而 `local_rank`是執行個體內 GPU 的索引。例如，如果有四個執行個體，每個執行個體都有八個 GPUs 配置給訓練，`rank`範圍從 0 到 31，`local_rank`範圍從 0 到 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)
```

接著，您可以`DistributedSampler`根據 定義 `world_size``rank`，然後將它傳遞至資料載入器。此取樣器會避免 GPUs 存取資料集的相同配量。

```
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,
)
```

接著，您可以使用 `DistributedDataParallel`類別來啟用資料平行處理。

```
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"])
```

以上是使用資料平行處理所需的變更。在 QML 中，您通常想要儲存結果並列印訓練進度。如果每個 GPU 執行儲存和列印命令，日誌會充滿重複的資訊，結果會互相覆寫。若要避免這種情況，您只能從具有 0 `rank` 的 GPU 儲存和列印。

```
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 支援 SageMaker 分散式資料平行程式庫的`ml.g4dn.12xlarge`執行個體類型。您可以透過混合任務中的 `InstanceConfig` 引數來設定執行個體類型。若要讓 SageMaker 分散式資料平行程式庫知道已啟用資料平行處理，您需要新增兩個額外的超參數，將 `"sagemaker_distributed_dataparallel_enabled"`設定為 `"true"`，並將 `"sagemaker_instance_type"`設定為您正在使用的執行個體類型。`smdistributed` 套件會使用這兩個超參數。您的演算法指令碼不需要明確使用它們。在 Amazon Braket SDK 中，它提供方便的關鍵字引數 `distribution`。在建立混合任務`distribution="data_parallel"`時，Amazon Braket SDK 會自動為您插入兩個超參數。如果您使用 Amazon Braket API，則需要包含這兩個超參數。

設定執行個體和資料平行處理後，您現在可以提交混合任務。`ml.g4dn.12xlarge` 執行個體中有 4 個 GPUs。當您設定 `instanceCount=1` 時，工作負載會分散到執行個體中的 8 個 GPUs。當您設定`instanceCount`大於一個時，工作負載會分散到所有執行個體中可用的 GPUs。使用多個執行個體時，每個執行個體會根據您使用的時間而產生費用。例如，當您使用四個執行個體時，計費時間為每個執行個體執行時間的四倍，因為有四個執行個體同時執行您的工作負載。

```
instance_config = InstanceConfig(instanceType='ml.g4dn.12xlarge',
                                 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",
    ...
)
```

**注意**  
在上述混合任務建立中， `train_dp.py`是使用資料平行處理的修改演算法指令碼。請注意，只有在您根據上述章節修改演算法指令碼時，資料平行處理才能正常運作。如果在未正確修改演算法指令碼的情況下啟用資料平行處理選項，混合任務可能會擲回錯誤，或者每個 GPU 可能會重複處理相同的資料配量，這很低效率。

如果正確使用，使用多個執行個體可能會導致時間和成本大幅減少。如需[詳細資訊，請參閱範例筆記本](https://github.com/amazon-braket/amazon-braket-examples/blob/main/examples/hybrid_jobs/5_Parallelize_training_for_QML/Parallelize_training_for_QML.ipynb)。

# 搭配 Amazon Braket 使用 CUDA-Q
<a name="braket-using-cuda-q"></a>

NVIDIA's CUDA-Q 是一種軟體程式庫，專為結合 CPUs、GPUs 和 Quantum 處理單元 (QPUs) 的程式設計混合量子演算法而設計。它提供統一的程式設計模型，可讓開發人員在單一程式中同時表達傳統和量子指令，簡化工作流程。 使用其內建 CPU 和 GPU 模擬器CUDA-Q加速量子程式模擬和執行時間。 CUDA-Q 可用於原生 Braket 筆記本執行個體 (NBIs) 和 Amazon Braket 混合任務。

**Topics**
+ [NBIs中的 CUDA-Q](#braket-cuda-q-nbis)
+ [混合任務中的 CUDA-Q](#braket-cuda-q-hybrid-jobs)

## NBIs中的 CUDA-Q
<a name="braket-cuda-q-nbis"></a>

CUDA-Q 預設會在 Braket NBI 環境中安裝 。您可以前往 Jupyter 啟動器頁面，然後選取 CUDA-Q和 Braket 圖磚來開啟CUDA-Q範例筆記本。這會在`0_Getting_started_with_CUDA-Q.ipynb`主視窗中開啟範例筆記本。如需更多CUDA-Q範例，請參閱 `nvidia_cuda_q/`目錄中的左側面板。

您也可以驗證 NBI 中安裝的 版本CUDA-Q或任何其他第三方套件。例如，您可以在筆記本程式碼儲存格中執行下列命令，以驗證安裝在環境中的 CUDA-Q、Qiskit、PennyLane 和 Braket 套件版本。

```
%pip freeze | grep -i -e cudaq -e qiskit -e pennylane -e braket
```

## 混合任務中的 CUDA-Q
<a name="braket-cuda-q-hybrid-jobs"></a>

在 [Amazon Braket 混合任務](https://docs.aws.amazon.com/braket/latest/developerguide/braket-jobs.html)CUDA-Q上使用 可提供彈性的隨需運算環境。運算執行個體只會在工作負載期間執行，確保您只需支付使用量的費用。Amazon Braket Hybrid Jobs 也提供可擴展的體驗。使用者可以從較小的執行個體開始進行原型設計和測試，然後擴展到能夠處理更大工作負載的大型執行個體，以進行完整的實驗。

Amazon Braket Hybrid Jobs 支援 GPUs，對於最大化 CUDA-Q的潛力至關重要。與 CPU 型模擬器相比，GPUs 可大幅加速量子程式模擬，特別是在使用高 qubit 計數電路時。在 Amazon Braket 混合任務CUDA-Q上使用 時，平行化會變得直接。混合任務可簡化多個運算節點之間電路取樣和可觀測評估的分佈。這種CUDA-Q工作負載的無縫平行化可讓使用者更專注於開發工作負載，而不是為大規模實驗設定基礎設施。

若要開始使用，請參閱 Amazon Braket 範例 Github 上的[CUDA-Q入門範例](https://github.com/amazon-braket/amazon-braket-examples/blob/main/examples/nvidia_cuda_q/0_Getting_started_with_CUDA-Q.ipynb)，以使用 Braket 提供的CUDA-Q混合任務容器。

下列程式碼片段是使用 Amazon Braket Hybrid Jobs 執行CUDA-Q程式`hello-world`的範例。

```
image_uri = retrieve_image(Framework.CUDAQ, AwsSession().region)

@hybrid_job(device='local:nvidia/qpp-cpu', image_uri=image_uri)
def hello_quantum():
    import cudaq

    # define the backend
    device=get_job_device_arn()
    cudaq.set_target(device.split('/')[-1])

    # define the Bell circuit
    kernel = cudaq.make_kernel()
    qubits = kernel.qalloc(2)
    kernel.h(qubits[0])
    kernel.cx(qubits[0], qubits[1])

    # sample the Bell circuit
    result = cudaq.sample(kernel, shots_count=1000)
    measurement_probabilities = dict(result.items())
    
    return measurement_probabilities
```

上述範例模擬 CPU 模擬器上的 Bell 電路。此範例會在您的筆記型電腦或 Braket Jupyter 筆記本上執行。由於 `local=True`設定，當您執行此指令碼時，容器會在您的本機環境中啟動，以執行用於測試和偵錯的CUDA-Q程式。完成測試後，您可以移除 `local=True`旗標，並在其中執行任務 AWS。若要進一步了解，請參閱[使用 Amazon Braket 混合任務](braket-jobs.md)。

如果您的工作負載具有高 qubit 計數、大量電路或大量反覆運算，您可以透過指定 `instance_config`設定來使用更強大的 CPU 運算資源。下列程式碼片段示範如何在`hybrid_job`裝飾項目中設定 `instance_config`設定。如需支援的執行個體類型的詳細資訊，請參閱[設定您的混合任務執行個體](braket-jobs-configure-job-instance-for-script.md)。如需執行個體類型的清單，請參閱 [Amazon EC2 執行個體類型](https://aws.amazon.com/ec2/instance-types/)。

```
@hybrid_job(
    device="local:nvidia/qpp-cpu",
    image_uri=image_uri,
    instance_config=InstanceConfig(instanceType="ml.c5.2xlarge"),
)
def my_job_script():
    ...
```

對於要求更高的工作負載，您可以在 CUDA-Q GPU 模擬器上執行工作負載。若要啟用 GPU 模擬器，請使用後端名稱 `nvidia`。`nvidia` 後端以 CUDA-Q GPU 模擬器的形式運作。接著，選取支援 NVIDIA GPU 的 Amazon EC2 執行個體類型。下列程式碼片段顯示 GPU 設定的`hybrid_job`裝飾項目。

```
@hybrid_job(
    device="local:nvidia/nvidia",
    image_uri=image_uri,
    instance_config=InstanceConfig(instanceType="ml.g4dn.xlarge"),
)
def my_job_script():
    ...
```

Amazon Braket 混合任務和 NBIs支援使用 的平行 GPU 模擬CUDA-Q。您可以平行評估多個可觀測項目或多個電路，以提升工作負載的效能。若要平行處理多個可觀測項目，請對演算法指令碼進行下列變更。

設定`nvidia`後端`mgpu`的選項。這是平行化可觀測項目的必要項目。平行處理使用 MPI 在 GPUs 之間進行通訊，因此 MPI 需要在執行前初始化，並在執行後完成。

接著，透過設定 來指定執行模式`execution=cudaq.parallel.mpi`。下列程式碼片段顯示這些變更。

```
cudaq.set_target("nvidia", option="mqpu")
cudaq.mpi.initialize()
result = cudaq.observe(
    kernel, hamiltonian, shots_count=n_shots, execution=cudaq.parallel.mpi
)
cudaq.mpi.finalize()
```

在`hybrid_job`裝飾項目中，指定託管多個 GPUs 的執行個體類型，如下列程式碼片段所示。

```
@hybrid_job(
    device="local:nvidia/nvidia-mqpu",
    instance_config=InstanceConfig(instanceType="ml.g4dn.12xlarge", instanceCount=1),
    image_uri=image_uri,
)
def parallel_observables_gpu_job(sagemaker_mpi_enabled=True):
    ...
```

Amazon Braket 範例 Github 中的[平行模擬筆記本](https://github.com/amazon-braket/amazon-braket-examples/blob/main/examples/nvidia_cuda_q/5_Multiple_GPU_simulations.ipynb)提供end-to-end範例，示範如何在 GPU 後端上執行量子程式模擬，以及對可觀測項目和電路批次執行平行模擬。

### 在量子電腦上執行工作負載
<a name="braket-using-cuda-q-quantum"></a>

完成模擬器測試後，您可以轉換至在 QPUs 上執行實驗。只要將目標切換到 Amazon Braket QPU，例如 IQM、 IonQ或 Rigetti 裝置。下列程式碼片段說明如何將目標設定為IQM Garnet裝置。如需可用 QPUs的清單，請參閱 [Amazon Braket 主控台](https://console.aws.amazon.com/braket/home)。

```
device_arn = "arn:aws:braket:eu-north-1::device/qpu/iqm/Garnet"
cudaq.set_target("braket", machine=device_arn)
```

如需混合任務的詳細資訊，請參閱開發人員指南中的[使用 Amazon Braket 混合任務](braket-jobs.md)。若要進一步了解 CUDA-Q，請參閱 [NVIDIA CUDA-Q 文件](https://nvidia.github.io/cuda-quantum/latest/index.html)。