跳到内容

表格数据分类

这是训练二元分类模型的完整示例。

这些交互式笔记本遵循本示例的步骤

  • Ludwig CLI: Adult Census Income Classification with Ludwig CLI
  • Ludwig Python API: Adult Census Income Classification with Ludwig API

下载 Adult Census Income 数据集

Adult Census Income 是 1994 年人口普查数据的摘录,用于预测个人年收入是否超过 5 万美元。该数据集包含超过 4.9 万条记录,具有 14 个属性,并包含缺失数据。

ludwig datasets download adult_census_income

此命令将在当前目录下创建一个名为 adult_census_income.csv 的数据集文件。

数据集中的列为

描述
age 数值变量,年龄
workclass 类别变量,工作类型
fnlwgt 数值变量,无定义
education 类别变量,教育程度
education-num 数值变量,无定义
marital-status 类别变量,婚姻状况
occupation 类别变量,职业
relationship 类别变量,与家庭关系
race 类别变量,种族
sex 类别变量,性别
capital-gain 数值变量,无定义
capital-loss 数值变量,无定义
hours-per-week 数值变量,每周工作小时数
native-country 类别变量,原籍国
income 二元变量," <=50K" 或 " >50K"
split 数值变量,指示数据分割:训练集(0),测试集(2)

训练

Ludwig 配置文件描述了机器学习任务。有大量的选项可以控制学习过程。本示例只涵盖了其中的一小部分选项。只描述了本示例中使用的选项。有关所有详细信息,请参阅配置部分

首先,defaults 部分定义了全局预处理选项。所有数值特征都进行 z-score 标准化,即中心化到均值为 0 并按标准差缩放。数值缺失值用非缺失值的均值填充。

input_features 部分描述了每个预测变量,即输入变量的列名和类型:数值类别

'combiner' 部分定义了如何组合输入特征以传递给输出解码器。本示例使用concat 组合器,它简单地将输入特征编码器的输出连接起来。组合后的数据通过一个三层的全连接网络,每层有 128 个单元,并使用 dropout 正则化。

接下来定义 output_features。在本示例中,有一个响应变量 income。这是一个二元特征,有两个可能的值:" <=50K" 或 " >50K"。由于这些值不是传统的二元值(例如 "True" 和 "False"),因此指定了一个特征特定的预处理选项,以指示哪个字符串(" >50K")被解释为 "True"。为此输出特征指定了一个四层的全连接解码器,每层有 32 个单元。

此配置文件的最后一部分描述了 trainer 的操作选项。在本示例中,trainer 将处理训练数据 10 个周期。优化器类型是 "adam"。

defaults:
  number:
    preprocessing:
      normalization: zscore
      missing_value_strategy: fill_with_mean

input_features:
  - name: age
    type: number
  - name: workclass
    type: category
  - name: fnlwgt
    type: number
  - name: education
    type: category
  - name: education-num
    type: number
  - name: marital-status
    type: category
  - name: occupation
    type: category
  - name: relationship
    type: category
  - name: race
    type: category
  - name: sex
    type: category
  - name: capital-gain
    type: number
  - name: capital-loss
    type: number
  - name: hours-per-week
    type: number
  - name: native-country
    type: category

combiner:
  type: concat
  num_fc_layers: 3
  output_size: 128
  dropout: 0.2

output_features:
  - name: income
    type: binary
    preprocessing:
      fallback_true_label: " >50K"
    decoder:
        num_fc_layers: 4
        output_size: 32

trainer:
  epochs: 10
  optimizer:
    type: adam

LudwigModel

# create Ludwig configuration dictionary
# define model configuration
config = {'combiner': {'dropout': 0.2,
              'num_fc_layers': 3,
              'output_size': 128,
              'type': 'concat'},
 'input_features': [{'name': 'age', 'type': 'number'},
                    {'name': 'workclass', 'type': 'category'},
                    {'name': 'fnlwgt', 'type': 'number'},
                    {'name': 'education', 'type': 'category'},
                    {'name': 'education-num', 'type': 'number'},
                    {'name': 'marital-status', 'type': 'category'},
                    {'name': 'occupation', 'type': 'category'},
                    {'name': 'relationship', 'type': 'category'},
                    {'name': 'race', 'type': 'category'},
                    {'name': 'sex', 'type': 'category'},
                    {'name': 'capital-gain', 'type': 'number'},
                    {'name': 'capital-loss', 'type': 'number'},
                    {'name': 'hours-per-week', 'type': 'number'},
                    {'name': 'native-country', 'type': 'category'}],
 'output_features': [{'name': 'income',
                      'decoder': {
                            'num_fc_layers': 4,
                            'output_size': 32
                      },
                      'preprocessing': {'fallback_true_label': ' >50K'},
                      'loss': {'type': 'binary_weighted_cross_entropy'},
                      'type': 'binary'}],
 'defaults': {
    'number': {
      'preprocessing': {
        'missing_value_strategy': 'fill_with_mean',
        'normalization': 'zscore'
      }
    }
 }
 'trainer': {'epochs': 10, 'optimizer': {'type': 'adam'}}}

# instantiate Ludwig model object
model = LudwigModel(config=config, logging_level=logging.INFO)

训练模型。

ludwig train 命令

ludwig train \
  --dataset adult_census_income.csv \
  --config config.yaml

train() 方法

# Trains the model. This cell might take a few minutes.
train_stats, preprocessed_data, output_directory = model.train(training_set=train_df,
                                                               test_set=test_df)

评估

ludwig evaluate 命令

ludwig evaluate --model_path results/experiment_run/model \
                 --dataset evaluation_dataset.csv \
                 --output_directory test_results

evaluate() 方法

# Generates predictions and performance statistics for the test set.
test_stats, predictions, output_directory = model.evaluate(
  eval_df,
  collect_predictions=True,
  collect_overall_stats=True,
  skip_save_eval_stats=False,
  skip_save_predictions=False,
  output_directory="test_results",
  return_type="dict"
)

可视化指标

ROC 曲线

ludwig visualize roc_curves 命令

!ludwig visualize --visualization roc_curves \
                  --ground_truth evaluation_dataset.csv \
                  --ground_truth_metadata results/experiment_run/model/training_set_metadata.json \
                  --probabilities test_results/predictions.parquet \
                  --output_feature_name income \
                  --output_directory visualizations \
                  --model_names "Adult Census Income Model" \
                  --file_format png

visualize.roc_curves() 函数

from ludwig.visualize import roc_curves

roc_curves(
    [predictions['income']['probabilities']],
    eval_df['income'],
    preprocessed_data[-1],
    'income',
    '1',
    model_names=["Adult Census Income"],
    output_directory='visualization',
    file_format='png'
)

ROC Curve

二元阈值指标

ludwig visualize binary_threshole_vs_metric 命令

ludwig visualize --visualization binary_threshold_vs_metric \
                  --ground_truth evaluation_dataset.csv \
                  --ground_truth_metadata results/experiment_run/model/training_set_metadata.json \
                  --probabilities test_results/predictions.parquet \
                  --output_feature_name income \
                  --positive_label 1 \
                  --output_directory visualizations \
                  --model_names "Adult Census Income Model" \
                  --metrics accuracy precision recall f1\
                  --file_format png

visualize.binary_threshold_vs_metric() 函数

from ludwig.visualize import binary_threshold_vs_metric

binary_threshold_vs_metric(
    [predictions["income"]["probabilities"]],
    eval_df["income"],
    preprocessed_data[-1],
    "income",
    ["accuracy", "precision", "recall", "f1"],
    1,
    model_names=["Adult Census Income"],
    output_directory="visualization",
    file_format="png",
)
准确率指标

accuracy

精确率指标

precision

召回率指标

recall

F1 指标

accuracy

预测

ludwig predict 命令

ludwig predict --model_path results/experiment_run/model \
                --dataset evaluation_dataset.csv \
                --output_directory predictions

predict() 方法

predictions, prediction_results = model.predict(dataset=eval_df, skip_save_predictions=False, output_directory="predictions_results")

样本预测 sample_predictions