Skip to content

探索 PyTorch Tabular 的高级功能

前提条件:对深度学习有中级知识,对表格问题(如回归和分类)有基本知识。还请阅读使用PyTorch Tabular解决任何表格问题教程。
水平:中级

在_使用PyTorch Tabular解决任何表格问题_中,我们了解了如何使用PyTorch Tabular及其智能默认设置。在本教程中,我们将看到如何利用PyTorch Tabular稍微高级的特性,以获得更大的灵活性和通常更好的结果。在本教程中,我们假设您已经知道如何使用PyTorch Tabular的基本功能。如果您对PyTorch Tabular不熟悉,请先阅读_使用PyTorch Tabular解决任何表格问题_的教程。

from rich.pretty import pprint
import numpy as np

数据

首先,让我们创建一个合成数据,它是数值特征和分类特征的混合,并且有多个回归目标。这意味着我们需要预测多个列,并使用相同的特征集。大多数经典的机器学习模型(例如scikit-learn中的模型)只处理单一目标问题。我们将必须为每个目标训练不同的模型。虽然这样做完全可以,但它并不是最有效的方式。首先,我们将不得不训练多个模型,这将耗费更多时间。其次,如果两个目标之间存在某种关系,我们将无法利用这些信息。例如,如果我们预测的是房子的价格和房子的面积,我们知道这两个目标是相关的。如果我们训练两个不同的模型,就无法利用这一信息。

PyTorch Tabular可以直接处理多目标问题(目前仅适用于回归)。我们只需将目标列的列表传递给DataConfig类的target参数。

from sklearn.model_selection import train_test_split
from pytorch_tabular.utils import make_mixed_dataset, print_metrics
data, cat_col_names, num_col_names = make_mixed_dataset(
    task="regression", n_samples=100000, n_features=20, n_categories=4, n_targets=2, random_state=42
)
target_cols = ["target_0", "target_1"]
train, test = train_test_split(data, random_state=42)
train, val = train_test_split(train, random_state=42)

让我们从 PyTorch Tabular 中导入所需的类。

from pytorch_tabular import TabularModel
from pytorch_tabular.models import CategoryEmbeddingModelConfig, GANDALFConfig
from pytorch_tabular.config import DataConfig, OptimizerConfig, TrainerConfig
from pytorch_tabular.models.common.heads import LinearHeadConfig

定义模型

我们已经知道在PyTorch Tabular中定义模型的基本步骤。我们需要定义一些配置并初始化 TabularModel。让我们来做这个。

但这一次,我们来看看PyTorch Tabular的一些更高级的功能。

1. DataConfig

我们知道需要在 DataConfig 中定义目标、连续和分类列。但还有一些其他参数可以用来定制数据处理流程。让我们看看其中的一些。

  • normalize_continuous: 为了更好的优化,深度学习模型更喜欢归一化的连续特征。默认情况下,PyTorch Tabular会归一化连续特征。但如果你想使用自定义的归一化,可以在PyTorch Tabular外部进行归一化,并将 normalize_continuous=False 传递给 DataConfig。这样PyTorch Tabular将不会归一化连续特征,而是使用原始值。
  • continuous_feature_transform: 有时,我们希望在将连续特征输入模型之前对其进行转换。例如,我们可能想对某个特征取对数或取平方根等。PyTorch Tabular内置了一些这样的转换。您可以将转换的名称传递给 DataConfigcontinuous_feature_transform 参数。允许的输入有:['quantile_normal', 'yeo-johnson', 'quantile_uniform', 'box-cox']。这内部使用了一些scikit-learn的转换器来进行转换。您可以在这里了解这些信息。
  • num_workerspin_memory 是两个用于加速数据加载过程的参数。如果您使用GPU,可以将 num_workers 设置为大于0的数字(仅适用于Linux)。这将使用多个CPU核心并行加载数据。pin_memory 是一个用于加速数据从CPU到GPU传输的参数。如果您使用GPU,可以设置 pin_memory=True 来加速数据传输。您可以在这里了解更多信息。

有关所有参数的完整列表,请参阅文档中的API参考。

data_config = DataConfig(
    target=target_cols,
    continuous_cols=num_col_names,
    categorical_cols=cat_col_names,
    num_workers=10,
    normalize_continuous_features=True,
    continuous_feature_transform="quantile_normal",
)

2. TrainingConfig

训练深度学习模型可能会变得非常复杂。PyTorch Tabular 通过继承 PyTorch Lightning,将整个工作负载卸载到基础的 PyTorch Lightning 框架上。在基本教程中,我们只是触及了 PyTorch Lightning 可以做的事情。 在本教程中,我们将看看如何利用 PyTorch Lightning 的一些更高级的功能以及 PyTorch Tabular 的一些便捷功能。

我们已经知道可以将 max_epochsbatch_size 传递给 TrainerConfig。让我们看看更多的参数。

accelerator

PyTorch Lightning 支持在多个 GPU 和 TPU 上进行训练。您可以将加速器类型传递给 TrainerConfigaccelerator 参数。允许的输入为:['cpu','gpu','tpu','ipu','auto']cpu 允许您在 CPU 上训练模型。gpu 允许您在 GPU 上训练模型。tpu 允许您在 TPU 上训练模型。ipu 允许您在 IPU 上训练模型。auto 允许 PyTorch Lightning 为您选择最佳加速器。您可以在 这里 阅读更多关于这些内容的信息。

devicesdevices_list

devices 允许您选择用于训练模型的设备数量(CPU 核心、GPU 等)。-1 意味着在所有可用设备上训练。devices_list 允许您选择用于训练模型的特定设备。例如,如果您想在 GPU 0 和 1 上训练模型,可以传递 devices_list=[0,1]

min_epochsmax_time

这些也是可以帮助您控制训练的参数,除了 max_epochsmin_epochs 允许您指定训练模型的最小轮次(在使用早期停止时通常很有用)。max_time 允许您指定训练模型的最长时间。

Early Stopping Parameters

PyTorch Lightning 支持开箱即用的早期停止。早期停止是一种通过监控验证集上的损失/指标来停止训练过程的技术,以防止模型没有改善。 您可以将以下参数传递给 TrainerConfig 以使用早期停止: > early_stopping: 监控早期停止的损失/指标。如果设置为 None,将不使用早期停止。
> early_stopping_min_delta: 作为早期停止改进的最低损失/指标变化。
> early_stopping_mode: 应该优化的损失/指标方向。选择包括:['max', 'min']。
> early_stopping_patience: 直到损失/指标没有进一步改善的轮次。
> early_stopping_kwargs: 早期停止回调的额外关键字参数。有关更多详细信息,请参考 PyTorch Lightning EarlyStopping 回调文档。
> load_best: 如果为 True,训练结束时加载最佳模型权重。默认值为 True。

Checkpoint Saving Parameters

PyTorch Lightning 支持自动保存模型检查点。检查点保存是一种在训练过程中定期保存模型权重的技术。这在由于某种原因中断训练过程时非常有用,或者如果我们想回去使用之前轮次的权重。在使用早期停止时尤其有用,以便我们可以回滚并使用最佳模型权重。您可以将以下参数传递给 TrainerConfig 来保存模型检查点: > checkpoints: str: 需要监控的损失/指标以进行检查点。如果 None,则不会有检查点。
> checkpoints_path: str: 保存模型的路径。默认值为 saved_models
> checkpoints_mode: str: 应该优化的损失/指标方向。选择包括 maxmin。默认值为 min
> checkpoints_save_top_k: int: 要保存的最佳模型数量。如果您希望保存多个最佳模型,可以将此参数设置为 >1。默认值为 1

注意: 确保您要追踪的指标/损失的名称与日志中的名称完全匹配。推荐的方式是运行模型并通过评估模型检查结果。从结果字典中,您可以选择一个键在训练期间进行追踪。

Learning Rate Finder

首次在这篇论文 Cyclical Learning Rates for Training Neural Networks 中提出,后来被 fast.ai 推广,是一种在不进行代价高昂的搜索的情况下找到最佳学习率邻域的技术。PyTorch Tabular 允许您找到最佳学习率(使用论文中提出的方法)并自动将其用于训练网络。所有这些都可以通过一个简单的标志 auto_lr_find 来开启。

Controlling the Gradients/Optimization

在训练过程中,可能会出现需要更严格控制梯度优化过程的情况。例如,如果梯度爆炸,您可能希望在每次更新之前剪辑梯度值。gradient_clip_val 允许您这样做。

有时,您可能希望在向后传播之前在多个批次之间累积梯度(可能是因为较大的批次大小不适合您的 GPU)。PyTorch Tabular 允许您使用 accumulate_grad_batches 来做到这一点。

Debugging Analysis

很多时候,您需要调试模型并查看为什么它没有按预期工作。或者,甚至在开发新模型时,您需要频繁调试模型。PyTorch Lightning 为此用例提供了一些功能,PyTorch Tabular 也采用了这些功能。

为了找到性能瓶颈,我们可以使用:

  • profiler: 可选[str]: 在训练期间分析各个步骤并帮助识别瓶颈。选择包括:None simple advanced。默认值为 None

要检查整个设置是否没有错误,我们可以使用:

  • fast_dev_run: 可选[str]: 验证的快速调试运行。默认值为 False

如果模型学习不良:

  • overfit_batches: float: 使用训练集的这部分数据。如果不为零,将使用相同的训练集进行验证和测试。如果训练数据加载器的 shuffle=True,Lightning 会自动禁用它。适合快速调试或故意过拟合。默认值为 0

  • track_grad_norm: bool: 仅在设置实验跟踪时使用。在记录器中跟踪和记录梯度范数。默认值为 -1,表示不跟踪。1 表示 L1 范数,2 表示 L2 范数,等等。默认值为 False。如果梯度范数迅速降为零,则表示我们存在问题。

有关所有参数的完整列表,请参阅文档中的 API 参考。

YAML Config

PyTorch Tabular 允许您将任何配置定义为配置类或 YAML 文件。YAML 文件是存储配置的极好方式。它可读性强且易于编辑。PyTorch Tabular 允许您在 YAML 文件中定义配置,并将 YAML 文件的路径传递给 TabularModel 的相应配置参数。

我们为 TrainerConfig 定义了以下内容的 YAML 文件:

batch_size: 1024
fast_dev_run: false
max_epochs: 20
min_epochs: 1
accelerator: 'auto'
devices: -1
accumulate_grad_batches: 1
auto_lr_find: true
check_val_every_n_epoch: 1
gradient_clip_val: 0.0
overfit_batches: 0.0
profiler: null
early_stopping: null
early_stopping_min_delta: 0.001
early_stopping_mode: min
early_stopping_patience: 3
checkpoints: valid_loss
checkpoints_path: saved_models
checkpoints_mode: min
checkpoints_save_top_k: 1
load_best: true
track_grad_norm: -1

让我们使用它,而不是将 TrainerConfig 定义为一个类。

3. OptimizerConfig

优化器是梯度下降过程的核心,是训练一个良好模型所需的关键组件,而 OptimizerConfig 允许您根据需要自定义优化器和学习率调度器。Pytorch Tabular 默认使用 Adam 优化器,学习率为 1e-3。这主要是因为一个经验法则,为我们提供了一个良好的起点。

让我们看看一些可以用来定制优化器的参数。

optimizer

PyTorch Tabular 允许您通过将优化器的名称作为字符串传递给 OptimizerConfigoptimizer 参数,选择来自 torch.optim 包的任何优化器。这包括 AdamSGDRMSPropAdamW 等优化器。您可以在 这里 阅读更多关于这些优化器的信息。除此之外,PyTorch Tabular 还支持任何有效的 PyTorch 优化器。如果这是一个可以从命名空间访问的优化器(例如您安装的库),我们可以将优化器的全名传递给 optimizer 参数。例如,如果您安装了 torch_optimizer 库,并希望使用其中的 QHAdam,您可以将 torch_optimizer.QHAdam 传递给 optimizer 参数。如果这是一个无法从命名空间访问的优化器,您无法在 OptimizerConfig 中传递它,但可以在稍后看到的 fit 过程中使用它。

optimizer_params

PyTorch Tabular 允许您将任何有效的优化器参数(学习率除外)传递给 OptimizerConfigoptimizer_params 参数。例如,如果您想使用 1e-2 的权重衰减,您可以将 optimizer_params={'weight_decay':1e-2} 传递给 OptimizerConfig。您需要参考您使用的优化器的文档,以找出有效参数。

lr_scheduler

学习率调度器是一种在训练期间控制学习率的方法。有时,从略高的学习率开始并在训练过程中逐渐降低是有益的。有时,当我们在学习时遇到平台期时,降低学习率也是有帮助的。PyTorch Tabular 允许您通过将调度器的名称作为字符串传递给 OptimizerConfiglr_scheduler 参数,选择来自 torch.optim.lr_scheduler 包的任何学习率调度器。这包括 StepLRReduceLROnPlateauCosineAnnealingLR 等调度器。您可以在 这里 阅读更多关于这些调度器的信息。

lr_scheduler_params

PyTorch Tabular 允许您将任何有效的学习率调度器参数传递给 OptimizerConfiglr_scheduler_params 参数。例如,如果您想为 StepLR 使用一个步幅为 10,您可以将 lr_scheduler_params={'step_size':10} 传递给 OptimizerConfig。您需要参考您使用的调度器的文档,以找出有效参数。

lr_scheduler_monitor_metric

这是一个仅在您使用 ReduceLROnPlateau 作为学习率调度器时使用的参数。这是将被监控以降低学习率的指标。这应该是模型中定义的有效损失或指标。

在这里,让我们使用带有 10 个周期的热身的 CosineAnnealingLR 作为学习率调度器,并使用来自第三方库 torch_optimizer 的优化器(您需要安装该库)。

optimizer_config = OptimizerConfig(
    optimizer="torch_optimizer.QHAdam",
    optimizer_params={"nus": (0.7, 1.0), "betas": (0.95, 0.998)},
    lr_scheduler="CosineAnnealingWarmRestarts",
    lr_scheduler_params={"T_0": 10, "T_mult": 1, "eta_min": 1e-5},
)

4. ModelConfig

ModelConfig 是您决定在模型中使用的模型类型和模型参数的方式。PyTorch Tabular 实现了一些用于表格数据的最先进模型。在 PyTorch Tabular 内部,一个模型有三个组件:

  1. 嵌入层 - 这是模型的一部分,负责将分类特征和连续特征处理成一个单一的张量。
  2. 主干 - 这是模型的真实架构。它是模型的一部分,接受嵌入层的输出并对其进行表示学习。输出同样是一个单一的张量,即从表示学习中学到的特征。
  3. 头部 - 这是模型的一部分,接受主干的输出并进行最终的分类/回归。头部的输出是最终的预测结果。
from pytorch_tabular import available_models
pprint(available_models())
[
'AutoIntConfig',
'CategoryEmbeddingModelConfig',
'DANetConfig',
'FTTransformerConfig',
'GANDALFConfig',
'GatedAdditiveTreeEnsembleConfig',
'MDNConfig',
'NodeConfig',
'TabNetModelConfig',
'TabTransformerConfig'
]

您可以通过从 pytorch_tabular.models 导入相应的类来选择这些模型,设置参数并将其传递给 TabularModelmodel_config 参数。所有这些配置类都继承自一个共同的 ModelConfig,其中包含一些标准参数,任何特定于模型的参数都会添加到各自的配置类中。由于继承的关系,我们能够在所有模型配置类中访问 ModelConfig 的所有参数。

让我们首先看看 ModelConfig 的一些常见参数:

  • task: str: 这定义了我们是为了 回归分类 任务还是作为 主干 模型来运行该模型。主干 任务用于自监督模型和混合密度模型。

头部配置

  • head: 可选[str]: 要用于模型的头部。应该是 pytorch_tabular.models.common.heads 中定义的头之一。默认为 LinearHead。下面的单元格显示了可用头部的列表。
import pytorch_tabular as pt
pprint([h for h in dir(pt.models.common.heads) if (not h.startswith("_") and "Head" in h and "Config" not in h)])
['LinearHead', 'MixtureDensityHead']
  • head_config: 可选的[字典]: 作为字典的配置,定义头部。如果留空,将初始化为默认线性头。虽然输入是一个字典,但建议使用相应的<specific>HeadConfig类,以确保只使用允许的参数。例如,如果您使用的是LinearHead,可以使用LinearHeadConfig来定义头部配置。下面的单元格显示可用的头部配置列表。

pprint([h for h in dir(pt.models.common.heads) if (not h.startswith("_") and "Head" in h and "Config" in h)])
['LinearHeadConfig', 'MixtureDensityHeadConfig']

嵌入配置

  • embedding_dims: 可选[列表]: 每个分类列的嵌入维度,以元组 (基数, 嵌入维度) 的列表形式表示。如果留空,将使用分类列的基数推断,规则为 min(50, (x + 1) // 2)
  • embedding_dropout: 浮点数: 应用于分类嵌入的 dropout。默认值为 0.0
  • batch_norm_continuous_input: 布尔值: 如果为 True,我们将在将连续层与分类嵌入结合之前,先通过 BatchNorm 层对其进行归一化。默认值为 True

其他配置

  • learning_rate: 浮点数: 模型的学习率。默认值为 1e-3。

  • loss: 可选[字符串]: 要应用的损失函数。默认情况下,回归使用 MSELoss,分类使用 CrossEntropyLoss。在大多数情况下,这些表现良好。但如果你想使用 PyTorch 的其他损失函数,可以在此处传递。例如,如果你想使用 BCEWithLogitsLoss,可以传递 loss='BCEWithLogitsLoss'。你可以在 PyTorch 中阅读更多损失函数 这里。我们也可以使用自定义损失函数。稍后我们将看到如何做到这一点。

注意: 选择损失函数不应被视为一个盲目应用的超参数,而是一个经过深思熟虑的决定。
  • metrics: 可选[列表[字符串]]: 需要在训练过程中跟踪的指标列表。这些指标应为 torchmetrics 中实现的 功能性 指标之一。您可以在 这里 找到完整的列表。分类情况下默认是 accuracy ,回归情况下默认是 mean_squared_error 。我们也可以使用自定义指标。稍后我们将看到如何做到这一点。

  • metrics_prob_input: 可选[列表[布尔值]]: 这是分类指标中定义的必需参数。这定义了指标函数的输入是概率还是类别。长度应与指标的数量相同。默认值为 None。

  • metrics_params: 可选[列表]: 将传递给指标函数的参数。一些函数,例如 f1_score 需要额外的参数如 task 才能正确定义。这也让你选择如何在多类分类中平均该指标。

  • target_range: 可选[列表]: 对于分类问题,目标始终是 0 或 1,一旦我们进行独热编码。但对于回归,它理论上是一个 (-inf, inf) 之间的实值。更实际地说,它通常在已知的边界之间。有时,让模型学习这些边界会造成额外负担,而 target_range 则是减轻该负担的一种方式。这个技术由 Jeremy Howard 在 fast.ai 推广,并在实践中相当有效。如果我们知道回归的输出值应该在 minmax 值之间,我们可以将这些值作为元组提供给 target_range。但需要注意的是,假设目标的分布是正常的。如果分布不正常,可能无法如预期那样工作。在多目标的情况下,我们将 target_range 设置为一个元组的列表,每个列表项对应于 target 参数中的相应条目。对于分类问题,该参数将被忽略。

target_range = [(train[target].min() * 0.8, train[target].max() * 1.2)]
  • virtual_batch_size: 可选[整数]: BatchNorm 是一种非常有用的技术(必要的恶)来规范化网络的激活。它通常导致更快的收敛和稳定的训练过程。但在使用大批量进行训练时,BatchNorm 可能导致“过拟合”(不是传统意义上的)。克服这个问题的一种方法是使用 GhostBatchNorm,我们将批次拆分为虚拟批次,并对每个虚拟批次应用 BatchNorm。通过将 virtual_batch_size 设置为大于 1 的数字,PyTorch Tabular 将自动将所有 BatchNorm 转换为指定虚拟批次大小的 GhostBatchNorm。

  • seed: 整数: 用于再现性的种子。默认值为 42

现在,每个我们选择的模型都将有自己的一组参数。文档中的 API 参考列出了所有模型及其各自的参数。在这里,我们使用一个简单的带有分类嵌入的 MLP。这在 PyTorch Tabular 中称为 CategoryEmbeddingModelConfig

我们将使用的关键参数是:

  • layers: 字符串: 分类头中图层和单位的连字符分隔数。默认值为 "128-64-32"
  • activation: 字符串: 分类头中的激活类型。默认的 激活函数在 PyTorch 中 如 ReLU、TanH、LeakyReLU 等。默认值为 ReLU
  • initialization: 字符串: 线性层的初始化方案。选项包括: kaiming xavier random。默认值为 kaiming
  • use_batch_norm: 布尔值: 标志,用于在每个线性层+DropOut 后包括一个 BatchNorm 层。默认值为 False
  • dropout: 浮点数: 元素被归零的概率。适用于所有线性层。默认值为 0.0
head_config = LinearHeadConfig(
    layers="",  # 头部没有额外的层,只有一个映射层输出到output_dim。
    dropout=0.1,
    initialization="kaiming",
).__dict__  # 转换为字典以传递给模型配置(OmegaConf 不接受对象)

model_config = CategoryEmbeddingModelConfig(
    task="regression",
    layers="64-32-16",
    activation="LeakyReLU",
    dropout=0.1,
    initialization="kaiming",
    head="LinearHead",  # 线性磁头
    head_config=head_config,  # 线性磁头配置
    learning_rate=1e-3,
    target_range=[(float(train[col].min()),float(train[col].max())) for col in target_cols]
)

5. TabularModel

在定义了所有配置之后,我们需要将所有内容整合在一起,这就是TabularModel出现的地方。TabularModel是核心组件,负责协调和设置一切。

TabularModel解析配置并:

  1. 初始化模型
  2. 设置实验跟踪框架(如果定义了)
  3. 初始化并设置TabularDatamodule,该模块处理所有数据转换和DataLoader的准备
  4. 设置回调和Pytorch Lightning Trainer
  5. 使您能够进行训练、保存、加载、预测等操作

现在我们已经定义了所有配置,让我们用这些配置初始化TabularModel。我们可以将配置作为类或YAML文件传递。我们将对TrainerConfig使用YAML文件,将其他配置使用类。

除了配置之外,我们还可以将以下参数传递给TabularModel

  • verbose:布尔值:如果为True,在训练过程中将打印不同的消息以指示进度。默认值为True
  • suppress_lightning_logger:PyTorch Lightning在训练时会打印大量日志,此参数可以让您抑制这些日志。更具体地说,它将PyTorch Lightning logger的日志级别设置为ERROR。默认值为False,因为Pytorch Lightning的日志在调试时非常有用。只有在您确定不需要它们时才将其关闭。
from pytorch_tabular import TabularModel
tabular_model = TabularModel(
    data_config=data_config,
    model_config=model_config,
    optimizer_config=optimizer_config,
    trainer_config="trainer_config.yml",
    verbose=True,
    suppress_lightning_logger=False
)
2024-01-11 14:43:34,218 - {pytorch_tabular.tabular_model:140} - INFO - Experiment Tracking is turned off           

训练模型

在 PyTorch Tabular 中,有两种训练模型的方法 - 高级 API 和低级 API。高级 API 是对低级 API 的封装,推荐使用这种方法来训练模型。但低级 API 提供了更多的控制权,适用于需要进行自定义训练的场景。让我们来看看它们的区别。

1. 高级 API

高级 API 只需一行代码即可完成所有操作。您只需调用 TabularModelfit 方法,它会处理所有其他内容。但我们已经在基础教程中看到了如何拟合模型。因此,让我们来看一下 fit 方法的一些其他参数。

  • loss:这是您可以使用自定义损失函数的地方。您可以将任何有效的 PyTorch 损失函数传递给 fit 方法的 loss 参数。

  • metrics:这是您可以使用自定义指标函数的地方。该参数接受一个 Callable 的列表,签名为:metric_fn(y_hat, y),其中 y_haty 是张量。在分类任务中,y_hat 的形状为 (batch_size, num_classes),而在回归任务中为 (batch_size, 1)y 在分类任务中的形状为 (batch_size, 1),在回归任务中的形状为 (batch_size, num_targets)

  • metrics_prob_inputs:如果您正在使用 metrics 参数,则这是一个必需参数。它是一个布尔值列表,定义输入到指标函数的是概率还是类别。长度应与指标的数量相同。默认为 None。

  • optimizeroptimizer_params:这是您可以使用自定义优化器的地方。您可以将任何有效的 PyTorch 优化器传递给 fit 方法的 optimizer 参数。您还可以将任何有效的优化器参数传递给 fit 方法的 optimizer_params 参数。

  • train_samplers:有时,我们希望强制对批次采样施加一些自定义行为。该参数接受任何继承自 torch.utils.data.Sampler 的类。例如,如果您想使用 WeightedRandomSampler,可以传递 train_samplers=WeightedRandomSampler(...)。您可以在 这里 查看有关采样器的更多信息。

  • target_transform:此参数是一个包含两个 Callable 的元组,允许您对目标使用任何自定义转换。如果您希望在将目标传递给损失函数之前进行一些自定义转换,这将非常有用。例如,如果您希望对目标取对数,可以传递 target_transform=[np.log, np.exp]。第一个函数将在将目标传递给损失函数之前应用,第二个函数将在模型的输出上应用。

  • callbacks:PyTorch Lightning 默认支持许多回调。您可以在 这里 阅读更多信息。PyTorch Lightning 还支持自定义回调。这些回调直接添加到 Lightning Trainer。

  • cache_data - 默认情况下,PyTorch Tabular 会将数据保存在 TabularDataModule 中。如果您希望多次训练模型而无需一遍又一遍地加载数据,这非常有用。但是如果您内存不足,您可以选择将文件保存到路径并从中加载。该参数接受一个字符串,即数据将保存的路径。默认值为 memory

还有一些其他参数,但您可以在 API 参考中查看完整选项列表。

让我们利用这些自定义选项来训练模型。 我们使用了 - 虚拟目标转换 - 自定义损失函数,即均方误差损失。这将覆盖在 ModelConfig 中定义的损失函数。 - 自定义优化器,即 torch_optimizer 中的 Lamb(仅用于演示如何使用自定义优化器)。这将覆盖在 OptimizerConfig 中定义的优化器。 - 自定义指标函数,意义不大,但只是为了演示如何使用。它将覆盖在 ModelConfig 中定义的指标。 - 自定义回调,训练不同阶段时仅打印一些消息。

注意 PyTorch Tabular 将原始模型输出传递给损失函数。在分类问题中,原始输出是 logits。损失函数负责应用正确的激活。如果您不理解这意味着什么,请保持损失函数的默认值或使用预先实现的损失函数。
import torch
import torch.nn as nn
from pytorch_lightning.callbacks import DeviceStatsMonitor
from torch_optimizer import Lamb


class CustomLoss(nn.Module):
    def __init__(self):
        super(CustomLoss, self).__init__()

    def forward(self, inputs, targets):
        loss = torch.mean((inputs - targets) ** 2)
        return loss.mean()


def custom_metric(y_true, y_pred):
    return torch.mean(torch.pow(y_true - y_pred, 3))

CustomOptimizer = Lamb
# #自定义优化器示例
# class CustomOptimizer(Optimizer):
#     def __init__(
# 自我,
# 参数,
#         lr: float = 1e-3,
#         betas=(0.9, 0.999),
#         eps: 浮点数 = 1e-6,
#         weight_decay: 浮点数 = 0,
# clamp_value: float = 10,
# adam: bool = False,
#         debias: 布尔值 = False,
# (  ):
# # 这里有一些代码
# defaults = dict(lr=lr, betas=betas, eps=eps, weight_decay=weight_decay)
# super().__init__(params, defaults)

#     def step(self, closure=None):
# #这里有一些代码
# 返回损失


tabular_model.fit(
    train=train,
    validation=val,
    loss=CustomLoss(),
    metrics=[custom_metric],
    metrics_prob_inputs=[False],
    target_transform=[lambda x: x + 100, lambda x: x - 100],
    optimizer=CustomOptimizer,
    optimizer_params={"weight_decay": 1e-6},
    callbacks=[DeviceStatsMonitor()],
)
Seed set to 42

2024-01-11 14:43:34,615 - {pytorch_tabular.tabular_model:524} - INFO - Preparing the DataLoaders                   
2024-01-11 14:43:34,631 - {pytorch_tabular.tabular_datamodule:499} - INFO - Setting up the datamodule for          
regression task                                                                                                    
2024-01-11 14:43:34,893 - {pytorch_tabular.tabular_model:574} - INFO - Preparing the Model: CategoryEmbeddingModel 
2024-01-11 14:43:34,924 - {pytorch_tabular.tabular_model:340} - INFO - Preparing the Trainer                       
GPU available: True (cuda), used: True
TPU available: False, using: 0 TPU cores
IPU available: False, using: 0 IPUs
HPU available: False, using: 0 HPUs

2024-01-11 14:43:36,420 - {pytorch_tabular.tabular_model:630} - INFO - Auto LR Find Started                        
You are using a CUDA device ('NVIDIA GeForce RTX 3060 Laptop GPU') that has Tensor Cores. To properly utilize them, you should set `torch.set_float32_matmul_precision('medium' | 'high')` which will trade-off precision for performance. For more details, read https://pytorch.org/docs/stable/generated/torch.set_float32_matmul_precision.html#torch.set_float32_matmul_precision
/home/manujosephv/miniconda3/envs/lightning_upgrade/lib/python3.11/site-packages/pytorch_lightning/callbacks/model_checkpoint.py:639: Checkpoint directory saved_models exists and is not empty.
LOCAL_RANK: 0 - CUDA_VISIBLE_DEVICES: [0]

Finding best initial lr:   0%|          | 0/100 [00:00<?, ?it/s]
`Trainer.fit` stopped: `max_steps=100` reached.
Learning rate set to 0.04365158322401657
Restoring states from the checkpoint path at /home/manujosephv/pytorch_tabular/docs/tutorials/.lr_find_4764cd76-0064-458b-881a-e2772b684d4d.ckpt
Restored all states from the checkpoint at /home/manujosephv/pytorch_tabular/docs/tutorials/.lr_find_4764cd76-0064-458b-881a-e2772b684d4d.ckpt

2024-01-11 14:43:40,092 - {pytorch_tabular.tabular_model:643} - INFO - Suggested LR: 0.04365158322401657. For plot 
and detailed analysis, use `find_learning_rate` method.                                                            
2024-01-11 14:43:40,095 - {pytorch_tabular.tabular_model:652} - INFO - Training Started                            
LOCAL_RANK: 0 - CUDA_VISIBLE_DEVICES: [0]

┏━━━┳━━━━━━━━━━━━━━━━━━┳━━━━━━━━━━━━━━━━━━━━━━━━━━━┳━━━━━━━━┓
┃    Name              Type                       Params ┃
┡━━━╇━━━━━━━━━━━━━━━━━━╇━━━━━━━━━━━━━━━━━━━━━━━━━━━╇━━━━━━━━┩
│ 0 │ custom_loss      │ CustomLoss                │      0 │
│ 1 │ _backbone        │ CategoryEmbeddingBackbone │  4.5 K │
│ 2 │ _embedding_layer │ Embedding1dLayer          │     92 │
│ 3 │ head             │ LinearHead                │     34 │
└───┴──────────────────┴───────────────────────────┴────────┘
Trainable params: 4.6 K                                                                                            
Non-trainable params: 0                                                                                            
Total params: 4.6 K                                                                                                
Total estimated model params size (MB): 0                                                                          
Output()
`Trainer.fit` stopped: `max_epochs=20` reached.



2024-01-11 14:44:11,064 - {pytorch_tabular.tabular_model:663} - INFO - Training the model completed                
2024-01-11 14:44:11,065 - {pytorch_tabular.tabular_model:1487} - INFO - Loading the best model                     
<pytorch_lightning.trainer.trainer.Trainer at 0x7f693b5f0b90>

我们可以看到训练过程的日志(因为我们设置了 verbose=True),以及显示训练和验证损失/指标的进度条。此外,我们还可以观察到模型摘要已打印出来,关于硬件加速器(例如 GPU)可用性和使用情况的一些日志也被打印。这是因为我们没有设置 suppress_lightning_logger=True。如果我们设置这个选项,我们将看不到这些日志。

您可以通过使用 Python 的 warnings 模块进一步减少来自 PyTorch Lightning 的警告,但不推荐这样做,因为您可能会错过一些重要的警告。

import warnings
warnings.filterwarnings("ignore")

2. 低级 API

低级 API 更加灵活,使您能够编写更复杂的逻辑,例如交叉验证、集成等。低级 API 的代码更冗长,要求您编写更多代码,但它为用户提供了更多的控制。

fit 方法分为三个子方法:

  1. prepare_dataloader

  2. prepare_model

  3. train

我们在高级 API 中讨论的参数被传递给各自的子方法。在详细介绍每个方法之前,让我们重新初始化 TabularModel 并关闭日志。

tabular_model = TabularModel(
    data_config=data_config,
    model_config=model_config,
    optimizer_config=optimizer_config,
    trainer_config="trainer_config.yml",
    verbose=False, # 关闭详细模式以避免从不同阶段打印日志
    suppress_lightning_logger=True, # 将闪电日志级别更改为警告
)

1. prepare_dataloader

此方法负责设置 TabularDataModule 并返回该对象。您可以使用 save_dataloader 保存此对象,并在稍后使用 load_datamodule 加载它,以跳过数据准备步骤。这在进行交叉验证或集成时非常有用。

因此,像 trainvalidationtrain_samplertarget_transformcache_data 等参数会传递给此方法。

datamodule = tabular_model.prepare_dataloader(
                train=train, validation=val, seed=42, target_transform=[lambda x: x + 100, lambda x: x - 100],
            )

2. prepare_model

此方法负责设置和初始化模型,并以准备好的数据模块作为输入。它返回模型实例。

此方法接受 datamodule 作为输入,以及其他参数,如 lossmetricsmetrics_prob_inputsoptimizeroptimizer_params

from torch_optimizer import Lamb
model = tabular_model.prepare_model(
    datamodule,
    loss=CustomLoss(),
    metrics=[custom_metric],
    metrics_prob_inputs=[False],
    optimizer=Lamb,
    optimizer_params={"weight_decay": 1e-6},
)

3. 训练

此方法负责训练模型,接收准备好的数据模块和模型作为输入。它返回训练好的模型实例。

训练接收数据模块模型作为输入,以及其他参数如回调最大周期最小周期等。

tabular_model.train(
    model,
    datamodule,
    callbacks=[DeviceStatsMonitor()],
)
/home/manujosephv/miniconda3/envs/lightning_upgrade/lib/python3.11/site-packages/pytorch_lightning/callbacks/model_checkpoint.py:639: Checkpoint directory saved_models exists and is not empty.

Finding best initial lr:   0%|          | 0/100 [00:00<?, ?it/s]
┏━━━┳━━━━━━━━━━━━━━━━━━┳━━━━━━━━━━━━━━━━━━━━━━━━━━━┳━━━━━━━━┓
┃    Name              Type                       Params ┃
┡━━━╇━━━━━━━━━━━━━━━━━━╇━━━━━━━━━━━━━━━━━━━━━━━━━━━╇━━━━━━━━┩
│ 0 │ custom_loss      │ CustomLoss                │      0 │
│ 1 │ _backbone        │ CategoryEmbeddingBackbone │  4.5 K │
│ 2 │ _embedding_layer │ Embedding1dLayer          │     92 │
│ 3 │ head             │ LinearHead                │     34 │
└───┴──────────────────┴───────────────────────────┴────────┘
Trainable params: 4.6 K                                                                                            
Non-trainable params: 0                                                                                            
Total params: 4.6 K                                                                                                
Total estimated model params size (MB): 0                                                                          
Output()


<pytorch_lightning.trainer.trainer.Trainer at 0x7f6900d7da90>

在新数据上进行预测和评估

正如我们在基础教程中看到的,我们可以使用 TabularModelpredict 方法对新数据进行预测。但还有一些其他参数可以用于自定义预测过程。

  • progress_bar - 此参数允许您关闭或选择所需的进度条类型。如果为 rich,则使用彩色的 rich 进度条。如果为 tqdm,则使用 tqdm 显示进度条。“None”或 None 将关闭进度条。默认为 rich

  • ret_logits - 这是一个布尔标志,如果打开,将返回原始模型输出(logits),而不是概率。通常在分类问题中有用。默认为 False

prediction = tabular_model.predict(test, progress_bar=None)
prediction.head()
target_0_prediction target_1_prediction
75721 143.383545 128.671326
80184 57.778259 35.192749
19864 60.018860 82.361267
76699 -124.672058 -23.280823
92991 33.951477 102.290710

我们还看到可以使用evaluate在新数据上评估模型,使用现有的指标。但还有一些其他参数可以用来定制评估过程。

  • verbose - 一个标志,如果为True,将打印结果并返回它们。默认为True
  • ckpt_path - 如果提供,将从检查点路径加载模型并在数据上评估。如果未提供,将使用当前模型在数据上进行评估。如果启用了模型检查点功能,我们还可以使用best自动加载最佳模型。默认为None
# 当前模式
result = tabular_model.evaluate(test, verbose=False)
Output()


# 从存储的检查点路径加载
best_ckpt_path = tabular_model.trainer.checkpoint_callback.best_model_path
result = tabular_model.evaluate(test, verbose=True, ckpt_path=best_ckpt_path)
Output()
┏━━━━━━━━━━━━━━━━━━━━━━━━━━━┳━━━━━━━━━━━━━━━━━━━━━━━━━━━┓
┃        Test metric               DataLoader 0        ┃
┡━━━━━━━━━━━━━━━━━━━━━━━━━━━╇━━━━━━━━━━━━━━━━━━━━━━━━━━━┩
│    test_custom_metric          54.31338882446289     │
│   test_custom_metric_0        -47.28584289550781     │
│   test_custom_metric_1        101.59922790527344     │
│         test_loss               53.098876953125      │
│        test_loss_0             24.37938117980957     │
│        test_loss_1            28.719507217407227     │
└───────────────────────────┴───────────────────────────┘


# 使用训练中的最佳检查点
result = tabular_model.evaluate(test, verbose=True, ckpt_path="best")
Output()
┏━━━━━━━━━━━━━━━━━━━━━━━━━━━┳━━━━━━━━━━━━━━━━━━━━━━━━━━━┓
┃        Test metric               DataLoader 0        ┃
┡━━━━━━━━━━━━━━━━━━━━━━━━━━━╇━━━━━━━━━━━━━━━━━━━━━━━━━━━┩
│    test_custom_metric          54.31338882446289     │
│   test_custom_metric_0        -47.28584289550781     │
│   test_custom_metric_1        101.59922790527344     │
│         test_loss               53.098876953125      │
│        test_loss_0             24.37938117980957     │
│        test_loss_1            28.719507217407227     │
└───────────────────────────┴───────────────────────────┘


恭喜!: 你已经学会了如何使用 PyTorch Tabular 的大部分高级功能。
现在尝试在你自己的项目和 Kaggle 竞赛中使用这些功能。如果你有任何问题,请随时在 GitHub 讨论区 中提问。