Машинное обучение с помощью Python в научных вычислениях: от теории к коду
Основы машинного обучения с Python: реализация и выбор алгоритмов
Какое решение является наиболее эффективным для старта задачи классификации с табличными данными?
В большинстве случаев рекомендуется использовать ансамблевый алгоритм RandomForestClassifier из библиотеки scikit-learn. Он устойчив к переобучению, работает с пропусками (при соответствующей настройке) и не требует сложной предобработки. Ниже приведён типовой пайплайн.
from sklearn.ensemble import RandomForestClassifier
from sklearn.model_selection import train_test_split
from sklearn.preprocessing import StandardScaler
from sklearn.metrics import classification_report, confusion_matrix
import pandas as pd
# Загрузка данных (например, Iris)
data = pd.read_csv('iris.csv')
X = data.drop('species', axis=1)
y = data['species']
# Разделение на обучающую и тестовую выборки
X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.2, random_state=42)
# Стандартизация (для RandomForest не обязательна, но полезна для некоторых метрик)
scaler = StandardScaler()
X_train_scaled = scaler.fit_transform(X_train)
X_test_scaled = scaler.transform(X_test)
# Обучение модели
model = RandomForestClassifier(n_estimators=100, max_depth=5, random_state=42)
model.fit(X_train_scaled, y_train)
# Оценка
y_pred = model.predict(X_test_scaled)
print(confusion_matrix(y_test, y_pred))
print(classification_report(y_test, y_pred))
машинное обучение с помощью python (машинное обучение)
Какие проблемы могут возникнуть при использовании RandomForest?
- Переобучение при слишком глубоких деревьях. Решение: ограничить
max_depthилиmin_samples_leaf. - Дисбаланс классов. Решение: установить
class_weight='balanced'или использовать SMOTE перед обучением. - Долгое обучение на больших наборах данных. Решение: уменьшить
n_estimatorsили использоватьn_jobs=-1для параллелизации.
Какой алгоритм выбрать для бинарной классификации с линейно разделимыми данными?
Логистическая регрессия (LogisticRegression) - простой и интерпретируемый метод. Он хорошо работает, когда признаки независимы и нет сложных взаимодействий.
from sklearn.linear_model import LogisticRegression
model_log = LogisticRegression(max_iter=1000, penalty='l2', C=1.0)
model_log.fit(X_train_scaled, y_train)
print('Accuracy:', model_log.score(X_test_scaled, y_test))
модуль numpy в python (модуль numpy в python)
Почему логистическая регрессия может давать низкое качество?
- Мультиколлинеарность признаков. Решение: применить регуляризацию (L1 или L2) или удалить коррелированные признаки.
- Несбалансированные классы. Решение: использовать
class_weight='balanced'.
Как обработать нелинейные зависимости в данных?
Метод опорных векторов (SVC) с ядром RBF способен строить нелинейные границы. Перед использованием обязательно выполняется стандартизация.
from sklearn.svm import SVC
model_svm = SVC(kernel='rbf', C=1.0, gamma='scale', probability=True)
model_svm.fit(X_train_scaled, y_train)
print('Accuracy:', model_svm.score(X_test_scaled, y_test))
Какие типичные ошибки встречаются при работе с SVM?
- Неправильное масштабирование признаков. Решение: всегда применять
StandardScalerилиMinMaxScaler. - Выбор гиперпараметров
Cиgammaнаугад. Решение: использоватьGridSearchCVс перекрёстной проверкой.
Как классифицировать данные, когда границы классов имеют сложную форму?
Метод k-ближайших соседей (KNeighborsClassifier) не делает предположений о распределении данных, но чувствителен к масштабу и выбросам.
from sklearn.neighbors import KNeighborsClassifier
model_knn = KNeighborsClassifier(n_neighbors=5, metric='euclidean')
model_knn.fit(X_train_scaled, y_train)
print('Accuracy:', model_knn.score(X_test_scaled, y_test))
Почему KNN может работать плохо?
- Разные масштабы признаков. Решение: применить стандартизацию.
- Неверно выбранное число соседей
k. Решение: подобрать через перекрёстную проверку. - Высокая размерность (проклятие размерности). Решение: использовать методы понижения размерности (PCA, t-SNE).
Расширенные примеры: настройка и оценка моделей
Пример 1. Подбор гиперпараметров с помощью GridSearchCV
from sklearn.model_selection import GridSearchCV
from sklearn.ensemble import RandomForestClassifier
param_grid = {
'n_estimators': [50, 100, 200],
'max_depth': [None, 10, 20],
'min_samples_split': [2, 5, 10]
}
grid = GridSearchCV(RandomForestClassifier(random_state=42), param_grid, cv=5, scoring='accuracy')
grid.fit(X_train, y_train)
print('Лучшие параметры:', grid.best_params_)
print('Точность на тесте:', grid.score(X_test, y_test))
Лучшие параметры: {'max_depth': 10, 'min_samples_split': 5, 'n_estimators': 100}
Точность на тесте: 0.9667
Пояснение: GridSearchCV перебирает все комбинации параметров и выбирает лучшую по средней точности на 5-кратной кросс-валидации.
Пример 2. Работа с категориальными признаками с помощью ColumnTransformer
from sklearn.compose import ColumnTransformer
from sklearn.preprocessing import OneHotEncoder, StandardScaler
from sklearn.pipeline import Pipeline
from sklearn.linear_model import LogisticRegression
import pandas as pd
# Предположим, что в данных есть категориальный признак 'color' и числовые 'height', 'weight'
df = pd.DataFrame({
'color': ['red', 'blue', 'green', 'red'],
'height': [150, 160, 155, 170],
'weight': [50, 60, 55, 65],
'target': [0, 1, 0, 1]
})
X = df.drop('target', axis=1)
y = df['target']
preprocessor = ColumnTransformer(
transformers=[
('num', StandardScaler(), ['height', 'weight']),
('cat', OneHotEncoder(drop='first'), ['color'])
]
)
pipeline = Pipeline([
('prep', preprocessor),
('clf', LogisticRegression(max_iter=1000))
])
pipeline.fit(X, y)
print('Коэффициенты модели:', pipeline.named_steps['clf'].coef_)
Коэффициенты модели: [[0.234 -0.567 1.234]]
Пояснение: ColumnTransformer позволяет применять разные преобразования к разным столбцам. Это удобно при работе со смешанными типами данных.
Пример 3. Визуализация кривых обучения
import matplotlib.pyplot as plt
from sklearn.model_selection import learning_curve
train_sizes, train_scores, test_scores = learning_curve(
RandomForestClassifier(n_estimators=50, random_state=42),
X_train, y_train,
cv=5,
train_sizes=np.linspace(0.1, 1.0, 5),
scoring='accuracy'
)
train_mean = np.mean(train_scores, axis=1)
test_mean = np.mean(test_scores, axis=1)
plt.plot(train_sizes, train_mean, 'o-', label='Обучение')
plt.plot(train_sizes, test_mean, 's-', label='Валидация')
plt.xlabel('Размер обучающей выборки')
plt.ylabel('Точность')
plt.legend(loc='best')
plt.title('Кривые обучения')
plt.show()
[График: две кривые, сходящиеся на уровне 0.95]
Пояснение: Кривые обучения помогают диагностировать переобучение (большой разрыв между кривыми) или недообучение (низкая точность на обеих кривых).
Пример 4. Балансировка классов с помощью SMOTE
from imblearn.over_sampling import SMOTE
from sklearn.model_selection import train_test_split
from sklearn.ensemble import RandomForestClassifier
X_train_bal, y_train_bal = SMOTE(random_state=42).fit_resample(X_train, y_train)
model = RandomForestClassifier(random_state=42)
model.fit(X_train_bal, y_train_bal)
print('Точность после SMOTE:', model.score(X_test, y_test))
Точность после SMOTE: 0.95
Пояснение: SMOTE создаёт синтетические примеры миноритарного класса, что улучшает качество на несбалансированных данных. Установка imbalanced-learn обязательна.