YOLOv10-1.1部分代码阅读笔记-tuner.py

tuner.py

ultralytics\utils\tuner.py

目录

tuner.py

1.所需的库和模块

2.def run_ray_tune(model, space: dict = None, grace_period: int = 10, gpu_per_trial: int = None, max_samples: int = 10, **train_args): 


1.所需的库和模块

# Ultralytics YOLO 🚀, AGPL-3.0 license

import subprocess

from ultralytics.cfg import TASK2DATA, TASK2METRIC, get_save_dir
from ultralytics.utils import DEFAULT_CFG, DEFAULT_CFG_DICT, LOGGER, NUM_THREADS, checks

2.def run_ray_tune(model, space: dict = None, grace_period: int = 10, gpu_per_trial: int = None, max_samples: int = 10, **train_args): 

# 这段代码定义了一个名为 run_ray_tune 的函数,用于使用Ray Tune进行超参数调整。Ray Tune是一个用于超参数调整的库,可以与Ultralytics YOLO11模型结合使用,以优化模型的性能。
# 这行代码定义了 run_ray_tune 函数,它接受多个参数。
# 1.model :要进行超参数调整的YOLO模型。
# 2.space :一个字典,定义了超参数的搜索空间,默认为 None 。
# 3.grace_period :早期停止的宽限期,默认为10。
# 4.gpu_per_trial :每个试验分配的GPU数量,默认为 None 。
# 5.max_samples :最大试验次数,默认为10。
# 6.**train_args :其他训练参数,以关键字参数的形式传递。
def run_ray_tune(
    model, space: dict = None, grace_period: int = 10, gpu_per_trial: int = None, max_samples: int = 10, **train_args
):
    # 使用 Ray Tune 运行超参数调整。
    """
    Runs hyperparameter tuning using Ray Tune.

    Args:
        model (YOLO): Model to run the tuner on.
        space (dict, optional): The hyperparameter search space. Defaults to None.
        grace_period (int, optional): The grace period in epochs of the ASHA scheduler. Defaults to 10.
        gpu_per_trial (int, optional): The number of GPUs to allocate per trial. Defaults to None.
        max_samples (int, optional): The maximum number of trials to run. Defaults to 10.
        train_args (dict, optional): Additional arguments to pass to the `train()` method. Defaults to {}.

    Returns:
        (dict): A dictionary containing the results of the hyperparameter search.

    Example:
        ```python
        from ultralytics import YOLO

        # Load a YOLOv8n model
        model = YOLO('yolov8n.pt')

        # Start tuning hyperparameters for YOLOv8n training on the COCO8 dataset
        result_grid = model.tune(data='coco8.yaml', use_ray=True)
        ```
    """

    # 输出一个信息,提示用户查看Ray Tune的文档。
    LOGGER.info("💡 Learn about RayTune at https://docs.ultralytics.com/integrations/ray-tune")    # 💡 了解 RayTune,请访问 https://docs.ultralytics.com/integrations/ray-tune 。
    # 如果 train_args 为 None ,则将其初始化为一个空字典。
    if train_args is None:
        train_args = {}

    # 这段代码用于安装和导入Ray Tune及其相关模块,并检查 Wandb 是否已安装。
    try:
        # 使用 subprocess.run 执行命令行指令来安装 ray[tune] 。这里使用 split() 方法将安装命令字符串分割成列表,因为 subprocess.run 需要命令和参数以列表的形式提供。 check=True 参数确保如果安装过程中出现错误(例如,安装失败),将会抛出一个异常。
        subprocess.run("pip install ray[tune]<=2.9.3".split(), check=True)  # do not add single quotes here

        # 导入 ray 模块,这是使用Ray Tune的基础。
        import ray
        # 从 ray 模块中导入 tune 子模块,它包含了进行超参数调整所需的功能。
        from ray import tune
        # 从 ray.air 导入 RunConfig ,用于配置训练运行的各种参数。
        from ray.air import RunConfig
        # 从 ray.air.integrations.wandb 导入 WandbLoggerCallback ,如果使用Wandb进行实验跟踪和可视化,这个回调函数可以将训练信息记录到Wandb。
        from ray.air.integrations.wandb import WandbLoggerCallback
        # 从 ray.tune.schedulers 导入 ASHAScheduler ,这是一种用于超参数调整的调度器,可以提前停止表现不佳的试验,从而节省资源。
        from ray.tune.schedulers import ASHAScheduler
    # 如果在导入过程中发生 ImportError ,意味着所需的模块没有正确安装或不存在。
    except ImportError:
        # 代码会抛出一个 ModuleNotFoundError ,并提供一条错误信息,指导用户如何安装 ray[tune] 。
        raise ModuleNotFoundError('Ray Tune required but not found. To install run: pip install "ray[tune]<=2.9.3"')    # 需要 Ray Tune,但未找到。要安装,请运行:pip install "ray[tune]<=2.9.3" 。

    try:
        # 尝试导入 wandb 模块。 wandb 是一个用于跟踪和可视化机器学习实验的工具,可以帮助用户记录实验的超参数、模型性能等信息。
        import wandb

        # 使用 assert 语句检查 wandb 模块是否具有 __version__ 属性。这个属性通常存在于正确安装的Python包中,用于表示包的版本号。如果 wandb 模块没有这个属性, assert 语句将引发 AssertionError 。
        assert hasattr(wandb, "__version__")
    # 如果在导入 wandb 或检查 __version__ 属性时发生 ImportError 或 AssertionError ,捕获这些异常。
    except (ImportError, AssertionError):
        # 如果捕获到上述任何异常,将 wandb 设置为 False 。这表示 wandb 未安装或安装不正确,后续代码可以据此决定是否使用 wandb 进行实验跟踪。
        wandb = False
    # 这段代码通过以下步骤确保Ray Tune和Wandb的安装和导入。使用 subprocess.run 安装Ray Tune及其依赖项。导入Ray Tune相关模块,包括 tune 、 RunConfig 、 WandbLoggerCallback 和 ASHAScheduler 。检查Wandb是否已安装,并确保其版本正确。如果导入过程中发生错误,抛出异常并提示用户安装所需的模块。这种设计确保了在使用Ray Tune进行超参数调整时,所有必要的模块都已正确安装和导入,同时提供了明确的错误提示,帮助用户解决问题。

    # 这段代码首先检查Ray库的版本是否符合要求,然后定义了一个默认的超参数搜索空间,用于后续的超参数调整。
    # 调用 checks.check_version 函数,检查已安装的Ray库的版本是否小于或等于2.9.3。如果版本不符合要求,会抛出一个异常,提示用户安装符合要求的版本。这个检查确保了后续代码可以正常运行,因为某些功能可能依赖于特定版本的Ray库。
    checks.check_version(ray.__version__, "<=2.9.3", "ray")

    # tune.uniform(lower, upper)
    # tune.uniform() 是 Ray Tune 库中的一个函数,用于定义超参数搜索空间时指定一个均匀分布的范围。当你希望超参数在某个连续的区间内均匀地被采样时,可以使用这个函数。
    # 参数说明 :
    # lower :均匀分布的下限。
    # upper :均匀分布的上限。
    # 返回值 :
    # 返回一个在 [lower, upper] 区间内均匀分布的浮点数。
    # 用法示例 :
    # 在超参数调优中,如果你想要学习率 lr 在 0.0001 到 0.1 之间均匀地被采样,可以这样定义搜索空间:
    # search_space = {"lr": tune.uniform(1e-4, 1e-1)}      # 等价于 tune.uniform(0.0001, 0.1)
    # 在这个例子中, tune.uniform(1e-4, 1e-1) 表示 lr 将在这个范围内均匀地被采样。Ray Tune 将会在这个区间内随机选择值,作为学习率的候选值,进行模型的训练和评估。
    # tune.uniform 是定义连续超参数搜索空间的常用方法之一,它使得超参数优化过程更加灵活和高效。通过调整 lower 和 upper 参数,你可以控制超参数的搜索范围,从而对模型进行更精细的调优。

    # 这个字典  default_space  定义了默认的超参数搜索空间,用于超参数调整。每个键值对表示一个超参数及其取值范围。 tune.uniform(a, b) 表示在区间 [a, b] 内均匀采样。
    default_space = {
        # 'optimizer': tune.choice(['SGD', 'Adam', 'AdamW', 'NAdam', 'RAdam', 'RMSProp']),
        # 初始学习率,范围从  1e-5  到  1e-1  。
        "lr0": tune.uniform(1e-5, 1e-1),
        # 最终学习率因子( lr0 * lrf ),范围从 0.01 到 1.0 。
        "lrf": tune.uniform(0.01, 1.0),  # final OneCycleLR learning rate (lr0 * lrf)
        # SGD动量或Adam的beta1,范围从 0.6 到 0.98 。
        "momentum": tune.uniform(0.6, 0.98),  # SGD momentum/Adam beta1
        # 优化器的权重衰减,范围从 0.0 到 0.001 。
        "weight_decay": tune.uniform(0.0, 0.001),  # optimizer weight decay 5e-4
        # 预热周期数,范围从 0.0 到 5.0 (可以是小数)。
        "warmup_epochs": tune.uniform(0.0, 5.0),  # warmup epochs (fractions ok)
        # 预热初始动量,范围从 0.0 到 0.95 。
        "warmup_momentum": tune.uniform(0.0, 0.95),  # warmup initial momentum
        # 框损失增益,范围从 0.02 到 0.2 。
        "box": tune.uniform(0.02, 0.2),  # box loss gain
        # 分类损失增益(与像素规模成比例),范围从 0.2 到 4.0 。
        "cls": tune.uniform(0.2, 4.0),  # cls loss gain (scale with pixels)
        # 图像HSV-Hue增强(比例),范围从 0.0 到 0.1 。
        "hsv_h": tune.uniform(0.0, 0.1),  # image HSV-Hue augmentation (fraction)
        # 图像HSV-Saturation增强(比例),范围从 0.0 到 0.9 。
        "hsv_s": tune.uniform(0.0, 0.9),  # image HSV-Saturation augmentation (fraction)
        # 图像HSV-Value增强(比例),范围从 0.0 到 0.9 。
        "hsv_v": tune.uniform(0.0, 0.9),  # image HSV-Value augmentation (fraction)
        # 图像旋转角度(正负),范围从 0.0 到 45.0 。
        "degrees": tune.uniform(0.0, 45.0),  # image rotation (+/- deg)
        # 图像平移比例(正负),范围从 0.0 到 0.9 。
        "translate": tune.uniform(0.0, 0.9),  # image translation (+/- fraction)
        # 图像缩放增益(正负),范围从 0.0 到 0.9 。
        "scale": tune.uniform(0.0, 0.9),  # image scale (+/- gain)
        # 图像剪切角度(正负),范围从 0.0 到 10.0 。
        "shear": tune.uniform(0.0, 10.0),  # image shear (+/- deg)
        # 图像透视比例(正负),范围从 0.0 到 0.001 。
        "perspective": tune.uniform(0.0, 0.001),  # image perspective (+/- fraction), range 0-0.001
        # 图像上下翻转概率,范围从 0.0 到 1.0 。
        "flipud": tune.uniform(0.0, 1.0),  # image flip up-down (probability)
        # 图像左右翻转概率,范围从 0.0 到 1.0 。
        "fliplr": tune.uniform(0.0, 1.0),  # image flip left-right (probability)
        # 图像通道BGR概率,范围从 0.0 到 1.0 。
        "bgr": tune.uniform(0.0, 1.0),  # image channel BGR (probability)
        # 图像mosaic概率,范围从 0.0 到 1.0 。
        "mosaic": tune.uniform(0.0, 1.0),  # image mixup (probability)
        # 图像mixup概率,范围从 0.0 到 1.0 。
        "mixup": tune.uniform(0.0, 1.0),  # image mixup (probability)
        # segment复制粘贴概率,范围从 0.0 到 1.0 。
        "copy_paste": tune.uniform(0.0, 1.0),  # segment copy-paste (probability)
    }
    # 这段代码通过检查Ray库的版本并定义默认的超参数搜索空间,为后续的超参数调整做好了准备。默认的超参数搜索空间涵盖了常见的超参数及其取值范围,这些超参数在训练深度学习模型时对模型性能有显著影响。通过使用Ray Tune进行超参数调整,可以自动寻找最优的超参数组合,从而提高模型的性能。

    # 这段代码展示了如何在Ray的分布式环境中准备和训练一个模型,特别是使用Ray Tune进行超参数调整。
    # Put the model in ray store
    # 获取模型的任务类型,这可能是分类、检测或其他任务,用于后续配置和训练过程。
    task = model.task

    # ray.put(value, *, owner=None)
    # ray.put() 是 Ray 框架中的一个核心函数,用于将 Python 对象存储到 Ray 的分布式对象存储(Object Store)中,并异步返回一个唯一的对象引用(ObjectID)。
    # 参数说明 :
    # value :要存储的 Python 对象。
    # owner :(实验性参数)拥有该对象的 actor。这允许创建与创建进程的生命周期解耦的对象。拥有者 actor 必须在对象创建者退出前接收到对象的引用,否则引用仍然会丢失。
    # 返回值 :
    # 返回一个对象引用(ObjectID),该 ID 可用于在 Ray 集群中的任何节点上访问该对象。
    # 用法示例:
    # import ray
    # # 初始化 Ray
    # ray.init()
    # # 将一个 Python 对象存储到 Ray 的对象存储中
    # object_id = ray.put("hello world")
    # # 在 Ray 的其他部分,可以通过 object_id 访问该对象
    # result = ray.get(object_id)
    # print(result)  # 输出: hello world
    # 在这个示例中,字符串 "hello world" 被存储到 Ray 的对象存储中,并且返回了一个对象引用 object_id 。随后,可以通过 ray.get(object_id) 获取存储的对象。
    # 注意事项 :
    # ray.put() 返回的对象引用(ObjectID)是不可变的,并且只要存在对该 ID 的引用,存储的对象就不会被驱逐。
    # ray.put() 通常用于将大型对象或需要在多个任务或 actor 之间共享的对象存储到对象存储中,以减少数据复制和传输的开销。
    # 使用 ray.put() 可以有效地减少函数参数的写入对象存储的次数,通过传递对象 ID 而不是直接传递对象,可以提高性能和容错性。

    # 使用 ray.put 将 模型对象 放入Ray的分布式对象存储中。这允许模型在不同的Ray任务和进程中共享和访问,提高资源利用效率。
    model_in_store = ray.put(model)

    # 定义训练函数。
    def _tune(config):
        # 使用指定的超参数和其他参数训练 YOLO 模型。
        # 参数:
        # config (dict):用于训练的超参数字典。
        """
        Trains the YOLO model with the specified hyperparameters and additional arguments.

        Args:
            config (dict): A dictionary of hyperparameters to use for training.

        Returns:
            None
        """
        # 从Ray存储中获取 模型对象 。这一步确保每个训练任务都能访问到相同的模型实例。
        model_to_train = ray.get(model_in_store)  # get the model from ray store for tuning
        # 重置模型的回调函数。 这可能是因为模型在多次训练中使用,需要清除旧的回调设置,以避免冲突。
        model_to_train.reset_callbacks()
        # 将传入的训练参数 train_args 更新到 配置字典 config 中。这允许动态调整训练过程中的参数,如学习率、批大小等。
        config.update(train_args)
        # 调用模型的 train 方法,传入配置字典 config 。这将启动模型的训练过程,根据配置参数进行训练。
        results = model_to_train.train(**config)
        # 返回 训练结果的字典 。这个字典可能包含训练过程中的各种指标,如损失、准确率等,用于后续分析和评估。
        return results.results_dict
    # 这段代码通过将模型放入Ray的分布式存储中,并定义一个训练函数 _tune ,实现了在Ray环境中进行模型训练和超参数调整的准备工作。将模型放入Ray存储,以便在不同的训练任务中共享。定义一个训练函数 _tune ,从Ray存储中获取模型,重置回调函数,更新训练参数,并启动训练过程。返回训练结果的字典,包含训练过程中的各种指标。这种设计利用了Ray的分布式计算能力,可以高效地进行超参数调整,通过并行训练多个模型配置,快速找到最优的超参数组合。

    # 这段代码用于获取超参数搜索空间和数据集配置,确保在进行超参数调整时,这些关键信息已经准备好。
    # Get search space
    # 条件判断。检查 是否提供了自定义的超参数搜索空间 space 。如果没有提供(即 space 为 None 或空),则使用默认的搜索空间 default_space 。
    if not space:
        space = default_space
        # 日志警告。如果使用了默认搜索空间,记录一个警告信息,提示用户正在使用默认的搜索空间。这有助于用户了解当前的配置状态。
        LOGGER.warning("WARNING ⚠️ search space not provided, using default search space.")    # 警告⚠️未提供搜索空间,使用默认搜索空间。

    # Get dataset
    # 获取数据集路径。从 train_args 字典中获取数据集路径 data 。如果 train_args 中没有提供 data ,则使用任务类型  task  对应的默认数据集路径 TASK2DATA[task] 。
    data = train_args.get("data", TASK2DATA[task])
    # 更新搜索空间。将获取到的数据集路径 data 添加到 超参数搜索空间 space 中,确保在超参数调整过程中使用正确的数据集。
    space["data"] = data
    # 日志警告。如果 train_args 中没有提供 data ,记录一个警告信息,提示用户正在使用默认的数据集路径。这有助于用户了解当前的配置状态。
    if "data" not in train_args:
        LOGGER.warning(f'WARNING ⚠️ data not provided, using default "data={data}".')    # 警告⚠️未提供数据,使用默认的“data={data}”。
    # 这段代码通过检查和设置超参数搜索空间和数据集配置,确保在进行超参数调整时,这些关键信息已经准备好。检查是否提供了自定义的超参数搜索空间,如果没有提供,则使用默认搜索空间,并记录警告信息。从训练参数中获取数据集路径,如果没有提供,则使用默认数据集路径,并记录警告信息。将数据集路径添加到超参数搜索空间中,确保在超参数调整过程中使用正确的数据集。这种设计确保了超参数调整过程中的配置信息是完整和准确的,有助于用户更好地控制和理解训练过程。

    # 这段代码定义了用于超参数调整的训练函数、调度器和回调函数。这些组件共同工作,确保超参数调整过程高效且有条不紊地进行。
    # Define the trainable function with allocated resources

    # tune.with_resources(trainable, resources)
    # tune.with_resources() 是 Ray Tune 库中的一个函数,它用于为具体的可训练对象(trainable)指定资源需求。这个包装器允许你为特定的可训练对象声明资源要求,并且会覆盖已有的资源请求。
    # 参数说明 :
    # trainable :要包装的可训练对象,可以是函数或类。
    # resources :资源字典、放置组工厂(PlacementGroupFactory),或者是接受配置字典并返回放置组工厂的可调用对象。
    # 返回值 :
    # 返回一个包装后的可训练对象,其中包含了指定的资源请求。
    # 注意事项 :
    # tune.with_resources 主要用于函数类型的可训练对象,当你使用 Tuner() API 时。
    # 类类型的可训练对象通常只需要实现 default_resource_request() 方法来声明资源需求。
    # 使用 tune.with_resources 时需要谨慎,因为它会覆盖已有的资源请求。
    # 这个函数的主要用例是为函数类型的可训练对象请求资源,特别是在使用 Tuner() API 时。通过这种方式,可以确保在分布式环境中,每个训练试验都能获得所需的计算资源。

    # 定义训练函数并分配资源。
    # tune.with_resources :这个函数用于将训练函数 _tune 与指定的资源(CPU和GPU)绑定。这样可以确保每个训练任务在运行时都能获得足够的计算资源。
    # 资源分配 : cpu :分配的CPU线程数,由 NUM_THREADS 变量指定。 gpu :分配的GPU数量,由 gpu_per_trial 变量指定。如果 gpu_per_trial 为 None ,则默认为0。
    trainable_with_resources = tune.with_resources(_tune, {"cpu": NUM_THREADS, "gpu": gpu_per_trial or 0})

    # Define the ASHA scheduler for hyperparameter search

    # ASHAScheduler(time_attr='training_iteration', metric='metric', mode='max', max_t=100, grace_period=1, reduction_factor=4, brackets=1)
    # ASHAScheduler 是 Ray Tune 中的一个调度器,它实现了异步连续减半(Async Successive Halving)算法。这种算法可以提前终止性能较差的试验,节省计算资源,并将资源分配给表现较好的试验。
    # 参数说明 :
    # time_attr :(默认为 'training_iteration')用于比较时间的属性,可以是任何单调递增的属性,例如训练轮次。
    # metric :要优化的指标名称,即在训练结果字典中用于衡量优化目标的值。
    # mode :(默认为 'max')优化模式,可以是 'min' 或 'max',表示是最小化还是最大化指标。
    # max_t :(默认为 100)试验可以运行的最大时间单位,单位由 time_attr 决定。
    # grace_period :(默认为 1)在至少这个时间之后才考虑停止试验,单位与 time_attr 相同。
    # reduction_factor :(默认为 4)用于设置减半率和数量的无量纲标量。
    # brackets :(默认为 1)分组的数量,每个分组有不同的减半率,由 reduction_factor 指定。
    # ASHAScheduler 与其他调度器相比,提供了更好的并行性,并且在淘汰过程中避免了落后问题。因此,Ray Tune 推荐使用 ASHAScheduler 而不是标准的 HyperBandScheduler 。

    # 定义ASHA调度器。
    # ASHAScheduler 是一个用于超参数调整的调度器,可以提前终止表现不佳的试验,从而节省计算资源。
    asha_scheduler = ASHAScheduler(
        # 以训练周期(epoch)作为时间属性。
        time_attr="epoch",
        # 指定用于评估试验性能的指标,例如 "metrics/mAP50-95(B)" 。
        metric=TASK2METRIC[task],
        # 优化目标是最大化指定的指标。
        mode="max",
        # 最大训练周期数,优先从 train_args 中获取,如果没有则从默认配置 DEFAULT_CFG_DICT 中获取,如果都没有则默认为100。
        max_t=train_args.get("epochs") or DEFAULT_CFG_DICT["epochs"] or 100,
        # 早期停止的宽限期,即在多少个周期内不进行早期停止。
        grace_period=grace_period,
        # 每次减少资源时的因子,用于控制资源分配的粒度。
        reduction_factor=3,
    )

    # Define the callbacks for the hyperparameter search

    # WandbLoggerCallback(project: str | None = None, group: str | None = None, api_key_file: str | None = None, api_key: str | None = None, excludes: List[str] | None = None, log_config: bool = False, upload_checkpoints: bool = False, save_checkpoints: bool = False, upload_timeout: int = 1800, **kwargs)
    # WandbLoggerCallback 类是 Ray Tune 提供的一个回调函数,用于将训练过程中的指标自动记录到 Weights & Biases (Wandb) 平台。这有助于实时监控和可视化训练过程,方便用户分析和优化模型性能。
    # 参数说明 :
    # project :Wandb 项目的名称。这是必需的参数。
    # group :Wandb 组的名称。默认为训练函数的名称。
    # api_key_file :包含 Wandb API 密钥的文件路径。如果使用 WandbLogger ,此文件只需在运行 Tune 脚本的节点上存在。
    # api_key :Wandb API 密钥。这是 api_key_file 的替代方案。
    # excludes :不应记录的指标和配置的列表。
    # log_config :布尔值,表示是否记录 results 字典中的 config 参数。如果在训练过程中参数会变化(例如使用 PopulationBasedTraining ),则应设置为 True 。默认为 False 。
    # upload_checkpoints :如果为 True ,模型检查点将作为工件上传到 Wandb。默认为 False 。
    # save_checkpoints :如果为 True ,模型检查点将保存到本地。默认为 False 。
    # upload_timeout :上传检查点到 Wandb 的超时时间(秒)。默认为 1800 秒(30 分钟)。
    # **kwargs :这些关键字参数将传递给 wandb.init() 。
    # 以下是 WandbLoggerCallback 类中常用的方法 :
    # __init__ :初始化 WandbLoggerCallback 对象,设置属性。
    # log :记录训练过程中的指标。这个方法在每个训练周期结束时自动调用,将指标发送到 Wandb 平台。
    # on_trial_start :在每个试验开始时调用,初始化 Wandb 实验。
    # on_trial_result :在每个试验的每个周期结束时调用,记录当前周期的指标。
    # on_trial_complete :在每个试验完成时调用,保存试验的最终结果。
    # on_trial_error :在每个试验出现错误时调用,记录错误信息。

    # 定义回调函数。
    # WandbLoggerCallback :如果 wandb 已安装且可用,使用 WandbLoggerCallback 将训练过程中的信息记录到Wandb项目 "YOLOv8-tune" 中。这有助于实时监控和可视化训练过程。
    # 条件判断 :如果 wandb 未安装或不可用, tuner_callbacks 将为空列表,表示不使用任何回调函数。
    tuner_callbacks = [WandbLoggerCallback(project="YOLOv8-tune")] if wandb else []
    # 这段代码通过定义训练函数、调度器和回调函数,为超参数调整过程做好了准备。使用 trainable_with_resources 将训练函数 _tune 与指定的资源(CPU和GPU)绑定。使用 ASHAScheduler 定义一个调度器,用于提前终止表现不佳的试验,节省计算资源。根据 wandb 的可用性,定义回调函数 WandbLoggerCallback ,用于将训练信息记录到Wandb项目中。这种设计确保了超参数调整过程高效且有条不紊地进行,同时提供了实时监控和可视化的能力。

    # 这段代码用于创建一个 Ray Tune 超参数搜索调谐器( tuner ),它将负责执行超参数调整任务。
    # Create the Ray Tune hyperparameter search tuner
    # 调用 get_save_dir 函数,传入默认配置 DEFAULT_CFG 和名称 "tune" ,获取保存目录的路径。这个函数确保返回的路径是绝对路径。 .resolve() :将路径转换为绝对路径。
    # def get_save_dir(args, name=None): -> 根据训练、验证或预测的参数返回一个保存目录( save_dir )。这个函数处理了多种情况,确保保存目录的路径是唯一且有效的。返回生成的保存目录路径,确保返回值是一个 Path 对象。 -> return Path(save_dir)
    tune_dir = get_save_dir(DEFAULT_CFG, name="tune").resolve()  # must be absolute dir
    # 创建保存目录,如果目录已存在则不抛出异常。 parents=True 表示创建所有必要的父目录, exist_ok=True 表示如果目录已存在则不抛出异常。
    tune_dir.mkdir(parents=True, exist_ok=True)

    # tune.Tuner(trainable, param_space=None, tune_config=None, run_config=None, **tuner_kwargs)
    # tune.Tuner() 是 Ray Tune 中用于启动和执行超参数调优作业的主要类。
    # 参数说明 :
    # trainable :这是要调优的可训练对象,可以是字符串、可调用函数、 Trainable 类型、 BaseTrainer 实例,或者是 None。这个参数定义了要优化的目标函数或模型。
    # param_space :这是超参数搜索空间,可以是字典、搜索算法对象或者是 None。这个参数定义了超参数调优的范围和分布。
    # tune_config :这是调优算法特定的配置,类型为 TuneConfig 。这个参数定义了调优过程中的算法配置,如试验次数、调度器等。
    # run_config :这是针对个别试验的运行时配置,类型为 RunConfig  。这个参数定义了每个试验的运行配置,如资源需求、存储路径等。
    # 返回值 :
    # 返回一个 Tuner 对象,该对象可以用于执行超参数调优作业,并获取调优结果。
    # tune.Tuner() 是 Ray Tune 中最核心的接口之一,它提供了一个简洁而强大的方法来执行超参数调优。通过配置 param_space 和 tune_config ,用户可以灵活地定义搜索空间和调优策略,以优化机器学习模型的性能。
    # Tuner 对象是 Ray Tune 中用于启动和管理超参数调优作业的核心组件。以下是 Tuner 对象的主要方法 :
    #  __init__ :构造函数,用于配置和构造一个调优作业。 
    # 参数包括 trainable (可训练对象), param_space (超参数搜索空间), tune_config (调优算法特定的配置), run_config (针对个别试验的运行时配置)等。
    # fit() :
    # 执行超参数调优作业,并返回结果。这个方法会根据配置的搜索空间、调度器和其他设置来运行调优过程,并返回一个包含调优结果的 ResultGrid 对象。
    # get_results() :
    # 获取超参数调优作业的结果。这个方法返回一个 ResultGrid 对象,其中包含了所有试验的结果,可以用于后续分析。
    # restore() :
    # 恢复之前失败的调优作业。通过提供之前调优作业的实验路径和可训练对象,可以恢复调优作业,继续之前的工作。
    # can_restore() :
    # 检查给定目录是否包含可恢复的 Ray Tune 实验。这个方法用于确定是否可以通过 restore 方法恢复调优作业。
    # 这些方法是 Tuner 对象的主要接口,提供了启动、管理和恢复超参数调优作业的能力。通过这些方法,用户可以灵活地执行调优作业,并根据需要获取和分析调优结果。

    # 创建 Ray Tune 调谐器。
    tuner = tune.Tuner(
        # 这是之前定义的训练函数,已经绑定了所需的资源(CPU和GPU)。
        trainable_with_resources,
        # 传入超参数搜索空间 space ,这个字典定义了超参数的取值范围。
        param_space=space,

        # tune.TuneConfig( metric=None, mode=None, search_alg=None, scheduler=None, num_samples=1, max_concurrent_trials=None, time_budget_s=None, reuse_actors=False, trial_name_creator=None, trial_dirname_creator=None, chdir_to_trial_dir=False,)
        # tune.TuneConfig() 是 Ray Tune 中的一个配置类,用于设置调优作业的特定参数。
        # 参数说明 :
        # metric :要优化的指标名称,该指标应该通过 tune.report() 报告。如果设置,将被传递给搜索算法和调度器。
        # mode :优化模式,必须是 min 或 max 之一。确定优化目标是最小化还是最大化指标。如果设置,将被传递给搜索算法和调度器。
        # search_alg :用于优化的搜索算法。默认为随机搜索。
        # scheduler :用于执行试验的调度器。可以选择 FIFO、MedianStopping、AsyncHyperBand、HyperBand 和 PopulationBasedTraining 等。更多选项可以参考 ray.tune.schedulers 。
        # num_samples :从超参数空间中采样的次数。默认为 1。如果提供了 grid_search ,则网格将重复 num_samples 次。如果设置为 -1,则在满足停止条件之前(虚拟地)无限生成样本。
        # max_concurrent_trials :同时运行的最大试验数。必须是非负数。如果为 None 或 0,则不限制并发试验数。
        # time_budget_s :全局时间预算,单位为秒,超过此时间后将停止调优作业。
        # reuse_actors :是否重用 actor 。默认为 False。
        # trial_name_creator :创建试验名称的回调函数。
        # trial_dirname_creator :创建试验目录名称的回调函数。
        # chdir_to_trial_dir :(已弃用)是否在试验运行前切换到试验目录。
        # tune.TuneConfig() 提供了丰富的配置选项,允许用户根据具体需求定制调优作业的行为。通过合理配置这些参数,可以更有效地进行超参数优化。

        # scheduler=asha_scheduler :使用之前定义的 ASHA 调度器 asha_scheduler ,用于提前终止表现不佳的试验。 num_samples=max_samples :指定最大试验次数 max_samples ,即要运行的试验数量。
        tune_config=tune.TuneConfig(scheduler=asha_scheduler, num_samples=max_samples),

        # RunConfig(name=None, local_dir=None, stop=None, checkpoint_config=None, storage_path=None, fail_fast=False, keep_checkpoints_num=None, synchronous_stop=False, verbose=False, experiment_name=None, trial_name_creator=None, trial_dirname_creator=None, chdir_to_trial_dir=False, callbacks=None,)
        # RunConfig 类是 Ray Tune 提供的一个配置类,用于定义训练运行的各种参数。这些参数包括资源分配、回调函数、日志记录、检查点保存等。
        # 参数说明 :
        # name :实验的名称,默认与 trainable 同名,用于保存结果时生成相应的文件夹。
        # local_dir :存储地址,默认为 ~/ray_results ,搜索结果的存储地址。
        # stop :终止条件,可以是一个字典,指定基于性能指标停止训练的条件,如 {"loss": 0.1, "training_iteration": 100} 。
        # checkpoint_config :检查点配置,用于设置检查点的保存策略。
        # storage_path :实验结果的存储路径,必须是绝对路径。
        # fail_fast :是否快速失败,如果设置为 True ,则在出现异常时立即停止所有试验。
        # keep_checkpoints_num :保留检查点的数量。
        # synchronous_stop :是否同步停止,如果设置为 True ,则在停止条件满足时同步停止所有试验。
        # verbose :是否为详细模式,如果设置为 True ,则输出更多的调试信息。
        # experiment_name :实验的名称,用于组织和查找实验结果。
        # trial_name_creator :创建试验名称的回调函数。
        # trial_dirname_creator :创建试验目录名称的回调函数。
        # chdir_to_trial_dir :是否在试验运行前切换到试验目录。
        # callbacks :回调函数列表,用于在试验的生命周期中执行自定义逻辑。
        # RunConfig 提供了丰富的配置选项,允许用户根据具体需求定制每个试验的运行参数,包括存储路径、终止条件和检查点策略等。通过合理配置这些参数,可以更有效地管理和分析超参数调优过程。

        # callbacks=tuner_callbacks :传入回调函数列表 tuner_callbacks ,如果 wandb 可用,则包含 WandbLoggerCallback 。 storage_path=tune_dir :指定保存试验结果的目录 tune_dir 。
        run_config=RunConfig(callbacks=tuner_callbacks, storage_path=tune_dir),
    )
    # 这段代码通过创建一个 Ray Tune 调谐器,准备好了超参数调整的所有必要组件。创建保存试验结果的目录 tune_dir ,确保目录存在。创建一个 Ray Tune 调谐器 tuner ,传入训练函数、超参数搜索空间、调度器配置和运行配置。调谐器将负责执行超参数调整任务,根据指定的搜索空间和调度器策略,运行多个试验,并记录试验结果。这种设计确保了超参数调整过程高效且有条不紊地进行,同时提供了实时监控和可视化的能力。通过合理配置参数,可以灵活地控制超参数调整的过程,满足不同的实验需求。

    # 这段代码用于启动超参数调整过程,并返回调整结果。
    # Run the hyperparameter search    运行超参数搜索。
    # 调用   tuner   对象的   fit   方法,启动超参数调整过程。这个方法会根据之前定义的配置(包括训练函数、超参数搜索空间、调度器和回调函数)运行多个试验,自动调整超参数,寻找最优的模型配置。
    tuner.fit()

    # Return the results of the hyperparameter search    返回超参数搜索的结果。
    # 调用 tuner 对象的 get_results 方法,获取超参数调整的结果。这个方法返回一个 ResultGrid 对象,其中包含了所有试验的结果,包括每个试验的超参数配置、最终指标、检查点等信息。
    return tuner.get_results()
    # 这段代码通过启动超参数调整过程并返回调整结果,完成了整个超参数调整的流程。使用 tuner.fit() 启动超参数调整过程,运行多个试验,自动调整超参数。使用 tuner.get_results() 获取超参数调整的结果,返回一个 ResultGrid 对象,包含所有试验的详细信息。这种设计确保了超参数调整过程高效且有条不紊地进行,同时提供了丰富的结果信息,方便用户分析和选择最优的模型配置。通过合理配置参数,可以灵活地控制超参数调整的过程,满足不同的实验需求。
# run_ray_tune 函数通过结合Ray Tune的高效超参数调整能力和Ultralytics YOLO11模型的灵活性,为用户提供了自动化的超参数优化流程。该函数首先确保必要的库已安装并导入,然后定义了一个训练函数,该函数从Ray的分布式存储中获取模型,重置回调函数,更新训练参数,并启动训练过程。接着,函数配置了超参数搜索空间、ASHA调度器和Wandb回调函数,创建了保存目录,并启动了Ray Tune调谐器。调谐器根据定义的配置运行多个试验,自动调整超参数,寻找最优的模型配置。最后,函数返回超参数调整的结果,包含所有试验的详细信息,帮助用户分析和选择最优的模型配置。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

红色的山茶花

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值