教程:使用 AutoML 和 Python 训练物体检测模型

适用范围:Azure CLI ml 扩展 v2(最新版)Python SDK azure-ai-ml v2(最新版)

本教程介绍如何通过 Azure 机器学习 CLI 扩展 v2 或 Azure 机器学习 Python SDK v2 使用 Azure 机器学习自动化 ML 训练物体检测模型。 此物体检测模型可识别图像是否包含对象(如罐、纸箱、奶瓶或水瓶)。

自动化 ML 接受训练数据和配置设置,并自动循环访问不同特征规范化/标准化方法、模型和超参数设置的组合,以实现最佳模型。

在本教程中,你将使用 Python SDK 编写代码,并了解以下任务:

  • 下载和转换数据
  • 训练自动化机器学习物体检测模型
  • 为模型指定超参数值
  • 执行超参数扫描
  • 部署模型
  • 直观呈现检测结果

先决条件

  • 要使用 Azure 机器学习,你需要一个工作区。 如果没有工作区,请完成创建开始使用所需的资源以创建工作区并详细了解如何使用它。

  • 此功能支持 Python 3.6 或 3.7

  • 下载并解压缩 odFridgeObjects.zip 数据文件*。 数据集以 Pascal VOC 格式进行注释,其中每个图像对应一个 xml 文件。 每个 xml 文件都包含有关其对应图像文件所在位置的信息,还包含有关边界框和对象标签的信息。 若要使用此数据,首先需要将其转换为所需的 JSONL 格式,如笔记本的将下载的数据转换为 JSONL 部分中所示。

  • 使用计算实例来学习本教程,无需安装其他软件。 (请参阅如何创建计算实例。)或者安装 CLI/SDK 以使用你自己的本地环境。

    适用于:Azure CLI ml 扩展 v2(当前)

    还可以在 GitHub 上的 azureml-examples 存储库中找到本教程。 如果你希望在自己的本地环境中运行计算实例:

计算目标设置

注意

要尝试无服务器计算(预览版),请跳过此步骤并继续进行实验设置

首先需要设置用于自动化 ML 模型训练的计算目标。 用于图像任务的自动化 ML 模型需要 GPU SKU。

本教程将使用 NCsv3 系列(具有 V100 GPU),因为此类计算目标会使用多个 GPU 来加速训练。 此外,还可以设置多个节点,以在优化模型的超参数时利用并行度。

以下代码创建一个大小为 Standard_NC24s_v3 的 GPU 计算,其中包含四个节点。

适用于:Azure CLI ml 扩展 v2(当前)

请创建一个具有以下配置的 .yml 文件。

$schema: https://azuremlschemas.azureedge.net/latest/amlCompute.schema.json 
name: gpu-cluster
type: amlcompute
size: Standard_NC24s_v3
min_instances: 0
max_instances: 4
idle_time_before_scale_down: 120

若要创建计算,请使用 .yml 文件的路径、工作区名称、资源组和订阅 ID 运行以下 CLI v2 命令。

az ml compute create -f [PATH_TO_YML_FILE] --workspace-name [YOUR_AZURE_WORKSPACE] --resource-group [YOUR_AZURE_RESOURCE_GROUP] --subscription [YOUR_AZURE_SUBSCRIPTION]

试验设置

可以使用试验来跟踪模型训练作业。

适用于:Azure CLI ml 扩展 v2(当前)

可以使用 experiment_name 键提供试验名称,如下所示:

experiment_name: dpv2-cli-automl-image-object-detection-experiment

直观呈现输入数据

JSONL(JSON 行)格式准备好输入图像数据后,就可以直观呈现图像的地面实况边界框。 若要执行此操作,请确保你已安装 matplotlib

%pip install --upgrade matplotlib

%matplotlib inline
import matplotlib.pyplot as plt
import matplotlib.image as mpimg
import matplotlib.patches as patches
from PIL import Image as pil_image
import numpy as np
import json
import os

def plot_ground_truth_boxes(image_file, ground_truth_boxes):
    # Display the image
    plt.figure()
    img_np = mpimg.imread(image_file)
    img = pil_image.fromarray(img_np.astype("uint8"), "RGB")
    img_w, img_h = img.size

    fig,ax = plt.subplots(figsize=(12, 16))
    ax.imshow(img_np)
    ax.axis("off")

    label_to_color_mapping = {}

    for gt in ground_truth_boxes:
        label = gt["label"]

        xmin, ymin, xmax, ymax =  gt["topX"], gt["topY"], gt["bottomX"], gt["bottomY"]
        topleft_x, topleft_y = img_w * xmin, img_h * ymin
        width, height = img_w * (xmax - xmin), img_h * (ymax - ymin)

        if label in label_to_color_mapping:
            color = label_to_color_mapping[label]
        else:
            # Generate a random color. If you want to use a specific color, you can use something like "red".
            color = np.random.rand(3)
            label_to_color_mapping[label] = color

        # Display bounding box
        rect = patches.Rectangle((topleft_x, topleft_y), width, height,
                                 linewidth=2, edgecolor=color, facecolor="none")
        ax.add_patch(rect)

        # Display label
        ax.text(topleft_x, topleft_y - 10, label, color=color, fontsize=20)

    plt.show()

def plot_ground_truth_boxes_jsonl(image_file, jsonl_file):
    image_base_name = os.path.basename(image_file)
    ground_truth_data_found = False
    with open(jsonl_file) as fp:
        for line in fp.readlines():
            line_json = json.loads(line)
            filename = line_json["image_url"]
            if image_base_name in filename:
                ground_truth_data_found = True
                plot_ground_truth_boxes(image_file, line_json["label"])
                break
    if not ground_truth_data_found:
        print("Unable to find ground truth information for image: {}".format(image_file))

对于任何给定的图像,利用上述帮助程序函数,可以运行以下代码来显示边界框。

image_file = "./odFridgeObjects/images/31.jpg"
jsonl_file = "./odFridgeObjects/train_annotations.jsonl"

plot_ground_truth_boxes_jsonl(image_file, jsonl_file)

上传数据并创建 MLTable

为了将数据用于训练,请将数据上传到 Azure 机器学习工作区的默认 Blob 存储并将其注册为资产。 注册数据的好处包括:

  • 便于与团队其他成员共享
  • 对元数据(位置、描述等)进行版本控制
  • 世系跟踪

适用于:Azure CLI ml 扩展 v2(当前)

请创建一个具有以下配置的 .yml 文件。

$schema: https://azuremlschemas.azureedge.net/latest/data.schema.json
name: fridge-items-images-object-detection
description: Fridge-items images Object detection
path: ./data/odFridgeObjects
type: uri_folder

若要将图像作为数据资产上传,请使用 .yml 文件的路径、工作区名称、资源组和订阅 ID 运行以下 CLI v2 命令。

az ml data create -f [PATH_TO_YML_FILE] --workspace-name [YOUR_AZURE_WORKSPACE] --resource-group [YOUR_AZURE_RESOURCE_GROUP] --subscription [YOUR_AZURE_SUBSCRIPTION]

下一步是使用 jsonl 格式的数据创建 MLTable,如下所示。 MLtable 会将数据打包为一个可供训练使用的对象。

paths:
  - file: ./train_annotations.jsonl
transformations:
  - read_json_lines:
        encoding: utf8
        invalid_lines: error
        include_path_column: false
  - convert_column_types:
      - columns: image_url
        column_type: stream_info

适用于:Azure CLI ml 扩展 v2(当前)

以下配置从 MLTable 创建训练和验证数据。

target_column_name: label
training_data:
  path: data/training-mltable-folder
  type: mltable
validation_data:
  path: data/validation-mltable-folder
  type: mltable

配置物体检测试验

若要为图像相关任务配置自动化 ML 作业,请创建特定于任务的 AutoML 作业。

适用于:Azure CLI ml 扩展 v2(当前)

若要使用无服务器计算(预览版),请将行 compute: azureml:gpu-cluster 替换为以下代码:

resources:
 instance_type: Standard_NC24s_v3
 instance_count: 4
task: image_object_detection
primary_metric: mean_average_precision
compute: azureml:gpu-cluster

适用于图像任务的自动超参数扫描 (AutoMode)

重要

此功能目前处于公开预览状态。 此预览版不附带服务级别协议。 某些功能可能不受支持或者受限。 有关详细信息,请参阅适用于 Azure 预览版的补充使用条款

在 AutoML 作业中,可以执行自动超参数扫描,以查找最佳模型(我们将此功能称为 AutoMode)。 你将仅指定试用次数;不需要超参数搜索空间、采样方法和提前终止策略。 系统会自动根据试用次数确定要扫描的超参数空间的区域。 介于 10 到 20 之间的值可能适用于许多数据集。

适用于:Azure CLI ml 扩展 v2(当前)

limits:
  max_trials: 10
  max_concurrent_trials: 2

然后,你可以提交作业来训练图像模型。

适用于:Azure CLI ml 扩展 v2(当前)

若要提交 AutoML 作业,请运行以下 CLI v2 命令,其中包含 .yml 文件路径、工作区名称、资源组和订阅 ID。

az ml job create --file ./hello-automl-job-basic.yml --workspace-name [YOUR_AZURE_WORKSPACE] --resource-group [YOUR_AZURE_RESOURCE_GROUP] --subscription [YOUR_AZURE_SUBSCRIPTION]

适用于图像任务的手动超参数扫描

在 AutoML 作业中,可以使用 model_name 参数指定模型体系结构,并配置设置以对定义的搜索空间执行超参数扫描,以查找最佳模型。

在本示例中,我们将使用 yolov5fasterrcnn_resnet50_fpn 训练一个物体检测模型,这两者都在 COCO 上预先进行了训练,COCO 是一个大规模物体检测、分段和字幕数据集,其中包含 80 多个标签类别的数千个带标签的图像。

可以对已定义的搜索空间执行超参数扫描,以查找最佳模型。

作业限制

可以通过在限制设置中为作业指定 timeout_minutesmax_trialsmax_concurrent_trials 来控制 AutoML 映像训练作业上花费的资源。 请参阅有关作业限制参数的详细说明

适用于:Azure CLI ml 扩展 v2(当前)

limits:
  timeout_minutes: 60
  max_trials: 10
  max_concurrent_trials: 2

以下代码定义了搜索空间,准备对每个已定义的体系结构 yolov5fasterrcnn_resnet50_fpn 进行超参数扫描。 在搜索空间中,指定 learning_rateoptimizerlr_scheduler 等的值范围,以便 AutoML 在尝试生成具有最佳主要指标的模型时从中进行选择。 如果未指定超参数值,则对每个体系结构使用默认值。

对于优化设置,通过使用 random sampling_algorithm,借助随机抽样从此参数空间中选取样本。 上面配置的作业限制可以让自动化 ML 尝试使用这些不同样本总共进行 10 次试验,在使用四个节点进行设置的计算目标上一次运行两次试验。 搜索空间的参数越多,查找最佳模型所需的试验次数就越多。

还使用了“Bandit 提前终止”策略。 此策略将终止性能不佳的试用;也就是那些与最佳性能试用版相差不在 20% 容许范围内的试用版,这样可显著节省计算资源。

适用于:Azure CLI ml 扩展 v2(当前)

sweep:
  sampling_algorithm: random
  early_termination:
    type: bandit
    evaluation_interval: 2
    slack_factor: 0.2
    delay_evaluation: 6
search_space:
  - model_name:
      type: choice
      values: [yolov5]
    learning_rate:
      type: uniform
      min_value: 0.0001
      max_value: 0.01
    model_size:
      type: choice
      values: [small, medium]

  - model_name:
      type: choice
      values: [fasterrcnn_resnet50_fpn]
    learning_rate:
      type: uniform
      min_value: 0.0001
      max_value: 0.001
    optimizer:
      type: choice
      values: [sgd, adam, adamw]
    min_size:
      type: choice
      values: [600, 800]

定义搜索空间和扫描设置后,便可以提交作业以使用训练数据集训练图像模型。

适用于:Azure CLI ml 扩展 v2(当前)

若要提交 AutoML 作业,请运行以下 CLI v2 命令,其中包含 .yml 文件路径、工作区名称、资源组和订阅 ID。

az ml job create --file ./hello-automl-job-basic.yml --workspace-name [YOUR_AZURE_WORKSPACE] --resource-group [YOUR_AZURE_RESOURCE_GROUP] --subscription [YOUR_AZURE_SUBSCRIPTION]

执行超参数扫描时,使用 HyperDrive UI 直观呈现所尝试的不同试用版会很有用。 可以导航到此 UI,方法是从上级(即 HyperDrive 父作业)转到主 automl_image_job 的 UI 中的“子作业”选项卡。 然后,可以转到此项的“子作业”选项卡。

也可在下面直接查看 HyperDrive 父作业,然后导航到其“子作业”选项卡:

适用于:Azure CLI ml 扩展 v2(当前)

CLI example not available, please use Python SDK.

注册和部署模型

作业完成后,可以注册从最佳试用(产生了最佳主要指标的配置)创建的模型。 可在下载后注册模型,也可通过指定具有相应 jobidazureml 路径进行注册。

获取最佳试用版

适用于:Azure CLI ml 扩展 v2(当前)

CLI example not available, please use Python SDK.

注册模型

使用 azureml 路径或本地下载的路径注册模型。

适用于:Azure CLI ml 扩展 v2(当前)

 az ml model create --name od-fridge-items-mlflow-model --version 1 --path azureml://jobs/$best_run/outputs/artifacts/outputs/mlflow-model/ --type mlflow_model --workspace-name [YOUR_AZURE_WORKSPACE] --resource-group [YOUR_AZURE_RESOURCE_GROUP] --subscription [YOUR_AZURE_SUBSCRIPTION]

注册要使用的模型后,可以使用托管联机终结点 deploy-managed-online-endpoint 进行部署

配置联机终结点

适用于:Azure CLI ml 扩展 v2(当前)

$schema: https://azuremlschemas.azureedge.net/latest/managedOnlineEndpoint.schema.json
name: od-fridge-items-endpoint
auth_mode: key

创建终结点

使用之前创建的 MLClient,我们现在将在工作区中创建终结点。 此命令会启动终结点创建操作,并在终结点创建操作继续时返回确认响应。

适用于:Azure CLI ml 扩展 v2(当前)

az ml online-endpoint create --file .\create_endpoint.yml --workspace-name [YOUR_AZURE_WORKSPACE] --resource-group [YOUR_AZURE_RESOURCE_GROUP] --subscription [YOUR_AZURE_SUBSCRIPTION]

还可以创建一个批处理终结点,用于针对一段时间内的大量数据执行批量推理。 签出用于使用批处理终结点执行批量推理的物体检测批处理评分笔记本。

配置联机部署

部署是一组资源,用于承载执行实际推理的模型。 我们将使用 ManagedOnlineDeployment 类为终结点创建一个部署。 可为部署群集使用 GPU 或 CPU VM SKU。

适用于:Azure CLI ml 扩展 v2(当前)

name: od-fridge-items-mlflow-deploy
endpoint_name: od-fridge-items-endpoint
model: azureml:od-fridge-items-mlflow-model@latest
instance_type: Standard_DS3_v2
instance_count: 1
liveness_probe:
    failure_threshold: 30
    success_threshold: 1
    timeout: 2
    period: 10
    initial_delay: 2000
readiness_probe:
    failure_threshold: 10
    success_threshold: 1
    timeout: 10
    period: 10
    initial_delay: 2000 

创建部署

使用前面创建的 MLClient,我们将在工作区中创建部署。 此命令将启动部署创建操作,并在部署创建操作继续时返回确认响应。

适用于:Azure CLI ml 扩展 v2(当前)

az ml online-deployment create --file .\create_deployment.yml --workspace-name [YOUR_AZURE_WORKSPACE] --resource-group [YOUR_AZURE_RESOURCE_GROUP] --subscription [YOUR_AZURE_SUBSCRIPTION]

更新流量:

默认情况下,当前部署设置为接收 0% 流量。 可以设置当前部署应接收的流量百分比。 使用一个终结点的所有部署接收的流量百分比总和不应超过 100%。

适用于:Azure CLI ml 扩展 v2(当前)

az ml online-endpoint update --name 'od-fridge-items-endpoint' --traffic 'od-fridge-items-mlflow-deploy=100' --workspace-name [YOUR_AZURE_WORKSPACE] --resource-group [YOUR_AZURE_RESOURCE_GROUP] --subscription [YOUR_AZURE_SUBSCRIPTION]

测试部署

适用于:Azure CLI ml 扩展 v2(当前)

CLI example not available, please use Python SDK.

直观呈现检测结果

为测试图像评分后,可以直观呈现此图像的边界框。 若要执行此操作,请确保已安装 matplotlib。

适用于:Azure CLI ml 扩展 v2(当前)

CLI example not available, please use Python SDK.

清理资源

如果打算运行其他 Azure 机器学习教程,请不要完成本部分。

如果不打算使用已创建的资源,请删除它们,以免产生任何费用。

  1. 在 Azure 门户中,选择最左侧的“资源组”。
  2. 从列表中选择已创建的资源组。
  3. 选择“删除资源组”
  4. 输入资源组名称。 然后选择“删除”。

还可保留资源组,但请删除单个工作区。 显示工作区属性,然后选择“删除”。

后续步骤

在本自动化机器学习教程中,你已完成以下任务:

  • 配置了工作区并准备了试验数据。
  • 训练了自动化物体检测模型
  • 为模型指定了超参数值
  • 执行了超参数扫描
  • 部署了模型
  • 直观呈现了检测结果

注意

可通过 MIT 许可证下的许可使用 fridge 对象数据集。