(Стратифицированный) KFold против train_test_split — какие обучающие данные используются?

#python #train-test-split #k-fold

#python #поезд-тест-сплит #k-кратный

Вопрос:

Я всего лишь новичок в ML и пытаюсь понять, в чем именно преимущество (стратифицированного) KFold перед классическим train_test_split.

Классический train_test_split использует ровно одну часть для обучения (в данном случае 75%) и одну часть для тестирования (в данном случае 25%). Здесь я точно знаю, какие точки данных используются для обучения и тестирования (см. Код)

При разделении с помощью (стратифицированного) Kfold мы используем 4 разделения, в результате чего у нас получается 4 разных обучающих / тестовых части. Для меня неясно, какая из 4 частей будет использоваться для обучения / тестирования логистической регрессии. Имеет ли смысл устанавливать это разделение таким образом? Насколько я понял, преимущество (стратифицированного) Kfold заключается в том, что вы можете использовать все данные для обучения. Как мне нужно изменить код для достижения этой цели?

Создание данных

 import pandas as pd
import numpy as np
target = np.ones(25)
target[-5:] = 0
df = pd.DataFrame({'col_a':np.random.random(25),
                  'target':target})
df
  

train_test_split

 
from sklearn.model_selection import train_test_split

X = df.col_a
y = df.target

X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.25, shuffle=True)
print("TRAIN:", X_train.index, "TEST:", X_test.index)

Output:
TRAIN: Int64Index([1, 13, 8, 9, 21, 12, 10, 4, 20, 19, 7, 5, 15, 22, 24, 17, 11, 23], dtype='int64')
TEST: Int64Index([2, 6, 16, 0, 14, 3, 18], dtype='int64')
  

Стратифицированный KFold

 from sklearn.model_selection import StratifiedKFold

X = df.col_a
y = df.target

skf = StratifiedKFold(n_splits=4)
for train_index, test_index in skf.split(X, y):
        X_train, X_test = X.loc[train_index], X.loc[test_index]
        y_train, y_test = y.loc[train_index], y.loc[test_index]
        print("TRAIN:", train_index, "TEST:", test_index)

Output: 
TRAIN: [ 5  6  7  8  9 10 11 12 13 14 15 16 17 18 19 22 23 24] TEST: [ 0  1  2  3  4 20 21]
TRAIN: [ 0  1  2  3  4 10 11 12 13 14 15 16 17 18 19 20 21 23 24] TEST: [ 5  6  7  8  9 22]
TRAIN: [ 0  1  2  3  4  5  6  7  8  9 15 16 17 18 19 20 21 22 24] TEST: [10 11 12 13 14 23]
TRAIN: [ 0  1  2  3  4  5  6  7  8  9 10 11 12 13 14 20 21 22 23] TEST: [15 16 17 18 19 24]
  

Использование логистической регрессии

 from sklearn.linear_model import LogisticRegression

X_train = X_train.reshape(-1, 1)
X_test = X_test.reshape(-1, 1)

clf = LogisticRegression()

clf.fit(X_train, y_train)
clf.predict(X_test)
  

Ответ №1:

Начнем с того, что они оба делают то же самое, но то, как они это делают, имеет значение.

Тест-разделение поезда:

Test-train split случайным образом разбивает данные на тестовые и обучающие наборы. Нет никаких правил, кроме процентного разделения.

У вас будет только одна обучающая информация для обучения и одна тестовая информация для тестирования модели.

K-кратный:

Данные случайным образом разбиваются на несколько комбинаций тестовых и обучающих данных. Единственным правилом здесь является количество комбинаций.

Проблема с разделением данных случайным образом может привести к искажению представления класса — т. Е. Один или несколько целевых классов представлены в тестовом / обучающем разделении больше, чем другие. Это может привести к смещению в обучении модели.

Чтобы предотвратить это, тестовые и обучающие разбиения должны иметь одинаковые пропорции целевых классов. Этого можно достичь с помощью StratifiedKFold .

Ссылка: https://scikit-learn.org/stable/modules/generated/sklearn.model_selection .StratifiedKFold.html#:~:text=Stratified K-Folds cross-validator Provides train/test indices to split,preserving the percentage of samples for each class.

Если вам нравится смотреть видео (смотреть с ~ 4.30): https://youtu.be/gJo0uNL-5Qw

Примечание: если вы пытаетесь улучшить обучение с помощью kfold, то может помочь объединение StratifiedKFold с GridSearchCV .

Ответ №2:

у train_test_split есть вызываемый параметр stratify . Выбор его в отношении меток гарантирует, что у вас будет равное представление классов как в обучающих, так и в тестовых данных. Согласно документации

Если нет, данные разделяются стратифицированным образом, используя это в качестве меток классов.