终于把机器学习中的特征选择搞懂了!!!

人工智能 机器学习
特征选择是机器学习中的重要步骤,其目的是从高维特征空间中选择对模型性能最有价值的特征。通过减少冗余和无关的特征,特征选择可以提高模型的训练效率、减少过拟合并提升模型的泛化性能。

今天给大家分享机器学习中的一个关键概念:特征选择。

特征选择是机器学习中的重要步骤,其目的是从高维特征空间中选择对模型性能最有价值的特征。

通过减少冗余和无关的特征,特征选择可以提高模型的训练效率、减少过拟合并提升模型的泛化性能。

特征选择的重要性

  1. 提高模型性能:通过去除冗余或无关的特征,可以减少噪声,提高模型的准确性和稳定性。
  2. 减少计算成本:较少的特征意味着更低的计算复杂度,加快训练和预测速度。
  3. 防止过拟合:去除不相关特征有助于减少模型的复杂度,降低过拟合风险。
  4. 提高模型可解释性:更少的特征使得模型更容易理解和解释,有助于发现数据中的关键因素。

特征选择的方法

特征选择通常分为三种主要方法:

  • 过滤法
  • 包裹法
  • 嵌入法

过滤法

过滤法基于统计指标对特征进行评分,并根据评分选择特征。

这类方法与具体的机器学习算法无关,通常作为预处理步骤。

常见技术

  • 相关系数,衡量每个特征与目标变量之间的线性相关性。例如,皮尔逊相关系数。
  • 卡方检验,适用于分类问题,评估特征与目标变量的独立性。
  • 信息增益,基于信息理论,衡量特征提供的信息量。
  • 互信息,衡量特征与目标变量之间的非线性依赖关系。
  • 方差选择法,去除方差低于某一阈值的特征,认为这些特征变化较小,信息量不足。

优缺点

  • 优点:计算速度快,适用于高维数据。
  • 缺点:忽略特征之间的相关性,可能无法捕捉到特征与目标变量之间的复杂关系。

包装法

包装法将特征选择视为一个搜索问题,通过训练模型评估特征子集的性能,选择最优子集。这类方法与具体的机器学习算法紧密相关。

常见技术

  • 递归特征消除
    递归地训练模型,移除最不重要的特征,直到达到预定的特征数量。
  • 前向选择
    从空特征集开始,逐步添加对模型性能提升最大的特征。
  • 后向消除
    从所有特征开始,逐步移除对模型性能影响最小的特征。

优缺点

  • 优点:能够考虑特征之间的相互作用,通常能获得更好的模型性能。
  • 缺点:计算成本高,尤其在高维数据中,可能不适用。

嵌入法

嵌入法在模型训练过程中进行特征选择,将特征选择嵌入到模型的训练过程中。

这类方法结合了过滤法和包装法的优点。

常见技术

  • Lasso回归:通过 L1 正则化,将不重要的特征系数压缩为零,实现特征选择。
  • 决策树及其集成方法:例如,随机森林和梯度提升树可以基于特征重要性进行特征选择。
  • 弹性网络:结合 L1 和 L2 正则化,兼具 Lasso和岭回归的优点。

优缺点

  • 优点:与模型训练相结合,能够自动选择重要特征,计算效率较高。
  • 缺点:依赖于具体的模型选择。

案例分享

下面我将通过 Python 代码展示如何在机器学习中应用不同的特征选择方法,包括过滤法、包装法和嵌入法。

这里,我们以经典的乳腺癌数据集为例进行说明。

数据加载与预处理

首先,我们导入相关的库,并加载数据集。

# 导入必要的库
import pandas as pd
import numpy as np
from sklearn.datasets import load_breast_cancer
from sklearn.model_selection import train_test_split
from sklearn.preprocessing import StandardScaler
import matplotlib.pyplot as plt
import seaborn as sns

# 加载乳腺癌数据集
data = load_breast_cancer()
X = pd.DataFrame(data.data, columns=data.feature_names)
y = pd.Series(data.target)

X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.2, random_state=42)

scaler = StandardScaler()
X_train_scaled = scaler.fit_transform(X_train)
X_test_scaled = scaler.transform(X_test)

过滤法

过滤法基于统计指标对特征进行评分和选择。

这里我们使用 SelectKBest 结合卡方检验和互信息两种方法。

使用卡方检验选择特征

from sklearn.feature_selection import SelectKBest, chi2
from sklearn.linear_model import LogisticRegression
from sklearn.metrics import accuracy_score

# 由于卡方检验要求非负特征,我们确保数据为非负
X_train_chi2 = X_train_scaled - X_train_scaled.min()
X_test_chi2 = X_test_scaled - X_train_scaled.min()

# 选择k个最佳特征
k = 2
selector = SelectKBest(score_func=chi2, k=k)
X_train_selected = selector.fit_transform(X_train_chi2, y_train)
X_test_selected = selector.transform(X_test_chi2)

# 查看选择的特征
selected_features = X.columns[selector.get_support()]
print(f"选择的特征(卡方检验): {list(selected_features)}")

# 使用逻辑回归进行训练和评估
model = LogisticRegression(max_iter=200)
model.fit(X_train_selected, y_train)
y_pred = model.predict(X_test_selected)
accuracy = accuracy_score(y_test, y_pred)
print(f"过滤法(卡方检验)后的准确率: {accuracy:.4f}")

#选择的特征(卡方检验): ['mean concave points', 'worst concave points']
#过滤法(卡方检验)后的准确率: 0.9386

使用互信息选择前10个特征

from sklearn.feature_selection import mutual_info_classif

# 选择前10个互信息最高的特征
selector_mi = SelectKBest(score_func=mutual_info_classif, k=10)
X_train_mi_selected = selector_mi.fit_transform(X_train_scaled, y_train)
X_test_mi_selected = selector_mi.transform(X_test_scaled)

# 查看选择的特征
selected_features_mi = X.columns[selector_mi.get_support()]
print("互信息选择的特征:\n", selected_features_mi)

# 训练模型
model.fit(X_train_mi_selected, y_train)
y_pred = model.predict(X_test_mi_selected)

# 评估模型
accuracy = accuracy_score(y_test, y_pred)
print("互信息后的模型准确率:", accuracy)

#互信息后的模型准确率: 0.9824561403508771

包装法

包装法将特征选择视为一个搜索问题。

这里我们使用递归特征消除(RFE)方法。

from sklearn.feature_selection import RFE

# 使用逻辑回归作为基模型
model = LogisticRegression(max_iter=200)
# 选择k个特征
k = 2
rfe = RFE(estimator=model, n_features_to_select=k)
rfe.fit(X_train_scaled, y_train)

# 查看选择的特征
selected_features = X.columns[rfe.support_]
print(f"选择的特征(RFE): {list(selected_features)}")

# 训练并评估模型
X_train_rfe = rfe.transform(X_train_scaled)
X_test_rfe = rfe.transform(X_test_scaled)

model.fit(X_train_rfe, y_train)
y_pred = model.predict(X_test_rfe)
accuracy = accuracy_score(y_test, y_pred)
print(f"包装法(RFE)后的准确率: {accuracy:.4f}")

#选择的特征(RFE): ['worst area', 'worst concave points']
#包装法(RFE)后的准确率: 0.9561

嵌入法

嵌入法在模型训练过程中进行特征选择,常见的方法包括Lasso回归和基于树的特征重要性。

使用 Lasso 回归进行特征选择

from sklearn.linear_model import LassoCV

# 使用Lasso进行特征选择
lasso = LassoCV(cv=5, random_state=42)
lasso.fit(X_train_scaled, y_train)

# 获取非零系数的特征
coef = pd.Series(lasso.coef_, index=X.columns)
selected_features_lasso = coef[coef != 0].index
print("Lasso选择的特征:\n", selected_features_lasso)

# 训练模型
X_train_lasso_selected = X_train_scaled[:, coef != 0]
X_test_lasso_selected = X_test_scaled[:, coef != 0]
model.fit(X_train_lasso_selected, y_train)
y_pred = model.predict(X_test_lasso_selected)
y_pred = (y_pred > 0.5).astype(int)

# 评估模型
accuracy = accuracy_score(y_test, y_pred)
print("Lasso后的模型准确率:", accuracy)

#Lasso后的模型准确率: 0.9824561403508771

使用随机森林进行特征重要性排序

from sklearn.ensemble import RandomForestClassifier

# 训练随机森林模型
rf = RandomForestClassifier(n_estimators=100, random_state=42)
rf.fit(X_train, y_train)

# 获取特征重要性
importances = pd.Series(rf.feature_importances_, index=X.columns)
importances_sorted = importances.sort_values(ascending=False)
print("特征重要性排名:\n", importances_sorted)

# 选择前10个重要特征
selected_features_rf = importances_sorted.head(10).index
print("随机森林选择的特征:\n", selected_features_rf)

# 训练模型
X_train_rf_selected = X_train[selected_features_rf]
X_test_rf_selected = X_test[selected_features_rf]
model.fit(X_train_rf_selected, y_train)
y_pred = model.predict(X_test_rf_selected)

# 评估模型
accuracy = accuracy_score(y_test, y_pred)
print("随机森林后的模型准确率:", accuracy)

# 随机森林后的模型准确率: 0.9912280701754386

# 可视化特征重要性
plt.figure(figsize=(10,6))
sns.barplot(x=importances_sorted.values[:10], y=importances_sorted.index[:10])
plt.title("随机森林特征重要性")
plt.xlabel("重要性分数")
plt.ylabel("特征")
plt.show()

图片图片

综合比较

为了比较不同特征选择方法对模型性能的影响,我们可以汇总各方法的准确率。

# 汇总准确率
accuracy_results = {
    "卡方检验": 0.9386,
    "互信息": 0.9824561403508771,
    "RFE": 0.9561,
    "Lasso": 0.9824561403508771,
    "随机森林": 0.9912280701754386
}

accuracy_df = pd.DataFrame(list(accuracy_results.items()), columns=["特征选择方法", "模型准确率"])
print(accuracy_df)

# 可视化比较
plt.figure(figsize=(8,6))
sns.barplot(x="模型准确率", y="特征选择方法", data=accuracy_df, palette="viridis")
plt.title("不同特征选择方法的模型准确率比较")
plt.xlabel("准确率")
plt.ylabel("特征选择方法")
plt.xlim(0.9, 1.0)
plt.show()

图片图片


责任编辑:武晓燕 来源: 程序员学长
相关推荐

2024-10-08 10:16:22

2024-10-28 00:00:10

机器学习模型程度

2024-10-28 15:52:38

机器学习特征工程数据集

2024-10-08 15:09:17

2024-09-18 16:42:58

机器学习评估指标模型

2024-10-14 14:02:17

机器学习评估指标人工智能

2024-11-05 12:56:06

机器学习函数MSE

2024-08-23 09:06:35

机器学习混淆矩阵预测

2024-10-30 08:23:07

2024-11-25 08:20:35

2024-08-01 08:41:08

2024-10-16 07:58:48

2024-12-03 08:16:57

2024-07-17 09:32:19

2024-09-23 09:12:20

2024-10-31 10:00:39

注意力机制核心组件

2024-12-02 01:10:04

神经网络自然语言DNN

2024-11-21 10:07:40

2024-12-02 13:28:44

2024-07-24 08:04:24

神经网络激活函数
点赞
收藏

51CTO技术栈公众号