42 lines
4.3 KiB
JSON
42 lines
4.3 KiB
JSON
|
|
{
|
|||
|
|
"id": 1,
|
|||
|
|
"title": "Стратифицированный split и масштабирование без data leakage",
|
|||
|
|
"difficulty": "hard",
|
|||
|
|
"topic_tags": {
|
|||
|
|
"Classification": 0.4,
|
|||
|
|
"DataPreprocessing": 0.4,
|
|||
|
|
"ModelSelection": 0.2
|
|||
|
|
},
|
|||
|
|
"task_context": "В учебном пайплайне для бинарной классификации нужно подготовить данные перед обучением модели. Текущая реализация допускает утечку данных: она обучает `StandardScaler` на всей выборке до разбиения на train и test, а затем делает разбиение без стратификации. Нужно сначала выполнить `train_test_split` с `test_size=0.2`, `random_state=42`, `stratify=y`, затем обучить `StandardScaler` только на `X_train`, преобразовать `X_train` и `X_test` и вернуть масштабированные выборки вместе с метками и обученным scaler.",
|
|||
|
|
"tests": [
|
|||
|
|
"import numpy as np",
|
|||
|
|
"X = [[1.0, 10.0], [2.0, 20.0], [3.0, 30.0], [4.0, 40.0], [5.0, 50.0], [6.0, 60.0], [7.0, 70.0], [8.0, 80.0], [9.0, 90.0], [10.0, 100.0]]",
|
|||
|
|
"y = [0, 0, 0, 0, 0, 1, 1, 1, 1, 1]",
|
|||
|
|
"X_train_scaled, X_test_scaled, y_train, y_test, scaler = split_and_scale_binary_data(X, y)",
|
|||
|
|
"assert y_train == [1, 0, 0, 0, 1, 1, 1, 0]",
|
|||
|
|
"assert y_test == [0, 1]",
|
|||
|
|
"assert X_train_scaled.shape == (8, 2)",
|
|||
|
|
"assert X_test_scaled.shape == (2, 2)",
|
|||
|
|
"assert np.allclose(scaler.mean_, [5.125, 51.25])",
|
|||
|
|
"assert np.allclose(scaler.scale_, [2.7128168017763383, 27.128168017763382])",
|
|||
|
|
"assert np.allclose(X_train_scaled.mean(axis=0), [0.0, 0.0], atol=1e-12)",
|
|||
|
|
"assert np.allclose(X_test_scaled, [[-0.4146981098256822, -0.4146981098256823], [1.7970251425779564, 1.7970251425779564]])"
|
|||
|
|
],
|
|||
|
|
"expected_output": "Функция должна вернуть кортеж `(X_train_scaled, X_test_scaled, y_train, y_test, scaler)`, где scaler обучен только на тренировочной части, а разбиение выполнено стратифицированно.",
|
|||
|
|
"input_example": "Пример входа: `X = [[1.0, 10.0], [2.0, 20.0], [3.0, 30.0], [4.0, 40.0], [5.0, 50.0], [6.0, 60.0], [7.0, 70.0], [8.0, 80.0], [9.0, 90.0], [10.0, 100.0]]`, `y = [0, 0, 0, 0, 0, 1, 1, 1, 1, 1]`.",
|
|||
|
|
"output_example": "Пример ожидаемого возврата: `y_train = [1, 0, 0, 0, 1, 1, 1, 0]`, `y_test = [0, 1]`, `scaler.mean_ = [5.125, 51.25]`, `scaler.scale_ = [2.7128168017763383, 27.128168017763382]`, `X_test_scaled = [[-0.4146981098256822, -0.4146981098256823], [1.7970251425779564, 1.7970251425779564]]`.",
|
|||
|
|
"requirements": [
|
|||
|
|
"Сначала выполнить стратифицированное разбиение данных на train и test.",
|
|||
|
|
"Обучить `StandardScaler` только на `X_train`.",
|
|||
|
|
"Преобразовать и `X_train`, и `X_test` одним и тем же scaler.",
|
|||
|
|
"Вернуть результат в порядке `X_train_scaled, X_test_scaled, y_train, y_test, scaler`."
|
|||
|
|
],
|
|||
|
|
"constraints": [
|
|||
|
|
"Не менять имя функции `split_and_scale_binary_data`.",
|
|||
|
|
"Не изменять входные `X` и `y` на месте.",
|
|||
|
|
"Не обучать scaler на всей выборке до split.",
|
|||
|
|
"Нельзя хардкодить значения из примеров входа и выхода."
|
|||
|
|
],
|
|||
|
|
"broken_code": "from sklearn.model_selection import train_test_split\\nfrom sklearn.preprocessing import StandardScaler\\n\\n\\ndef split_and_scale_binary_data(X, y):\\n scaler = StandardScaler()\\n X_scaled = scaler.fit_transform(X) # ВОТ ТУТ НУЖНО ИСПРАВИТЬ КОД: scaler нельзя обучать на всей выборке до split\\n X_train, X_test, y_train, y_test = train_test_split(X_scaled, y, test_size=0.2, random_state=42) # ВОТ ТУТ НУЖНО ИСПРАВИТЬ КОД: нужен stratify=y и split должен быть до масштабирования\\n return X_train, X_test, y_train, y_test, scaler"
|
|||
|
|
}
|