使用Scikit-learn构建一个完整分类任务流程
Scikit-learn 非常适合构建传统机器学习任务。它提供了数据切分、特征预处理、模型训练、交叉验证和指标评估等工具。对于表格数据分类任务,先用 Scikit-learn 做一个完整 baseline,通常比直接上复杂深度学习模型更稳。
本文通过一个二分类任务,演示从数据读取到模型保存的完整流程。
准备数据
假设数据文件 churn.csv 用于预测用户是否流失,字段包括年龄、消费金额、登录次数、城市、设备类型和标签:
1 | import pandas as pd |
分离特征和标签:
1 | target = "is_churn" |
如果标签缺失,应该先清理:
1 | mask = y.notna() |
划分训练集和测试集
分类任务建议使用分层切分,保持标签比例:
1 | from sklearn.model_selection import train_test_split |
random_state 保证结果可复现。测试集只用于最终评估,不应该参与调参。
区分数值和类别特征
数值特征和类别特征通常需要不同处理:
1 | numeric_features = ["age", "amount", "login_count"] |
实际项目中可以根据 df.dtypes 自动识别,但手动列出更可控,尤其是某些 ID 字段虽然是数字,但不应该按连续数值处理。
构建预处理流程
使用 ColumnTransformer 分别处理不同特征:
1 | from sklearn.compose import ColumnTransformer |
handle_unknown="ignore" 很重要。线上或测试集中可能出现训练集没有见过的新城市、新设备,如果不忽略会直接报错。
训练模型
以逻辑回归为例:
1 | from sklearn.linear_model import LogisticRegression |
把预处理和模型放在同一个 Pipeline 中,可以避免训练和预测时特征处理不一致,也方便保存整体模型。
class_weight="balanced" 适合类别不均衡的初始 baseline,但最终是否保留要根据验证指标决定。
评估模型
预测:
1 | y_pred = model.predict(X_test) |
输出指标:
1 | from sklearn.metrics import classification_report, confusion_matrix |
如果业务更关注流失用户召回率,就重点观察正类 recall。如果更担心误伤正常用户,就重点观察 precision。
对于支持概率输出的模型,可以调整阈值:
1 | y_proba = model.predict_proba(X_test)[:, 1] |
阈值不是固定必须 0.5,应该根据业务成本选择。
交叉验证
为了评估模型稳定性,可以使用交叉验证:
1 | from sklearn.model_selection import cross_val_score |
如果不同折之间分数差异很大,说明数据分布不稳定、样本量不足或特征存在问题。
保存模型
使用 joblib 保存整个 Pipeline:
1 | import joblib |
加载并预测:
1 | loaded_model = joblib.load("churn_model.joblib") |
保存整个 Pipeline 的好处是预处理步骤也一起保存,部署时不需要重新手写编码和标准化逻辑。
常见问题
训练报错 “could not convert string to float” 通常说明类别特征没有编码。
测试集报错未知类别,通常是 OneHotEncoder 没有设置 handle_unknown="ignore"。
指标很好但上线很差,可能是数据泄漏。例如使用了未来信息、标签派生字段,或者训练测试切分方式不符合真实业务时间顺序。
类别严重不均衡时,不要只看 accuracy,应关注 precision、recall、F1 和 PR 曲线。
小结
Scikit-learn 的 Pipeline 和 ColumnTransformer 可以把数据预处理和模型训练串成一个可复现流程。完整分类任务应包含数据清理、分层切分、特征预处理、模型训练、指标评估、阈值选择和模型保存。这个流程可以作为大多数表格分类任务的 baseline。







