sklearn函数总结六——特征降维 压缩数据 - 特征提取(PCA&LDA)

纯手打,代码整理中,

持续更新中^-^

序号延用总结五

目录

12、主成分分析 (PCA)

13、线性判别分析 (LDA)

核心目标

数学推导

代码示例

参数说明

[1.solver : str, {'svd', 'lsqr', 'eigen'}, default='svd'](#1.solver : str, {'svd', 'lsqr', 'eigen'}, default='svd')

[2.shrinkage : float or 'auto', default=None](#2.shrinkage : float or 'auto', default=None)

[3.priors : array-like of shape (n_classes,), default=None](#3.priors : array-like of shape (n_classes,), default=None)

[4.n_components : int, default=None](#4.n_components : int, default=None)

[5.store_covariance : bool, default=False](#5.store_covariance : bool, default=False)

[6.tol : float, default=1e-4](#6.tol : float, default=1e-4)

[7.covariance_estimator : estimator, default=None](#7.covariance_estimator : estimator, default=None)


特征提取------将原始特征转换到新的特征空间,从而减少特征数量。

12、主成分分析 (PCA)

PCA通过线性变换将原始特征转换为一组线性不相关的变量(主成分),按方差大小排序。

PCA的核心思想是:将原始高维特征通过线性变换映射到新的低维坐标系中,这个新坐标系的坐标轴(主成分)按照能够保留原始数据最大方差的方向依次排列。

这意味着第一个新坐标轴(第一主成分)保留了数据中最大程度的方差,第二个新坐标轴(第二主成分)在与第一个正交的前提下保留次大方差,以此类推。

直观理解:

想象你在黑暗中从不同角度观察一个三维物体(比如一个倾斜的椭圆盘子),并记录下它在二维平面上的影子。

• 某些角度下的影子(比如正上方)可能看起来只是一个短线,丢失了大量关于盘子形状的信息。

• 某些角度下的影子(比如从盘子侧面)则能最大程度地展现它的形状和大小(一个椭圆)。

PCA要做的就是自动找到那个"最佳观测角度",使得投影后的影子(低维数据)能包含原始物体(高维数据)最多的信息。而这个"信息量",在PCA中就用方差来衡量。方差越大,意味着数据点在新坐标轴上分布得越分散,保留的信息就越多。

数学原理与计算步骤(可分步理解)

假设有一个包含 m 个样本和 n 个特征的数据集 X),其中,每个样本 是一个n 维向量。

  1. 计算样本的均值向量
  1. 将数据集进行中心化处理,即每个特征减去对应的均值:
  1. 计算数据集的协方差矩阵
  1. 对协方差矩阵进行特征值分解,得到特征值和对应的特征向量

  2. 选择前 k 个特征值对应的特征向量作为主成分,构成一个投影矩阵 (每列是一个特征向量)。

  3. 将数据集投影到由前 k 个特征向量构成的子空间中:

其中,是降维后的数据集。

这就是 PCA 的数学公式,它描述了 PCA 的主要步骤和数学原理。

我们来看一个示例:

python 复制代码
from sklearn.decomposition import PCA
from sklearn.preprocessing import StandardScaler
from sklearn.datasets import load_iris
 # 加载数据
iris = load_iris()
X, y = iris.data, iris.target
 # 1. 标准化数据(至关重要!)
scaler = StandardScaler()
X_scaled = scaler.fit_transform(X)
 # 2. 初始化PCA,保留2个主成分用于可视化
pca = PCA(n_components=2)
 # 3. 训练转换数据
X_pca = pca.fit_transform(X_scaled)
print("原始数据形状:", X.shape)
print("降维后数据:", X_pca)

输出

python 复制代码
原始数据形状: (150, 4)
降维后数据: [[-2.26470281  0.4800266 ]
 [-2.08096115 -0.67413356]
   ......................................................
 [ 1.37278779  1.01125442]
 [ 0.96065603 -0.02433167]]

主要参数详解

|---------------------------|----------------------------------------------------------------------------|
| 参数/概念 | 说明 |
| n_components | 最重要的参数。指定要保留的主成分个数 k。可以设为整数(如 2),也可以设为 0 到 1 之间的浮点数(如 0.95,表示保留 95%的原始方差)。 |
| svd_solver | 指定求解器。通常使用默认的 'auto' 即可。对于大型数据,使用 'randomized' 的随机SVD方法会更高效。 |
| explained_variance_ | 属性。一个数组,表示每个主成分所捕获的方差大小(即特征值)。 |
| explained_variance_ratio_ | 属性。一个数组,表示每个主成分所捕获的方差占总方差的百分比。这是决定 k 取多少的关键依据。 |
| components_ | 属性。投影矩阵 W,每一行是一个主成分(特征向量)。 |

13、线性判别分析 (LDA)

LDA是一种有监督的降维方法,旨在最大化类间距离,最小化类内距离。

线性判别分析(Linear Discriminant Analysis, LDA)是一种经典的有监督 学习算法,主要用于分类 和降维。它的核心思想与主成分分析(PCA)不同:PCA追求的是数据方差最大化,是一种无监督的降维方法;而LDA追求的是最大化类间 散度 (类与类之间的距离)的同时最小化类内散度(同一类内的数据离散程度),即寻找能够最好地将不同类别区分开来的特征子空间。

核心目标

给定数据集,LDA的目标是找到一个投影方向(对于多类问题则是投影平面),使得:

  1. 类间散度(Between-class scatter)最大:不同类别的投影点中心尽可能远离。

  2. 类内散度(Within-class scatter)最小:同一类别的投影点尽可能聚集。

通过优化这两个目标,LDA能够使得投影后的数据具有最好的分类效果。

数学推导

代码示例

在 scikit-learn 库中LinearDiscriminantAnalysis 类来实现LDA。 在 sklearn.discriminant_analysis 模块中,LinearDiscriminantAnalysis 的构造函数如下

python 复制代码
LinearDiscriminantAnalysis(solver='svd',
                         shrinkage=None,
                         priors=None,
                         n_components=None,
                         store_covariance=False,
                         tol=0.0001,
                         covariance_estimator=None)

我们来看一个示例:

python 复制代码
from sklearn.discriminant_analysis import LinearDiscriminantAnalysis
from sklearn.preprocessing import StandardScaler
from sklearn.datasets import load_iris

# 加载数据
iris = load_iris()
X, y = iris.data, iris.target

# 1. 标准化数据(至关重要!)
scaler = StandardScaler()
X_scaled = scaler.fit_transform(X)

# 2. 初始化LDA,保留2个维度
lda = LinearDiscriminantAnalysis(n_components=2)

# 3. 训练并转换数据
X_lda = lda.fit_transform(X_scaled, y)

print("原始数据形状:", X.shape)
print("降维后数据:", X_lda)

输出

python 复制代码
原始数据形状: (150, 4)
降维后数据: [[ 8.06179978e+00 -3.00420621e-01]
 [ 7.12868772e+00  7.86660426e-01]
 ..........................................................................................
 [-4.96774090e+00 -8.21140550e-01]
 [-5.88614539e+00 -2.34509051e+00]
 [-4.68315426e+00 -3.32033811e-01]]

参数说明

1.solver : str, {'svd', 'lsqr', 'eigen'}, default='svd'

求解器算法。这是最重要的参数,它决定了LDA内部采用何种数学算法来求解,并且它会限制其他一些参数是否可用。

• 'svd' (奇异值分解):

o 原理: 不直接计算散度矩阵 ,而是通过SVD(奇异值分解)来求解。这是一种数值上最稳定、最精确的方法。

o 优点:

■ 无需计算 ,节省内存,尤其适用于特征数量非常多(甚至多于样本数)的场景。

■ 不会因为 是奇异矩阵(不可逆)而出现问题。

o 限制: 不能使用 shrinkage(收缩)参数。

o 适用场景: 默认选择。在大多数情况下都是最佳选择,特别是当特征维数高或担心数值稳定性时。

• 'lsqr' (最小二乘解):

o 原理: 通过最小化平方误差来求解。此算法可以执行收缩。

o 优点: 支持 shrinkage。

o 要求: 需要计算协方差矩阵,因此当 n_features 很大时可能效率不高。

o 适用场景: 当你明确需要使用收缩,并且特征维度不是极高时。

• 'eigen' (特征值分解):

o 原理: 通过求解广义特征值问题 来求解(即我们原理部分推导的方法)。此算法也可以执行收缩。

o 优点: 支持 shrinkage。

o 要求: 需要计算协方差矩阵,同样不适用于特征维度极高的场景。

o 适用场景: 与 'lsqr' 类似,当你需要收缩且特征数不多时。'eigen' 和 'lsqr' 的结果通常非常相似。

总结选择指南:

• 默认或特征数很多 -> 'svd'

• 需要收缩(Shrinkage)-> 'lsqr' 或 'eigen'

2.shrinkage : float or 'auto', default=None

收缩参数。用于估计协方差矩阵的正则化方法,主要用于解决当样本数量少于特征数量时,矩阵奇异(不可逆)的问题,或者改善协方差矩阵的估计。

• 原理: 收缩通过将类内散度矩阵 向一个对角矩阵(或单位矩阵)进行"缩小"来正则化它:

• 取值:

o None 或 0: 不进行任何收缩。

o 'auto': 使用Ledoit-Wolf引理自动确定最优的收缩强度。这是非常实用的一个选项。

o float between 0 and 1: 手动指定固定的收缩强度。例如,0.5 表示一半是原始协方差,一半是对角矩阵。

• 依赖关系: 仅当 solver 为 'lsqr' 或 'eigen' 时有效。'svd' 求解器不需要也不支持收缩。

• 适用场景: 当训练样本数较少、特征数较多导致模型过拟合或 $$S_$$ 奇异时,设置 shrinkage='auto' 通常能显著提升模型的泛化能力。

3.priors : array-like of shape (n_classes,), default=None

类的 先验概率

• 原理: 在贝叶斯框架下,LDA可以融入关于类别分布的先验知识。如果你知道你的数据中各类别的出现概率(例如,在医学诊断中,健康人群远多于患病人群),可以通过此参数指定。

• 取值: 一个长度等于类别数的数组,数组元素之和应为1.0。例如,对于三分分类问题,可以设置为 [0.3, 0.3, 0.4]。

• 默认 None: 模型将直接从训练数据中计算每个类的先验概率,即 priors = np.bincount(y) / len(y)。

• 影响: 这个参数会直接影响决策边界的的位置。如果你设置的先验概率与数据中的真实分布差异很大,决策边界会向先验概率较小的类别方向移动。

4.n_components : int, default=None

降维后希望保留的维度数。

• 原理: LDA降维后的最大维度是 min(n_features, n_classes - 1)。此参数用于指定最终保留的维度。

• 取值:

o None: 默认值,会自动设置为 n_classes - 1。

o int: 一个小于 n_classes - 1 的整数。例如,对于4分类问题,最多可降到3维,你可以设置 n_components=2 来只取前两个线性判别式。

• 注意: 此参数主要用于降维。即使你将其用作分类器,transform 方法也会使用这个维度。

5.store_covariance : bool, default=False

是否计算并存储每个类的 协方差矩阵

• 原理: 为 True 时,模型拟合后会有 covariance_ 属性,它是一个数组,包含了每个类的协方差矩阵。

• 取值:

o False (默认): 不存储。节省内存。

o True: 存储。主要用于调试和可视化,或者你需要查看类的协方差结构时。

• 依赖关系: 仅当 solver='svd' 时不可用,因为 'svd' 求解器根本不计算协方差矩阵。

6.tol : float, default=1e-4

用于秩估计的阈值。

• 原理: 当 solver='svd' 时,用于判断矩阵秩的容差值。任何奇异值小于 tol 的维度都会被丢弃。这是一个非常技术性的参数,通常不需要调整。

• 适用场景: 除非你非常了解数值线性代数,并且发现默认值导致了一些问题,否则保持默认即可。

7.covariance_estimator : estimator, default=None

协方差 估计器。

• 原理: 这是一个实验性参数(截至 scikit-learn 1.2版本)。它允许你传入一个自定义的协方差估计器对象(例如 sklearn.covariance.ShrunkCovariance)来替代标准的极大似然估计。

• 取值: 一个实现了 fit 方法的协方差估计器对象。

• 依赖关系: 仅当 solver='lsqr' 或 'eigen' 时可用。

• 适用场景: 为高级用户提供极大的灵活性,可以尝试各种不同的协方差矩阵正则化方法。绝大多数用户不需要使用此参数。

相关推荐
LucianaiB几秒前
【基于昇腾平台的CodeLlama实践:从环境搭建到高效开发】
运维·人工智能·性能优化
工藤学编程1 分钟前
零基础学AI大模型之LangChain Tool工具
人工智能·langchain
AI题库2 分钟前
NLTK自然语言处理实战:1.3 NLTK核心数据结构
数据结构·人工智能·自然语言处理
计算机程序设计小李同学4 分钟前
基于贝叶斯分类算法的垃圾邮件筛选器开发
人工智能·分类·数据挖掘
小龙4 分钟前
【学习笔记】模型的权重数据到底是干嘛的
人工智能·笔记·学习·权重
小程故事多_808 分钟前
重读ReAct,LLM Agent的启蒙之光,从“空想”到“实干”的范式革命
前端·人工智能·aigc
一个专注写代码的程序媛10 分钟前
流式读取数据
java·数据结构·算法
戴西软件11 分钟前
戴西软件AICrash:基于机器学习的行人保护仿真新范式
大数据·人工智能·机器学习·华为云·云计算·腾讯云·aws
Halo_tjn12 分钟前
Java Set集合知识点
java·开发语言·数据结构·windows·算法
愚公搬代码13 分钟前
【愚公系列】《扣子开发 AI Agent 智能体应用》018-提示词编写和优化(扣子平台设置提示词案例)
人工智能