Scikit-learn机器学习详解
Scikit-learn机器学习详解
Scikit-learn是Python中最流行的机器学习库,提供了统一的API接口和丰富的算法实现。
Scikit-learn基础
数据集加载
from sklearn.datasets import load_iris, load_digits, make_classification
from sklearn.model_selection import train_test_split
import pandas as pd
import numpy as np
# 加载内置数据集
iris = load_iris()
X, y = iris.data, iris.target
print(f"数据集形状: {X.shape}")
print(f"特征名称: {iris.feature_names}")
print(f"目标名称: {iris.target_names}")
print(f"类别分布: {np.bincount(y)}")
# 转换为DataFrame
df = pd.DataFrame(X, columns=iris.feature_names)
df['target'] = y
print("\n数据前5行:")
print(df.head())
生成数据集
# 生成分类数据
X_cls, y_cls = make_classification(
n_samples=1000,
n_features=10,
n_informative=5,
n_redundant=2,
n_classes=2,
random_state=42
)
print(f"生成的分类数据形状: {X_cls.shape}")
print(f"类别分布: {np.bincount(y_cls)}")
数据预处理
特征缩放
from sklearn.preprocessing import StandardScaler, MinMaxScaler, RobustScaler
# 创建示例数据
np.random.seed(42)
X = np.random.rand(100, 4) * 100
# 标准化
scaler_standard = StandardScaler()
X_standard = scaler_standard.fit_transform(X)
# 归一化
scaler_minmax = MinMaxScaler()
X_minmax = scaler_minmax.fit_transform(X)
# 鲁棒缩放
scaler_robust = RobustScaler()
X_robust = scaler_robust.fit_transform(X)
print("特征缩放效果比较:")
print(f"原始数据 - 均值: {X.mean(axis=0)[:2]}, 标准差: {X.std(axis=0)[:2]}")
print(f"标准化 - 均值: {X_standard.mean(axis=0)[:2]}, 标准差: {X_standard.std(axis=0)[:2]}")
print(f"归一化 - 最小值: {X_minmax.min(axis=0)[:2]}, 最大值: {X_minmax.max(axis=0)[:2]}")
编码处理
from sklearn.preprocessing import LabelEncoder, OneHotEncoder
# 标签编码
le = LabelEncoder()
y_encoded = le.fit_transform(['猫', '狗', '鸟', '猫', '狗'])
print(f"标签编码: {y_encoded}")
print(f"编码映射: {dict(zip(le.classes_, le.transform(le.classes_)))}")
# 独热编码
ohe = OneHotEncoder(sparse_output=False)
categories = [['猫'], ['狗'], ['鸟'], ['猫'], ['狗']]
y_onehot = ohe.fit_transform(categories)
print(f"\n独热编码形状: {y_onehot.shape}")
print(f"独热编码结果:\n{y_onehot}")
分类算法
逻辑回归
from sklearn.linear_model import LogisticRegression
from sklearn.metrics import accuracy_score, classification_report
# 加载数据
X, y = load_iris(return_X_y=True)
X_train, X_test, y_train, y_test = train_test_split(
X, y, test_size=0.2, random_state=42
)
# 逻辑回归
log_reg = LogisticRegression(max_iter=200, random_state=42)
log_reg.fit(X_train, y_train)
# 预测
y_pred = log_reg.predict(X_test)
accuracy = accuracy_score(y_test, y_pred)
print(f"逻辑回归准确率: {accuracy:.4f}")
print("\n分类报告:")
print(classification_report(y_test, y_pred))
随机森林
from sklearn.ensemble import RandomForestClassifier
# 随机森林
rf = RandomForestClassifier(n_estimators=100, random_state=42)
rf.fit(X_train, y_train)
# 预测
y_pred_rf = rf.predict(X_test)
accuracy_rf = accuracy_score(y_test, y_pred_rf)
print(f"随机森林准确率: {accuracy_rf:.4f}")
# 特征重要性
feature_importance = rf.feature_importances_
print("\n特征重要性:")
for i, importance in enumerate(feature_importance):
print(f"特征{i}: {importance:.4f}")
支持向量机
from sklearn.svm import SVC
# 支持向量机
svm = SVC(kernel='rbf', random_state=42)
svm.fit(X_train, y_train)
# 预测
y_pred_svm = svm.predict(X_test)
accuracy_svm = accuracy_score(y_test, y_pred_svm)
print(f"SVM准确率: {accuracy_svm:.4f}")
回归算法
线性回归
from sklearn.linear_model import LinearRegression
from sklearn.metrics import mean_squared_error, r2_score
from sklearn.datasets import make_regression
# 生成回归数据
X_reg, y_reg = make_regression(n_samples=100, n_features=5, noise=0.1, random_state=42)
X_reg_train, X_reg_test, y_reg_train, y_reg_test = train_test_split(
X_reg, y_reg, test_size=0.2, random_state=42
)
# 线性回归
lr = LinearRegression()
lr.fit(X_reg_train, y_reg_train)
# 预测
y_reg_pred = lr.predict(X_reg_test)
# 评估
mse = mean_squared_error(y_reg_test, y_reg_pred)
r2 = r2_score(y_reg_test, y_reg_pred)
print(f"线性回归 MSE: {mse:.4f}")
print(f"线性回归 R²: {r2:.4f}")
梯度提升
from sklearn.ensemble import GradientBoostingRegressor
# 梯度提升回归
gb = GradientBoostingRegressor(n_estimators=100, random_state=42)
gb.fit(X_reg_train, y_reg_train)
# 预测
y_reg_pred_gb = gb.predict(X_reg_test)
# 评估
mse_gb = mean_squared_error(y_reg_test, y_reg_pred_gb)
r2_gb = r2_score(y_reg_test, y_reg_pred_gb)
print(f"梯度提升 MSE: {mse_gb:.4f}")
print(f"梯度提升 R²: {r2_gb:.4f}")
模型评估
交叉验证
from sklearn.model_selection import cross_val_score, cross_validate
# 交叉验证
cv_scores = cross_val_score(rf, X, y, cv=5, scoring='accuracy')
print(f"交叉验证准确率: {cv_scores.mean():.4f} (+/- {cv_scores.std()*2:.4f})")
# 多指标交叉验证
scoring = ['accuracy', 'precision_macro', 'recall_macro', 'f1_macro']
cv_results = cross_validate(rf, X, y, cv=5, scoring=scoring)
print("\n多指标交叉验证结果:")
for metric in scoring:
scores = cv_results[f'test_{metric}']
print(f"{metric}: {scores.mean():.4f} (+/- {scores.std()*2:.4f})")
超参数调优
from sklearn.model_selection import GridSearchCV, RandomizedSearchCV
# 网格搜索
param_grid = {
'n_estimators': [50, 100, 200],
'max_depth': [3, 5, 10, None],
'min_samples_split': [2, 5, 10]
}
grid_search = GridSearchCV(
RandomForestClassifier(random_state=42),
param_grid,
cv=5,
scoring='accuracy',
n_jobs=-1,
verbose=1
)
grid_search.fit(X_train, y_train)
print(f"最佳参数: {grid_search.best_params_}")
print(f"最佳交叉验证准确率: {grid_search.best_score_:.4f}")
模型持久化
保存和加载模型
import joblib
from sklearn.pipeline import Pipeline
from sklearn.preprocessing import StandardScaler
# 创建管道
pipeline = Pipeline([
('scaler', StandardScaler()),
('classifier', RandomForestClassifier(n_estimators=100, random_state=42))
])
# 训练管道
pipeline.fit(X_train, y_train)
# 保存模型
joblib.dump(pipeline, 'model_pipeline.pkl')
print("模型已保存")
# 加载模型
loaded_pipeline = joblib.load('model_pipeline.pkl')
y_pred_loaded = loaded_pipeline.predict(X_test)
print(f"加载模型的准确率: {accuracy_score(y_test, y_pred_loaded):.4f}")
完整机器学习流程
from sklearn.pipeline import Pipeline
from sklearn.compose import ColumnTransformer
from sklearn.preprocessing import StandardScaler, OneHotEncoder
from sklearn.impute import SimpleImputer
# 创建完整管道
full_pipeline = Pipeline([
('preprocessor', ColumnTransformer([
('num', Pipeline([
('imputer', SimpleImputer(strategy='median')),
('scaler', StandardScaler())
]), [0, 1, 2, 3]), # 数值特征索引
('cat', Pipeline([
('imputer', SimpleImputer(strategy='constant', fill_value='missing')),
('onehot', OneHotEncoder(handle_unknown='ignore'))
]), []) # 分类特征索引
])),
('classifier', RandomForestClassifier(n_estimators=100, random_state=42))
])
# 训练
full_pipeline.fit(X_train, y_train)
# 评估
y_pred_full = full_pipeline.predict(X_test)
print(f"完整管道准确率: {accuracy_score(y_test, y_pred_full):.4f}")
最佳实践
- 数据预处理:始终对数据进行预处理
- 模型选择:根据问题类型选择合适的算法
- 交叉验证:使用交叉验证评估模型性能
- 超参数调优:使用网格搜索或随机搜索优化参数
- 模型持久化:保存训练好的模型以便复用
Scikit-learn是机器学习入门和实践的最佳工具,掌握Scikit-learn可以快速构建各种机器学习应用。