@(Aaron) [机器学习, 特征工程]
主要内容包括:
- 数据理解
- 数据清洗:
- 特征构造:
- 特征选择:
- 类别不平衡
文章目录
绝大多数标准数据集都假设已经拥有一个干净的[n_samples, n_features] 特征矩阵。其实在现实工作中,数据很少会这么干净。因此,机器学习实践中更重要的步骤之一是特征工程(Feature Engineering)——将数据转换为能更好地表示潜在问题的特征,从而提高机器学习性能。
1 数据理解
探索数据,了解数据,主要在 EDA 阶段完成。只有对数据有充分的认识和理解,才能借助特征工程实现更好的算法。
1.1 数字特征
- 定距:可以加减——温度、日期
- 定比:可以乘除——价格、重量
可以进行如下分析:
相关性分析
查看几个特征得 偏度和峰值
每个数字特征得分布可视化
数字特征相互之间的关系可视化
多变量互相回归关系可视化
1.2 类别特征
- 定类:按名称分类——血型、城市
- 定序:有序分类——成绩(A B C)
可查看:
unique分布
类别特征箱形图可视化
类别特征的小提琴图可视化
类别特征的柱形图可视化类别
特征的每个类别频数可视化(count_plot)
2 数据清洗
- 目的:提高数据质量,降低算法用错误数据建模的风险。
2.1 特征变换
- 目的:解决模型无法处理或不适合处理的情况
主要情况有:
- 定性变量编码:Label Encoder;Onehot Encoder;Distribution coding;
- 标准化和归一化:z分数标准化(标准正太分布)、min-max 归一化;
一种常见的非数值数据类型是分类数据。例如,浏览房屋数据的时候,除了看到“房价”(price)和“面积”(rooms)之类的数值特征,还会有“地点”(neighborhood)信息,数据可能像这样:
{'price': 850000, 'rooms': 4, 'neighborhood': 'Queen Anne'},
{'price': 700000, 'rooms': 3, 'neighborhood': 'Fremont'},
{'price': 650000, 'rooms': 3, 'neighborhood': 'Wallingford'},
{'price': 600000, 'rooms': 2, 'neighborhood': 'Fremont'}
你可能会把分类特征用映射关系编码成整数:
{'Queen Anne': 1, 'Fremont': 2, 'Wallingford': 3};
但是,在Scikit-Learn 中这么做并不是一个好办法:这个程序包的所有模块都有一个基本假设,那就是数值特征可以反映代数量(algebraic quantities)。因此,这样映射编码可能会让人觉得存在Queen Anne < Fremont < Wallingford,甚至还有Wallingford - Queen Anne =Fremont,这显然是没有意义的。
面对这种情况,常用的解决方法是独热编码。它可以有效增加额外的列,让0 和1 出现在对应的列分别表示每个分类值有或无。当你的数据是像上面那样的字典列表时,用Scikit-Learn 的DictVectorizer 类就可以实现:
from sklearn.feature_extraction import DictVectorizer
vec = DictVectorizer(sparse=False, dtype=int)
vec.fit_transform(data)
array([[ 0, 1, 0, 850000, 4],
[ 1, 0, 0, 700000, 3],
[ 0, 0, 1, 650000, 3],
[ 1, 0, 0, 600000, 2]], dtype=int64)
你会发现,neighborhood 字段转换成三列来表示三个地点标签,每一行中用1 所在的列对应一个地点。当这些分类特征编码之后,你就可以和之前一样拟合Scikit-Learn 模型了。
但这种方法也有一个显著的缺陷:如果你的分类特征有许多枚举值,那么数据集的维度就会急剧增加。然而,由于被编码的数据中有许多0,因此用稀疏矩阵表示会非常高效。
另外,对于决策树模型不推荐对离散特征进行 one-hot。原因如下:
2.2. 缺失值处理
-
目的:减少增加不确定性,解决可能会导致不可靠输出
- 不处理(针对类似 XGBoost 等树模型);
- 删除(缺失数据太多);
- 插值补全,包括均值/中位数/众数/建模预测/多重插补/压缩感知补全/矩阵补全等;
- 分箱,缺失值一个箱;
2.3. 异常值处理
- 目的:减少脏数据
- 简单统计:如 describe() 的统计描述;散点图等;
- 3∂ 法则(正态分布)/箱型图截断;
- BOX-COX 转换(处理有偏分布);
- 长尾截断;
- 利用模型进行离群点检测:聚类、K近邻、One Class SVM、Isolation Forest;
2.4 其他
删除无效列/更改dtypes/删除列中的字符串/将时间戳从字符串转换为日期时间格式等
3 特征构造
- 目的:增强数据表达,添加先验知识。
3.1 统计量特征:
- 计数、求和、比例、标准差;
3.2 时间特征:
- 绝对时间、相对时间、节假日、双休日;
3.3 地理信息:
- 分桶;
3.4 非线性变换:
- 取 log/平方/根号;
3.5 数据分桶:
- 等频/等距分桶、Best-KS 分桶、卡方分桶;
3.6 特征组合
4 特征选择
- 目的:降低噪声,平滑预测能力和计算复杂度,增强模型预测性能。
4.1 过滤式(Filter)
先用特征选择方法对初识特征进行过滤然后再训练学习器,特征选择过程与后续学习器无关。
- Relief/方差选择/相关系数/卡方检验/互信息法
4.2. 包裹式(Wrapper)
直接把最终将要使用的学习器的性能作为衡量特征子集的评价准则,其目的在于为给定学习器选择最有利于其性能的特征子集。
- Las Vegas Wrapper(LVM)
4.3. 嵌入式(Embedding)
结合过滤式和包裹式方法,将特征选择与学习器训练过程融为一体,两者在同一优化过程中完成,即学习器训练过程中自动进行了特征选择。
- LR+L1或决策树
5 类别不平衡
-
缺点:少类别提供信息太少,没有学会如何判别少数类。
主要解决方法:- 扩充数据集;
- 尝试其他评价指标:AUC等;
- 调整θ值;
- 重采样:过采样/欠采样;
- 合成样本:SMOTE;
- 选择其他模型:决策树等;
- 加权少类别人样本错分代价;
- 创新:
- 将大类分解成多个小类;
- 将小类视为异常点,并用异常检测建模。
-
理论完善
-
代码实践