Spec-Zone.ru › scikit-learn

Примечание

Перейти в конец, чтобы скачать полный код примера или запустить этот пример в браузере через JupyterLite или Binder.

Многометочная классификация с использованием цепочки классификаторов

В этом примере показано, как использовать ClassifierChain для решения задачи многометочной классификации.

Самый простой способ решения такой задачи — независимо обучить бинарный классификатор для каждой метки (т. е. для каждого столбца целевой переменной). Во время предсказания ансамбль бинарных классификаторов используется для формирования многозадачного предсказания.

Этот подход не позволяет моделировать взаимосвязи между различными задачами. ClassifierChain — это метаоцениватель (т. е. оцениватель, использующий внутренний оцениватель), реализующий более совершенный подход. Ансамбль бинарных классификаторов образует цепочку, в которой предсказание одного классификатора используется как признак при обучении следующего классификатора для новой метки. Таким образом, эти дополнительные признаки позволяют каждой цепочке учитывать корреляции между метками.

Оценка сходства Жаккара для цепочки, как правило, выше, чем для набора независимых базовых моделей.

# Authors: The scikit-learn developers
# SPDX-License-Identifier: BSD-3-Clause

Загрузка набора данных

В этом примере мы используем набор данных yeast, содержащий 2 417 точек данных, каждая из которых имеет 103 признака и 14 возможных меток. Каждая точка данных имеет как минимум одну метку. В качестве базового подхода сначала обучим логистический регрессионный классификатор для каждой из 14 меток. Чтобы оценить производительность этих классификаторов, сделаем предсказания на отложенной тестовой выборке и вычислим сходство Жаккара для каждого образца.

import matplotlib.pyplot as plt
import numpy as np

from sklearn.datasets import fetch_openml
from sklearn.model_selection import train_test_split

# Load a multi-label dataset from https://www.openml.org/d/40597
X, Y = fetch_openml("yeast", version=4, return_X_y=True)
Y = Y == "TRUE"
X_train, X_test, Y_train, Y_test = train_test_split(X, Y, test_size=0.2, random_state=0)

Обучение моделей

Обучим LogisticRegression, обернутый в OneVsRestClassifier, а также ансамбль из нескольких экземпляров ClassifierChain.

LogisticRegression в оболочке OneVsRestClassifier

Поскольку по умолчанию LogisticRegression не может работать с данными, имеющими несколько целевых переменных, необходимо использовать OneVsRestClassifier. После обучения модели вычислим сходство Жаккара.

from sklearn.linear_model import LogisticRegression
from sklearn.metrics import jaccard_score
from sklearn.multiclass import OneVsRestClassifier

base_lr = LogisticRegression()
ovr = OneVsRestClassifier(base_lr)
ovr.fit(X_train, Y_train)
Y_pred_ovr = ovr.predict(X_test)
ovr_jaccard_score = jaccard_score(Y_test, Y_pred_ovr, average="samples")

Цепочка бинарных классификаторов

Поскольку модели в каждой цепочке расположены случайным образом, производительность цепочек существенно различается. Вероятно, существует оптимальный порядок классов в цепочке, который обеспечит наилучший результат. Однако заранее нам этот порядок неизвестен. Вместо этого можно построить голосующий ансамбль цепочек классификаторов, усреднив бинарные предсказания цепочек и применив порог 0,5. Оценка сходства Жаккара для ансамбля выше, чем для независимых моделей, и, как правило, превышает оценку каждой цепочки в ансамбле (хотя для цепочек со случайным порядком это не гарантируется).

from sklearn.multioutput import ClassifierChain

chains = [ClassifierChain(base_lr, order="random", random_state=i) for i in range(10)]
for chain in chains:
    chain.fit(X_train, Y_train)

Y_pred_chains = np.array([chain.predict_proba(X_test) for chain in chains])
chain_jaccard_scores = [
    jaccard_score(Y_test, Y_pred_chain >= 0.5, average="samples")
    for Y_pred_chain in Y_pred_chains
]

Y_pred_ensemble = Y_pred_chains.mean(axis=0)
ensemble_jaccard_score = jaccard_score(
    Y_test, Y_pred_ensemble >= 0.5, average="samples"
)

Построение графика результатов

Построим график оценок сходства Жаккара для независимой модели, каждой цепочки и ансамбля (обратите внимание, что вертикальная ось графика начинается не с 0).

model_scores = [ovr_jaccard_score] + chain_jaccard_scores + [ensemble_jaccard_score]

model_names = (
    "Independent",
    "Chain 1",
    "Chain 2",
    "Chain 3",
    "Chain 4",
    "Chain 5",
    "Chain 6",
    "Chain 7",
    "Chain 8",
    "Chain 9",
    "Chain 10",
    "Ensemble",
)

x_pos = np.arange(len(model_names))

fig, ax = plt.subplots(figsize=(7, 4))
ax.grid(True)
ax.set_title("Classifier Chain Ensemble Performance Comparison")
ax.set_xticks(x_pos)
ax.set_xticklabels(model_names, rotation="vertical")
ax.set_ylabel("Jaccard Similarity Score")
ax.set_ylim([min(model_scores) * 0.9, max(model_scores) * 1.1])
colors = ["r"] + ["b"] * len(chain_jaccard_scores) + ["g"]
ax.bar(x_pos, model_scores, alpha=0.5, color=colors)
plt.tight_layout()
plt.show()
Classifier Chain Ensemble Performance Comparison

Интерпретация результатов

Из этого графика можно сделать три основных вывода:

  • Независимая модель в оболочке OneVsRestClassifier работает хуже ансамбля цепочек классификаторов и некоторых отдельных цепочек. Это связано с тем, что логистическая регрессия не моделирует взаимосвязи между метками.
  • ClassifierChain учитывает корреляции между метками, но из-за случайного порядка меток может дать результат хуже, чем независимая модель.
  • Ансамбль цепочек работает лучше, поскольку не только выявляет взаимосвязи между метками, но и не делает строгих предположений об их правильном порядке.

Общее время выполнения скрипта: (0 минут 2.411 секунды)

Launch binder
Launch JupyterLite

Download Jupyter notebook: plot_classifier_chain_yeast.ipynb

Download Python source code: plot_classifier_chain_yeast.py

Download zipped: plot_classifier_chain_yeast.zip

Связанные примеры

Обзор метаоценивателей для обучения многоклассовых моделей

Статистическое сравнение моделей с помощью поиска по сетке

Преобразование признаков с помощью ансамблей деревьев

Основные нововведения scikit-learn 0.22

© 2007–2026 The scikit-learn developers
Licensed under the 3-clause BSD License.
https://scikit-learn.org/1.9/auto_examples/multioutput/plot_classifier_chain_yeast.html

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API