Обучение моделей Scikit-learn в большом масштабе с помощью Машинного обучения Azure

ОБЛАСТЬ ПРИМЕНЕНИЯ: Пакет SDK для Python azure-ai-ml версии 2 (current)

В этой статье вы узнаете, как запустить скрипты обучения scikit-learn с помощью Машинное обучение Azure пакета SDK для Python версии 2.

Примеры сценариев, приведенные в этой статье, используются для классификации изображений ирисов для создания модели машинного обучения на основе набора данных ирисов Scikit-learn.

Обучаете ли вы модель Scikit-learn машинного обучения с нуля или переносите существующую модель в облако, вы можете использовать Машинное обучение Azure для горизонтального масштабирования заданий обучения с открытым кодом с помощью эластичных облачных вычислительных ресурсов. Вы можете создавать, развертывать, версионировать и отслеживать модели производственного уровня с помощью Машинного обучения Azure.

Необходимые компоненты

Вы можете запустить код для этой статьи в Машинное обучение Azure вычислительном экземпляре или в собственной записной книжке Jupyter Notebook.

  • Вычислительная операция Машинного обучения Azure

    • Завершите создание ресурсов, чтобы приступить к созданию вычислительного экземпляра. Каждый вычислительный экземпляр включает выделенный сервер записной книжки, предварительно загруженный пакетом SDK и примером репозитория записных книжек.
    • Перейдите на вкладку "Записная книжка" в Студии машинного обучения Azure. В папке обучения примеров найдите завершенную и развернутую записную книжку, перейдя к этому каталогу: задания > пакета SDK > версии 2 > с одним шагом > scikit-learn > train-hyperparameter-tune-deploy-with-sklearn.
    • Для выполнения этого руководства можно использовать предварительно заполненный код в образце папки обучения.
  • Сервер записной книжки Jupyter.

Настройка задания

Этот раздел настраивает задание для обучения, загружая необходимые пакеты Python, подключаясь к рабочей области, создавая вычислительный ресурс для выполнения задания команды и создавая среду для запуска задания.

Подключение к рабочей области

Сначала необходимо подключиться к рабочей области Машинное обучение Azure. Рабочая область Машинного обучения Azure — это ресурс верхнего уровня данной службы. Он предоставляет централизованное место для работы со всеми артефактами, создаваемыми при использовании Машинное обучение Azure.

Мы используем DefaultAzureCredential для получения доступа к рабочей области. Эти учетные данные должны быть способны обрабатывать большинство сценариев проверки подлинности пакета SDK Для Azure.

Если DefaultAzureCredential вы не работаете, ознакомьтесь azure-identity reference documentation с дополнительными доступными учетными данными.Set up authentication

# Handle to the workspace
from azure.ai.ml import MLClient

# Authentication package
from azure.identity import DefaultAzureCredential

credential = DefaultAzureCredential()

Если вы предпочитаете использовать браузер для входа и проверки подлинности, удалите комментарии в следующем коде и используйте его.

# Handle to the workspace
# from azure.ai.ml import MLClient

# Authentication package
# from azure.identity import InteractiveBrowserCredential
# credential = InteractiveBrowserCredential()

Затем получите дескриптор рабочей области, указав идентификатор подписки, имя группы ресурсов и имя рабочей области. Чтобы найти следующие параметры, выполните следующие действия.

  1. Найдите в правом верхнем углу панели инструментов Студия машинного обучения Azure имя рабочей области.
  2. Выберите имя рабочей области, чтобы отобразить идентификатор группы ресурсов и подписки.
  3. Скопируйте значения для группы ресурсов и идентификатора подписки в код.
# Get a handle to the workspace
ml_client = MLClient(
    credential=credential,
    subscription_id="<SUBSCRIPTION_ID>",
    resource_group_name="<RESOURCE_GROUP>",
    workspace_name="<AML_WORKSPACE_NAME>",
)

Результатом выполнения этого скрипта является дескриптор рабочей области, используемый для управления другими ресурсами и заданиями.

Примечание.

Создание MLClient не приведет к подключению клиента к рабочей области. Инициализация клиента отложена и ожидает первого вызова. В этой статье это произойдет во время создания вычислений.

Создание вычислительного ресурса

Машинное обучение Azure требуется вычислительный ресурс для запуска задания. Этот ресурс может быть одним или несколькими узлами с ОС Linux или Windows или определенной вычислительной структурой, такой как Spark.

В следующем примере скрипта мы подготавливаем Linux compute cluster. Вы увидите страницу Azure Machine Learning pricing полного списка размеров и цен на виртуальные машины. Для этого примера нам нужен только базовый кластер; Таким образом, мы выбрали модель Standard_DS3_v2 с 2 ядрами vCPU и 7 ГБ ОЗУ для создания Машинное обучение Azure вычислений.

from azure.ai.ml.entities import AmlCompute

# Name assigned to the compute cluster
cpu_compute_target = "cpu-cluster"

try:
    # let's see if the compute target already exists
    cpu_cluster = ml_client.compute.get(cpu_compute_target)
    print(
        f"You already have a cluster named {cpu_compute_target}, we'll reuse it as is."
    )

except Exception:
    print("Creating a new cpu compute target...")

    # Let's create the Azure ML compute object with the intended parameters
    cpu_cluster = AmlCompute(
        name=cpu_compute_target,
        # Azure ML Compute is the on-demand VM service
        type="amlcompute",
        # VM Family
        size="STANDARD_DS3_V2",
        # Minimum running nodes when there is no job running
        min_instances=0,
        # Nodes in cluster
        max_instances=4,
        # How many seconds will the node running after the job termination
        idle_time_before_scale_down=180,
        # Dedicated or LowPriority. The latter is cheaper but there is a chance of job termination
        tier="Dedicated",
    )

    # Now, we pass the object to MLClient's create_or_update method
    cpu_cluster = ml_client.compute.begin_create_or_update(cpu_cluster).result()

print(
    f"AMLCompute with name {cpu_cluster.name} is created, the compute size is {cpu_cluster.size}"
)

Создание среды задания

Чтобы запустить задание Машинное обучение Azure, требуется среда. Среда Машинное обучение Azure инкапсулирует зависимости (такие как среда выполнения программного обеспечения и библиотеки), необходимые для запуска скрипта обучения машинного обучения на вычислительном ресурсе. Эта среда похожа на среду Python на локальном компьютере.

Машинное обучение Azure позволяет использовать курированную (или готовую) среду или создать настраиваемую среду с помощью образа Docker или конфигурации Conda. В этой статье вы создадите настраиваемую среду для заданий с помощью файла Conda YAML.

Создание пользовательской среды

Чтобы создать настраиваемую среду, необходимо определить зависимости Conda в YAML-файле. Сначала создайте каталог для хранения файла. В этом примере мы назвали каталог env.

import os

dependencies_dir = "./env"
os.makedirs(dependencies_dir, exist_ok=True)

Затем создайте файл в каталоге зависимостей. В этом примере мы назвали файл conda.yml.

%%writefile {dependencies_dir}/conda.yaml
name: sklearn-env
channels:
  - conda-forge
dependencies:
  - python=3.8
  - pip=21.2.4
  - scikit-learn=0.24.2
  - scipy=1.7.1
  - pip:  
    - azureml-mlflow==1.42.0
    - mlflow-skinny==2.3.2

Спецификация содержит некоторые обычные пакеты (например, numpy и pip), которые вы используете в задании.

Затем используйте YAML-файл, чтобы создать и зарегистрировать эту настраиваемую среду в рабочей области. Среда упаковается в контейнер Docker во время выполнения.

from azure.ai.ml.entities import Environment

custom_env_name = "sklearn-env"

job_env = Environment(
    name=custom_env_name,
    description="Custom environment for sklearn image classification",
    conda_file=os.path.join(dependencies_dir, "conda.yaml"),
    image="mcr.microsoft.com/azureml/openmpi4.1.0-ubuntu20.04:latest",
)
job_env = ml_client.environments.create_or_update(job_env)

print(
    f"Environment with name {job_env.name} is registered to workspace, the environment version is {job_env.version}"
)

Дополнительные сведения о создании и использовании сред см. в разделе Создание и использование программных сред в Машинном обучении Azure.

[Необязательно] Создание пользовательской среды с помощью расширения Intel® для Scikit-Learn

Хотите ускорить скрипты scikit-learn на оборудовании Intel? Попробуйте добавить расширение Intel® для Scikit-Learn в файл conda yaml и выполните следующие действия, описанные выше. Далее мы покажем, как включить эти оптимизации в следующем примере:

%%writefile {dependencies_dir}/conda.yaml
name: sklearn-env
channels:
  - conda-forge
dependencies:
  - python=3.8
  - pip=21.2.4
  - scikit-learn=0.24.2
  - scikit-learn-intelex
  - scipy=1.7.1
  - pip:  
    - azureml-mlflow==1.42.0
    - mlflow-skinny==2.3.2

Настройка и отправка задания обучения

В этом разделе описано, как запустить задание обучения с помощью предоставленного скрипта обучения. Для начала создайте задание обучения, настроив команду для запуска скрипта обучения. Затем вы отправляете задание обучения для выполнения в Машинное обучение Azure.

Подготовка скрипта обучения

В этой статье мы предоставили скрипт обучения train_iris.py. На практике вы можете использовать любой настраиваемый скрипт обучения как есть и запустить его с помощью Машинное обучение Azure без необходимости изменять код.

Примечание.

Указанный сценарий обучения выполняет следующие действия.

  • показывает, как регистрировать некоторые метрики в Машинное обучение Azure выполнения;
  • загружает и извлекает обучающие данные с помощью iris = datasets.load_iris(); и
  • обучает модель, а затем сохраняет и регистрирует ее.

Чтобы использовать и получать доступ к собственным данным, узнайте , как считывать и записывать данные в задании , чтобы сделать данные доступными во время обучения.

Чтобы использовать скрипт обучения, сначала создайте каталог, в котором будет храниться файл.

import os

src_dir = "./src"
os.makedirs(src_dir, exist_ok=True)

Затем создайте файл скрипта в исходном каталоге.

%%writefile {src_dir}/train_iris.py
# Modified from https://www.geeksforgeeks.org/multiclass-classification-using-scikit-learn/

import argparse
import os

# importing necessary libraries
import numpy as np

from sklearn import datasets
from sklearn.metrics import confusion_matrix
from sklearn.model_selection import train_test_split

import joblib

import mlflow
import mlflow.sklearn

def main():
    parser = argparse.ArgumentParser()

    parser.add_argument('--kernel', type=str, default='linear',
                        help='Kernel type to be used in the algorithm')
    parser.add_argument('--penalty', type=float, default=1.0,
                        help='Penalty parameter of the error term')

    # Start Logging
    mlflow.start_run()

    # enable autologging
    mlflow.sklearn.autolog()

    args = parser.parse_args()
    mlflow.log_param('Kernel type', str(args.kernel))
    mlflow.log_metric('Penalty', float(args.penalty))

    # loading the iris dataset
    iris = datasets.load_iris()

    # X -> features, y -> label
    X = iris.data
    y = iris.target

    # dividing X, y into train and test data
    X_train, X_test, y_train, y_test = train_test_split(X, y, random_state=0)

    # training a linear SVM classifier
    from sklearn.svm import SVC
    svm_model_linear = SVC(kernel=args.kernel, C=args.penalty)
    svm_model_linear = svm_model_linear.fit(X_train, y_train)
    svm_predictions = svm_model_linear.predict(X_test)

    # model accuracy for X_test
    accuracy = svm_model_linear.score(X_test, y_test)
    print('Accuracy of SVM classifier on test set: {:.2f}'.format(accuracy))
    mlflow.log_metric('Accuracy', float(accuracy))
    # creating a confusion matrix
    cm = confusion_matrix(y_test, svm_predictions)
    print(cm)

    registered_model_name="sklearn-iris-flower-classify-model"

    ##########################
    #<save and register model>
    ##########################
    # Registering the model to the workspace
    print("Registering the model via MLFlow")
    mlflow.sklearn.log_model(
        sk_model=svm_model_linear,
        registered_model_name=registered_model_name,
        artifact_path=registered_model_name
    )

    # # Saving the model to a file
    print("Saving the model via MLFlow")
    mlflow.sklearn.save_model(
        sk_model=svm_model_linear,
        path=os.path.join(registered_model_name, "trained_model"),
    )
    ###########################
    #</save and register model>
    ###########################
    mlflow.end_run()

if __name__ == '__main__':
    main()

[Необязательно] Включение оптимизаций Intel® Extension для Scikit-Learn для повышения производительности на оборудовании Intel

Если вы установили расширение Intel® для Scikit-Learn (как показано в предыдущем разделе), можно включить оптимизацию производительности, добавив две строки кода в начало файла скрипта, как показано ниже.

Дополнительные сведения о расширении Intel® для Scikit-Learn см. в документации по пакету.

%%writefile {src_dir}/train_iris.py
# Modified from https://www.geeksforgeeks.org/multiclass-classification-using-scikit-learn/

import argparse
import os

# Import and enable Intel Extension for Scikit-learn optimizations
# where possible

from sklearnex import patch_sklearn
patch_sklearn()

# importing necessary libraries
import numpy as np


from sklearn import datasets
from sklearn.metrics import confusion_matrix
from sklearn.model_selection import train_test_split

import joblib

import mlflow
import mlflow.sklearn

def main():
    parser = argparse.ArgumentParser()

    parser.add_argument('--kernel', type=str, default='linear',
                        help='Kernel type to be used in the algorithm')
    parser.add_argument('--penalty', type=float, default=1.0,
                        help='Penalty parameter of the error term')

    # Start Logging
    mlflow.start_run()

    # enable autologging
    mlflow.sklearn.autolog()

    args = parser.parse_args()
    mlflow.log_param('Kernel type', str(args.kernel))
    mlflow.log_metric('Penalty', float(args.penalty))

    # loading the iris dataset
    iris = datasets.load_iris()

    # X -> features, y -> label
    X = iris.data
    y = iris.target

    # dividing X, y into train and test data
    X_train, X_test, y_train, y_test = train_test_split(X, y, random_state=0)

    # training a linear SVM classifier
    from sklearn.svm import SVC
    svm_model_linear = SVC(kernel=args.kernel, C=args.penalty)
    svm_model_linear = svm_model_linear.fit(X_train, y_train)
    svm_predictions = svm_model_linear.predict(X_test)

    # model accuracy for X_test
    accuracy = svm_model_linear.score(X_test, y_test)
    print('Accuracy of SVM classifier on test set: {:.2f}'.format(accuracy))
    mlflow.log_metric('Accuracy', float(accuracy))
    # creating a confusion matrix
    cm = confusion_matrix(y_test, svm_predictions)
    print(cm)

    registered_model_name="sklearn-iris-flower-classify-model"

    ##########################
    #<save and register model>
    ##########################
    # Registering the model to the workspace
    print("Registering the model via MLFlow")
    mlflow.sklearn.log_model(
        sk_model=svm_model_linear,
        registered_model_name=registered_model_name,
        artifact_path=registered_model_name
    )

    # # Saving the model to a file
    print("Saving the model via MLFlow")
    mlflow.sklearn.save_model(
        sk_model=svm_model_linear,
        path=os.path.join(registered_model_name, "trained_model"),
    )
    ###########################
    #</save and register model>
    ###########################
    mlflow.end_run()

if __name__ == '__main__':
    main()

Создание задания обучения

Теперь, когда у вас есть все ресурсы, необходимые для выполнения задания, пришло время создать его с помощью пакета SDK для Python версии 2 Машинное обучение Azure. Чтобы запустить задание, мы создадим command.

Машинное обучение Azure command — это ресурс, который указывает все сведения, необходимые для выполнения кода обучения в облаке. Эти сведения включают входные и выходные данные, тип оборудования для использования, программное обеспечение для установки и запуск кода. Содержит command сведения для выполнения одной команды.

Настройка команды

Вы используете общую цель command для запуска скрипта обучения и выполнения нужных задач. Command Создайте объект, чтобы указать сведения о конфигурации задания обучения.

  • Входные данные для этой команды включают количество эпох, скорость обучения, импульс и выходной каталог.
  • Для значений параметров:
    • укажите вычислительный кластер cpu_compute_target = "cpu-cluster" , созданный для выполнения этой команды;
    • укажите пользовательскую средуsklearn-env, созданную для выполнения задания Машинное обучение Azure;
    • настройте само действие командной строки — в данном случае — это python train_iris.pyкоманда. Доступ к входным и выходным данным в команде можно получить с помощью ${{ ... }} нотации; и
    • настройте метаданные, такие как отображаемое имя и имя эксперимента; где эксперимент — это контейнер для всех итерации, которые выполняется в определенном проекте. Все задания, отправленные под тем же именем эксперимента, будут перечислены рядом друг с другом в Студия машинного обучения Azure.
from azure.ai.ml import command
from azure.ai.ml import Input

job = command(
    inputs=dict(kernel="linear", penalty=1.0),
    compute=cpu_compute_target,
    environment=f"{job_env.name}:{job_env.version}",
    code="./src/",
    command="python train_iris.py --kernel ${{inputs.kernel}} --penalty ${{inputs.penalty}}",
    experiment_name="sklearn-iris-flowers",
    display_name="sklearn-classify-iris-flower-images",
)

отправить задание.

Теперь пришло время отправить задание для выполнения в Машинное обучение Azure. На этот раз вы используете create_or_updateml_client.jobs.

ml_client.jobs.create_or_update(job)

После завершения задание регистрирует модель в рабочей области (в результате обучения) и выводит ссылку для просмотра задания в Студия машинного обучения Azure.

Предупреждение

Машинное обучение Azure запускает сценарии обучения, копируя весь исходный каталог. Если у вас есть конфиденциальные данные, которые вы не хотите отправлять, используйте файл .ignore или не включайте их в исходный каталог.

Что происходит во время выполнения задания

По мере выполнения задания он проходит через следующие этапы:

  • Подготовка. Создается образ Docker в соответствии с определенной средой. Образ отправляется в реестр контейнеров рабочей области и кэшируется для последующего выполнения. Журналы также передаются в журнал выполнения, и их можно просматривать для отслеживания хода выполнения. Если указана курированная среда, используется кэшированный образ, который поддерживается курированной средой.

  • Масштабирование. Кластер пытается увеличить масштаб, если кластеру требуется больше узлов для выполнения запуска, чем сейчас доступно.

  • Выполняется: все скрипты в папке скрипта передаются в целевой объект вычислений, хранилища данных подключены или копируются, а скрипт выполняется. Выходные данные из stdout и папки ./logs передаются в журнал выполнения и могут использоваться для мониторинга выполнения.

Настройка гиперпараметров модели

Теперь, когда вы узнали, как выполнить простой обучающий запуск Scikit-learn с помощью пакета SDK, давайте посмотрим, можно ли повысить точность модели. Вы можете настроить и оптимизировать гиперпараметры модели с помощью возможностей Машинное обучение Azuresweep.

Чтобы настроить гиперпараметры модели, определите пространство параметров, в котором выполняется поиск во время обучения. Это можно сделать, заменив некоторые параметры (kernel и penalty) переданы в задание обучения специальными входными данными из azure.ml.sweep пакета.

from azure.ai.ml.sweep import Choice

# we will reuse the command_job created before. we call it as a function so that we can apply inputs
# we do not apply the 'iris_csv' input again -- we will just use what was already defined earlier
job_for_sweep = job(
    kernel=Choice(values=["linear", "rbf", "poly", "sigmoid"]),
    penalty=Choice(values=[0.5, 1, 1.5]),
)

Затем вы настроите очистку в задании команды с помощью некоторых параметров, таких как основная метрика для просмотра и алгоритма выборки для использования.

В следующем коде мы используем случайную выборку, чтобы попробовать различные наборы конфигураций гиперпараметров в попытке максимизировать основную метрику Accuracy.

sweep_job = job_for_sweep.sweep(
    compute="cpu-cluster",
    sampling_algorithm="random",
    primary_metric="Accuracy",
    goal="Maximize",
    max_total_trials=12,
    max_concurrent_trials=4,
)

Теперь вы можете отправить это задание, как и раньше. На этот раз вы выполняете задание очистки, которое проходит над заданием обучения.

returned_sweep_job = ml_client.create_or_update(sweep_job)

# stream the output and wait until the job is finished
ml_client.jobs.stream(returned_sweep_job.name)

# refresh the latest status of the job after streaming
returned_sweep_job = ml_client.jobs.get(name=returned_sweep_job.name)

Вы можете отслеживать задание с помощью ссылки пользовательского интерфейса студии, представленной во время выполнения задания.

Поиск и регистрация лучшей модели

После завершения всех запусков можно найти запуск, создающий модель с максимальной точностью.

from azure.ai.ml.entities import Model

if returned_sweep_job.status == "Completed":

    # First let us get the run which gave us the best result
    best_run = returned_sweep_job.properties["best_child_run_id"]

    # lets get the model from this run
    model = Model(
        # the script stores the model as "sklearn-iris-flower-classify-model"
        path="azureml://jobs/{}/outputs/artifacts/paths/sklearn-iris-flower-classify-model/".format(
            best_run
        ),
        name="run-model-example",
        description="Model created from run.",
        type="custom_model",
    )

else:
    print(
        "Sweep job status: {}. Please wait until it completes".format(
            returned_sweep_job.status
        )
    )

Затем эту модель можно зарегистрировать.

registered_model = ml_client.models.create_or_update(model=model)

Развертывание модели

После регистрации модели его можно развернуть так же, как и любая другая зарегистрированная модель в Машинное обучение Azure. Дополнительные сведения о развертывании см. в статье "Развертывание и оценка модели машинного обучения с управляемой веб-конечной точкой с помощью пакета SDK для Python версии 2".

Следующие шаги

В этой статье вы обучили и зарегистрировали модель scikit-learn и узнали о вариантах развертывания. Подробные сведения о Машинном обучении Azure см. в следующих статьях.