نمونه اولیه برای تولید: تنظیم فراپارامتر

۱. مرور کلی

در این آزمایش، شما از Vertex AI برای اجرای یک کار تنظیم هایپرپارامتر در Vertex AI Training استفاده خواهید کرد.

این آزمایشگاه بخشی از مجموعه ویدیوهای نمونه اولیه تا تولید است. قبل از امتحان کردن این آزمایش، حتماً آزمایش قبلی را انجام دهید. برای کسب اطلاعات بیشتر می‌توانید سری ویدیوهای همراه را تماشا کنید:

.

آنچه یاد می‌گیرید

شما یاد خواهید گرفت که چگونه:

  • اصلاح کد برنامه آموزشی برای تنظیم خودکار هایپرپارامتر
  • پیکربندی و اجرای یک کار تنظیم هایپرپارامتر با Vertex AI Python SDK

هزینه کل اجرای این آزمایشگاه در گوگل کلود حدود ۱ دلار است.

۲. مقدمه‌ای بر هوش مصنوعی ورتکس

این آزمایشگاه از جدیدترین محصول هوش مصنوعی موجود در Google Cloud استفاده می‌کند. Vertex AI، محصولات یادگیری ماشین را در سراسر Google Cloud در یک تجربه توسعه یکپارچه ادغام می‌کند. پیش از این، مدل‌های آموزش‌دیده با AutoML و مدل‌های سفارشی از طریق سرویس‌های جداگانه قابل دسترسی بودند. این محصول جدید، هر دو را در یک API واحد، به همراه سایر محصولات جدید، ترکیب می‌کند. همچنین می‌توانید پروژه‌های موجود را به Vertex AI منتقل کنید.

Vertex AI شامل محصولات مختلفی برای پشتیبانی از گردش‌های کاری یادگیری ماشینی سرتاسری است. این آزمایشگاه بر روی محصولات برجسته زیر تمرکز خواهد کرد: آموزش و میز کار

بررسی اجمالی محصولات ورتکس

۳. محیط خود را آماده کنید

مراحل آموزش مدل‌های سفارشی با آزمایشگاه Vertex AI را برای راه‌اندازی محیط خود تکمیل کنید.

۴. کد برنامه آموزشی را کانتینریزه کنید

شما این کار آموزشی را با قرار دادن کد برنامه آموزشی خود در یک کانتینر Docker و ارسال این کانتینر به Google Artifact Registry به Vertex AI ارسال خواهید کرد. با استفاده از این رویکرد، می‌توانید مدلی را که با هر چارچوبی ساخته شده است، آموزش داده و تنظیم کنید.

برای شروع، از منوی Launcher نوت‌بوک Workbench که در آزمایش‌های قبلی ایجاد کرده‌اید، یک پنجره ترمینال باز کنید.

ترمینال را در نوت بوک باز کنید

مرحله ۱: نوشتن کد آموزشی

یک دایرکتوری جدید به نام flowers-hptune ایجاد کنید و با دستور cd به آن وارد شوید:

mkdir flowers-hptune
cd flowers-hptune

دستور زیر را اجرا کنید تا یک دایرکتوری برای کد آموزشی و یک فایل پایتون ایجاد شود که کد زیر را در آن اضافه خواهید کرد.

mkdir trainer
touch trainer/task.py

اکنون باید موارد زیر را در دایرکتوری flowers-hptune/ خود داشته باشید:

+ trainer/
    + task.py

سپس، فایل task.py که ایجاد کردید را باز کنید و کد زیر را در آن کپی کنید.

شما باید {your-gcs-bucket} در BUCKET_ROOT با باکت Cloud Storage که مجموعه داده‌های گل‌ها را در تمرین ۱ ذخیره کرده‌اید، جایگزین کنید.

import tensorflow as tf
import numpy as np
import os
import hypertune
import argparse

## Replace {your-gcs-bucket} !!
BUCKET_ROOT='/gcs/{your-gcs-bucket}'

# Define variables
NUM_CLASSES = 5
EPOCHS=10
BATCH_SIZE = 32

IMG_HEIGHT = 180
IMG_WIDTH = 180

DATA_DIR = f'{BUCKET_ROOT}/flower_photos'

def get_args():
  '''Parses args. Must include all hyperparameters you want to tune.'''

  parser = argparse.ArgumentParser()
  parser.add_argument(
      '--learning_rate',
      required=True,
      type=float,
      help='learning rate')
  parser.add_argument(
      '--momentum',
      required=True,
      type=float,
      help='SGD momentum value')
  parser.add_argument(
      '--num_units',
      required=True,
      type=int,
      help='number of units in last hidden layer')
  args = parser.parse_args()
  return args

def create_datasets(data_dir, batch_size):
  '''Creates train and validation datasets.'''

  train_dataset = tf.keras.utils.image_dataset_from_directory(
    data_dir,
    validation_split=0.2,
    subset="training",
    seed=123,
    image_size=(IMG_HEIGHT, IMG_WIDTH),
    batch_size=batch_size)

  validation_dataset = tf.keras.utils.image_dataset_from_directory(
    data_dir,
    validation_split=0.2,
    subset="validation",
    seed=123,
    image_size=(IMG_HEIGHT, IMG_WIDTH),
    batch_size=batch_size)

  train_dataset = train_dataset.cache().shuffle(1000).prefetch(buffer_size=tf.data.AUTOTUNE)
  validation_dataset = validation_dataset.cache().prefetch(buffer_size=tf.data.AUTOTUNE)

  return train_dataset, validation_dataset


def create_model(num_units, learning_rate, momentum):
  '''Creates model.'''

  model = tf.keras.Sequential([
    tf.keras.layers.Resizing(IMG_HEIGHT, IMG_WIDTH),
    tf.keras.layers.Rescaling(1./255, input_shape=(IMG_HEIGHT, IMG_WIDTH, 3)),
    tf.keras.layers.Conv2D(16, 3, padding='same', activation='relu'),
    tf.keras.layers.MaxPooling2D(),
    tf.keras.layers.Conv2D(32, 3, padding='same', activation='relu'),
    tf.keras.layers.MaxPooling2D(),
    tf.keras.layers.Conv2D(64, 3, padding='same', activation='relu'),
    tf.keras.layers.MaxPooling2D(),
    tf.keras.layers.Flatten(),
    tf.keras.layers.Dense(num_units, activation='relu'),
    tf.keras.layers.Dense(NUM_CLASSES, activation='softmax')
  ])

  model.compile(optimizer=tf.keras.optimizers.SGD(learning_rate=learning_rate, momentum=momentum),
              loss=tf.keras.losses.SparseCategoricalCrossentropy(),
              metrics=['accuracy'])
  
  return model

def main():
  args = get_args()
  train_dataset, validation_dataset = create_datasets(DATA_DIR, BATCH_SIZE)
  model = create_model(args.num_units, args.learning_rate, args.momentum)
  history = model.fit(train_dataset, validation_data=validation_dataset, epochs=EPOCHS)

  # DEFINE METRIC
  hp_metric = history.history['val_accuracy'][-1]

  hpt = hypertune.HyperTune()
  hpt.report_hyperparameter_tuning_metric(
      hyperparameter_metric_tag='accuracy',
      metric_value=hp_metric,
      global_step=EPOCHS)


if __name__ == "__main__":
    main()

قبل از ساخت کانتینر، بیایید نگاه عمیق‌تری به کد بیندازیم. چند مؤلفه وجود دارد که مختص استفاده از سرویس تنظیم هایپرپارامتر هستند.

  1. این اسکریپت کتابخانه hypertune را وارد می‌کند.
  2. تابع get_args() یک آرگومان خط فرمان برای هر ابرپارامتری که می‌خواهید تنظیم کنید، تعریف می‌کند. در این مثال، ابرپارامترهایی که تنظیم می‌شوند عبارتند از نرخ یادگیری، مقدار تکانه در بهینه‌ساز و تعداد واحدها در آخرین لایه پنهان مدل، اما می‌توانید با موارد دیگر نیز آزمایش کنید. مقداری که در این آرگومان‌ها ارسال می‌شود، سپس برای تنظیم ابرپارامتر مربوطه در کد استفاده می‌شود.
  3. در انتهای تابع main() ، از کتابخانه hypertune برای تعریف معیاری که می‌خواهید بهینه‌سازی کنید استفاده می‌شود. در TensorFlow، متد model.fit در keras یک شیء History را برمی‌گرداند. ویژگی History.history رکوردی از مقادیر تلفات آموزش و مقادیر معیارها در دوره‌های متوالی است. اگر داده‌های اعتبارسنجی را به model.fit ارسال کنید، ویژگی History.history شامل مقادیر تلفات اعتبارسنجی و معیارها نیز خواهد بود. به عنوان مثال، اگر مدلی را برای سه دوره با داده‌های اعتبارسنجی آموزش داده‌اید و accuracy به عنوان معیار ارائه داده‌اید، ویژگی History.history مشابه دیکشنری زیر خواهد بود.
{
 "accuracy": [
   0.7795261740684509,
   0.9471358060836792,
   0.9870933294296265
 ],
 "loss": [
   0.6340447664260864,
   0.16712145507335663,
   0.04546636343002319
 ],
 "val_accuracy": [
   0.3795261740684509,
   0.4471358060836792,
   0.4870933294296265
 ],
 "val_loss": [
   2.044623374938965,
   4.100203514099121,
   3.0728273391723633
 ]

اگر می‌خواهید سرویس تنظیم هایپرپارامتر مقادیری را که دقت اعتبارسنجی مدل را به حداکثر می‌رسانند، کشف کند، باید معیار را به عنوان آخرین ورودی (یا NUM_EPOCS - 1 ) از لیست val_accuracy تعریف کنید. سپس، این معیار را به یک نمونه از HyperTune منتقل کنید. می‌توانید هر رشته‌ای را که دوست دارید برای hyperparameter_metric_tag انتخاب کنید، اما بعداً هنگام شروع کار تنظیم هایپرپارامتر، باید دوباره از این رشته استفاده کنید.

مرحله ۲: ایجاد یک داکرفایل

برای کانتینرایز کردن کد خود، باید یک Dockerfile ایجاد کنید. در Dockerfile تمام دستورات مورد نیاز برای اجرای تصویر را قرار خواهید داد. این فایل تمام کتابخانه‌های لازم را نصب کرده و نقطه ورود کد آموزشی را تنظیم می‌کند.

از طریق ترمینال خود، یک Dockerfile خالی در ریشه دایرکتوری flowers-hptune خود ایجاد کنید:

touch Dockerfile

اکنون باید موارد زیر را در دایرکتوری flowers-hptune/ خود داشته باشید:

+ Dockerfile
+ trainer/
    + task.py

فایل Dockerfile را باز کنید و موارد زیر را در آن کپی کنید. متوجه خواهید شد که این تقریباً مشابه فایل Dockerfile است که در آزمایش اول استفاده کردیم، با این تفاوت که اکنون کتابخانه cloudml-hypertune را نصب می‌کنیم.

FROM gcr.io/deeplearning-platform-release/tf2-gpu.2-8

WORKDIR /

# Installs hypertune library
RUN pip install cloudml-hypertune

# Copies the trainer code to the docker image.
COPY trainer /trainer

# Sets up the entry point to invoke the trainer.
ENTRYPOINT ["python", "-m", "trainer.task"]

مرحله 3: ساخت کانتینر

از ترمینال خود، دستور زیر را برای تعریف یک متغیر env برای پروژه خود اجرا کنید، و مطمئن شوید که your-cloud-project را با شناسه پروژه خود جایگزین می‌کنید:

PROJECT_ID='your-cloud-project'

یک مخزن (repo) در رجیستری مصنوعات (Artifact Registry) تعریف کنید. ما از مخزنی که در تمرین اول ایجاد کردیم استفاده خواهیم کرد.

REPO_NAME='flower-app'

یک متغیر با URI تصویر کانتینر خود در Google Artifact Registry تعریف کنید:

IMAGE_URI=us-central1-docker.pkg.dev/$PROJECT_ID/$REPO_NAME/flower_image_hptune:latest

پیکربندی داکر

gcloud auth configure-docker \
    us-central1-docker.pkg.dev

سپس، با اجرای دستور زیر از ریشه دایرکتوری flower-hptune کانتینر را بسازید:

docker build ./ -t $IMAGE_URI

در آخر، آن را به رجیستری مصنوعات (Artifact Registry) منتقل کنید:

docker push $IMAGE_URI

با قرار دادن کانتینر در فهرست آثار باستانی، اکنون آماده‌اید تا کار آموزشی را شروع کنید.

۵. اجرای تابع تنظیم هایپرپارامتر با SDK

در این بخش، نحوه پیکربندی و ارسال کار تنظیم هایپرپارامتر را با استفاده از API پایتون Vertex خواهید آموخت.

از طریق Launcher، یک دفترچه یادداشت TensorFlow 2 ایجاد کنید.

نوت بوک_جدید

Vertex AI SDK را وارد کنید.

from google.cloud import aiplatform
from google.cloud.aiplatform import hyperparameter_tuning as hpt

برای شروع کار تنظیم هایپرپارامتر، ابتدا باید worker_pool_specs را تعریف کنید که نوع ماشین و تصویر داکر را مشخص می‌کند. مشخصات زیر یک ماشین با دو پردازنده گرافیکی NVIDIA Tesla V100 را تعریف می‌کند.

شما باید {PROJECT_ID} را در image_uri با پروژه خود جایگزین کنید.

# The spec of the worker pools including machine type and Docker image
# Be sure to replace PROJECT_ID in the `image_uri` with your project.

worker_pool_specs = [{
    "machine_spec": {
        "machine_type": "n1-standard-4",
        "accelerator_type": "NVIDIA_TESLA_V100",
        "accelerator_count": 1
    },
    "replica_count": 1,
    "container_spec": {
        "image_uri": "us-central1-docker.pkg.dev/{PROJECT_ID}/flower-app/flower_image_hptune:latest"
    }
}]

در مرحله بعد، parameter_spec تعریف کنید، که یک دیکشنری است که پارامترهایی را که می‌خواهید بهینه کنید مشخص می‌کند. کلید دیکشنری رشته‌ای است که برای هر هایپرپارامتر به آرگومان خط فرمان اختصاص داده‌اید و مقدار دیکشنری، مشخصات پارامتر است.

برای هر هایپرپارامتر، باید نوع و همچنین محدوده مقادیری را که سرویس تنظیم امتحان خواهد کرد، تعریف کنید. هایپرپارامترها می‌توانند از نوع Double، Integer، Categorical یا Discrete باشند. اگر نوع Double یا Integer را انتخاب کنید، باید حداقل و حداکثر مقدار را ارائه دهید. و اگر Categorical یا Discrete را انتخاب کنید، باید مقادیر را ارائه دهید. برای انواع Double و Integer، باید مقدار مقیاس‌بندی را نیز ارائه دهید. می‌توانید در این ویدیو درباره نحوه انتخاب بهترین مقیاس بیشتر بیاموزید.

# Dictionary representing parameters to optimize.
# The dictionary key is the parameter_id, which is passed into your training
# job as a command line argument,
# And the dictionary value is the parameter specification of the metric.
parameter_spec = {
    "learning_rate": hpt.DoubleParameterSpec(min=0.001, max=1, scale="log"),
    "momentum": hpt.DoubleParameterSpec(min=0, max=1, scale="linear"),
    "num_units": hpt.DiscreteParameterSpec(values=[64, 128, 512], scale=None)
}

آخرین مشخصه برای تعریف، metric_spec است که یک دیکشنری است که معیار بهینه‌سازی را نشان می‌دهد. کلید دیکشنری، hyperparameter_metric_tag است که در کد برنامه آموزشی خود تنظیم می‌کنید و مقدار آن، هدف بهینه‌سازی است.

# Dictionary representing metric to optimize.
# The dictionary key is the metric_id, which is reported by your training job,
# And the dictionary value is the optimization goal of the metric.
metric_spec={'accuracy':'maximize'}

پس از تعریف مشخصات، یک CustomJob ایجاد خواهید کرد که مشخصات رایجی است که برای اجرای کار شما در هر یک از آزمایش‌های تنظیم هایپرپارامتر استفاده خواهد شد.

شما باید {YOUR_BUCKET} را با باکتی که قبلاً ایجاد کرده‌اید جایگزین کنید.

# Replace YOUR_BUCKET
my_custom_job = aiplatform.CustomJob(display_name='flowers-hptune-job',
                              worker_pool_specs=worker_pool_specs,
                              staging_bucket='gs://{YOUR_BUCKET}')

سپس، HyperparameterTuningJob را ایجاد و اجرا کنید.

hp_job = aiplatform.HyperparameterTuningJob(
    display_name='flowers-hptune-job',
    custom_job=my_custom_job,
    metric_spec=metric_spec,
    parameter_spec=parameter_spec,
    max_trial_count=15,
    parallel_trial_count=3)

hp_job.run()

چند استدلال وجود دارد که باید به آنها توجه کرد:

  • max_trial_count : شما باید یک حد بالا برای تعداد آزمایش‌هایی که سرویس اجرا خواهد کرد، تعیین کنید. آزمایش‌های بیشتر عموماً منجر به نتایج بهتری می‌شوند، اما نقطه‌ای از بازده نزولی وجود خواهد داشت که پس از آن آزمایش‌های اضافی تأثیر کمی یا هیچ تأثیری بر معیاری که سعی در بهینه‌سازی آن دارید، ندارند. بهترین روش این است که با تعداد کمتری آزمایش شروع کنید و قبل از افزایش مقیاس، میزان تأثیرگذاری هایپرپارامترهای انتخابی خود را ارزیابی کنید.
  • parallel_trial_count : اگر از آزمایش‌های موازی استفاده می‌کنید، سرویس چندین خوشه پردازش آموزشی را فراهم می‌کند. افزایش تعداد آزمایش‌های موازی، مدت زمان اجرای کار تنظیم هایپرپارامتر را کاهش می‌دهد؛ با این حال، می‌تواند اثربخشی کلی کار را کاهش دهد. دلیل این امر این است که استراتژی تنظیم پیش‌فرض از نتایج آزمایش‌های قبلی برای اطلاع‌رسانی در مورد تخصیص مقادیر در آزمایش‌های بعدی استفاده می‌کند.
  • search_algorithm : می‌توانید الگوریتم جستجو را روی شبکه‌ای، تصادفی یا پیش‌فرض (هیچکدام) تنظیم کنید. گزینه پیش‌فرض، بهینه‌سازی بیزی را برای جستجوی فضای مقادیر ممکن ابرپارامتر اعمال می‌کند و الگوریتم پیشنهادی است. می‌توانید اطلاعات بیشتر در مورد این الگوریتم را اینجا بیابید.

در کنسول، می‌توانید پیشرفت کار خود را مشاهده کنید.

hp_job

و وقتی تمام شد، می‌توانید نتایج هر آزمایش و اینکه کدام مجموعه از مقادیر بهترین عملکرد را داشته‌اند را ببینید.

نتایج hp

🎉 تبریک می‌گویم! 🎉

شما یاد گرفتید که چگونه از Vertex AI برای موارد زیر استفاده کنید:

  • اجرای یک کار تنظیم خودکار هایپرپارامتر

برای کسب اطلاعات بیشتر در مورد بخش‌های مختلف Vertex، مستندات آن را بررسی کنید.

۶. پاکسازی

از آنجا که نوت‌بوک را طوری پیکربندی کرده‌ایم که پس از ۶۰ دقیقه بیکاری، زمان انقضا داشته باشد، نیازی نیست نگران خاموش کردن نمونه باشیم. اگر می‌خواهید نمونه را به صورت دستی خاموش کنید، روی دکمه Stop در بخش Vertex AI Workbench کنسول کلیک کنید. اگر می‌خواهید نوت‌بوک را به طور کامل حذف کنید، روی دکمه Delete کلیک کنید.

مثال را متوقف کنید

برای حذف Storage Bucket، با استفاده از منوی ناوبری در Cloud Console خود، به Storage بروید، Bucket خود را انتخاب کنید و روی Delete کلیک کنید:

حذف فضای ذخیره‌سازی