趋近智
封装方法通过训练和测试特定的机器学习模型来评估特征子集。这种方式不同于过滤方法,过滤方法独立于任何模型评估特征。因为封装方法使用模型表现作为评估标准,它们通常能找到更适合特定算法的特征子集,有可能捕捉到过滤方法可能遗漏的特征间关系。然而,这伴随着更高的计算成本,因为需要训练多个模型。
递归特征消除 (RFE) 是一种通过训练和测试特定机器学习模型来评估特征子集的封装方法。这种方法以递归方式移除最不重要的特征,其依据是外部评估器为特征分配的权重或重要性得分(例如线性模型的系数或基于树模型的特征重要性)。
RFE 的核心思路直观明了:
feature_importances_ 属性。这个迭代过程逐步修剪特征集,旨在保留那些对模型预测能力贡献最大的特征,根据所选评估器。
递归特征消除 (RFE) 的迭代过程。
在 RFE 中评估器的选择很重要,因为特征重要性排序完全取决于它。
LinearRegression、LogisticRegression 或 LinearSVC 等评估器使用系数大小 (coef_) 来对特征进行排序。具有较大绝对值的系数的特征被认为更重要。这些模型中的正则化(如 L1 或 L2)会影响系数,从而影响排序。DecisionTreeClassifier、RandomForestClassifier 或 GradientBoostingClassifier 等评估器使用 feature_importances_ 属性,该属性通常衡量每个特征对减少森林或集成中所有树的杂质(如基尼不纯度或熵)的贡献程度。通常,在 RFE 中选用与您最终打算部署的模型相似的评估器是较好的做法,尽管更简单、更快的模型(如线性模型)常用于选择过程本身,以控制计算成本。
Scikit-learn 提供了通过 sklearn.feature_selection.RFE 类实现的便捷 RFE。
import pandas as pd
from sklearn.datasets import make_classification
from sklearn.feature_selection import RFE
from sklearn.linear_model import LogisticRegression
# 生成模拟数据
X, y = make_classification(n_samples=100, n_features=10, n_informative=5,
n_redundant=2, n_classes=2, random_state=42)
X = pd.DataFrame(X, columns=[f'feature_{i}' for i in range(10)])
# 1. 选择一个评估器
estimator = LogisticRegression(solver='liblinear')
# 2. 初始化 RFE
# 选择最重要的 5 个特征
rfe_selector = RFE(estimator=estimator, n_features_to_select=5, step=1) # step=1 表示每次迭代移除 1 个特征
# 3. 在数据上拟合 RFE
rfe_selector = rfe_selector.fit(X, y)
# 4. 获取结果
selected_features_mask = rfe_selector.support_
feature_ranking = rfe_selector.ranking_
print("Feature Names:", X.columns.tolist())
print("Selected Mask:", selected_features_mask) # 选定特征为 True
print("Feature Ranking:", feature_ranking) # 1 表示已选,数字越大表示越早被移除
# 获取选定特征的名称
selected_feature_names = X.columns[selected_features_mask]
print("\nSelected Features:", selected_feature_names.tolist())
# 转换数据以仅保留选定特征
X_selected = rfe_selector.transform(X)
print("\nShape of original data:", X.shape)
print("Shape of data after RFE:", X_selected.shape)
在此示例中:
LogisticRegression 作为基础评估器。n_features_to_select=5,这告诉 RFE 在只剩下 5 个最优特征时停止。support_ 属性返回一个布尔掩码,表示哪些特征被选中。ranking_ 属性为每个特征赋予一个排名(1 表示选中,2 表示第一个被移除的,依此类推)。transform 方法可以直接获取只包含选定特征的数据集。RFE 的一个常见问题是不知道要保留多少特征 (n_features_to_select)。选择太少可能丢弃有用信息,而选择太多可能保留噪声或冗余特征。
Scikit-learn 提供了 RFECV (带交叉验证的 RFE),它自动确定最优特征数量。它在交叉验证循环中执行 RFE,评估不同数量选定特征的模型表现。
from sklearn.feature_selection import RFECV
from sklearn.model_selection import StratifiedKFold
# 使用 RFECV 寻找最优特征数量
cv_strategy = StratifiedKFold(n_splits=5) # 对于分类问题使用分层 K 折交叉验证
rfecv_selector = RFECV(estimator=estimator,
step=1,
cv=cv_strategy,
scoring='accuracy', # 要优化的性能指标
min_features_to_select=1) # 考虑的最小特征数量
rfecv_selector = rfecv_selector.fit(X, y)
print(f"\nOptimal number of features found by RFECV: {rfecv_selector.n_features_}")
print("Selected Features by RFECV:", X.columns[rfecv_selector.support_].tolist())
# 您可以选择绘制性能与特征数量的关系图
# grid_scores_ 属性(或新版本中的 cv_results_['mean_test_score'])
# 包含测试的每个特征数量的得分。
# (为简洁起见,省略了绘图代码)
RFECV 使用指定的交叉验证策略 (cv) 和性能指标 (scoring) 来寻找在各折中产生最佳平均得分的特征数量。这通常是选择特征子集大小的一种更数据驱动的方式,相比于手动设置 n_features_to_select。
优点:
缺点:
RFECV,还可能乘以交叉验证的折数)。这对于大型数据集或复杂模型可能很慢。RFE 是一种有价值的工具,当您怀疑特征间关系相关且计算成本可控时。使用 RFECV 提供了一种更自动化且通常更可靠的应用 RFE 的方式,通过集成交叉验证来确定要保留的特征数量。
这部分内容有帮助吗?
© 2026 ApX Machine Learning用心打造