跳转到内容

E.C.4 线性判别分析

LDA 有监督投影直觉图

LDA 会寻找一个投影方向,让同类样本更靠近、不同类样本更分开。它既可以做分类,也可以做有监督降维。

  • Python 3.10+
  • 当前稳定版 scikit-learnnumpy
Terminal window
python -m pip install -U scikit-learn numpy
  • 类内方差:同一个类别内部有多分散。
  • 类间分离:不同类别中心之间有多远。
  • 投影:把特征映射到更低维空间。
  • 有监督降维:降维时使用标签信息。
  • 这里的 LDA:Linear Discriminant Analysis,不是 Latent Dirichlet Allocation。

创建 lda_projection.py

import numpy as np
from sklearn.discriminant_analysis import LinearDiscriminantAnalysis
X = np.array([
[1.0, 2.0],
[1.5, 1.8],
[2.0, 1.5],
[4.0, 5.0],
[4.5, 4.8],
[5.0, 4.5],
])
y = np.array([0, 0, 0, 1, 1, 1])
model = LinearDiscriminantAnalysis(n_components=1)
model.fit(X, y)
pred = model.predict([[1.4, 1.9], [4.8, 4.6]])
projection = model.transform(X)
print("predictions:", pred.tolist())
print("projection_shape:", projection.shape)

运行:

Terminal window
python lda_projection.py

预期输出:

Terminal window
predictions: [0, 1]
projection_shape: (6, 1)

同一个模型既完成了新点分类,也把训练数据投影到一个有判别力的一维方向。

PCA 寻找整体方差大的方向,不看标签。LDA 使用标签,寻找最能分开类别的方向。当类别分离比通用压缩更重要时,LDA 更有意义。

适合尝试 LDA:

  1. 已有标签。
  2. 类别内部比较紧凑。
  3. 想做轻量线性 baseline。
  4. 想为可视化或下游模型得到低维表示。

如果类别边界明显高度非线性,就不要优先用它。

复盘 LDA 时,检查投影后类别是否真的更容易分开。一个小图、类别均值表,或者投影前后的分数对比,都可以作为这页的证据。

不要默认“降维后一定更好”。如果投影后类别仍然重叠,就把这个结论写下来,并和 SVM、KNN 或其他 baseline 对比。LDA 的价值是解释分离方向,而不是制造一个新矩阵。

交付检查时,记录投影后的形状和每个类别的投影均值。若均值靠得很近,说明 LDA 找到的方向不够区分类别。这个结论本身也有价值,因为它告诉你需要更好的特征或非线性模型。

学完这一页,至少保留这张证据卡:

模型家族
SVM、KNN、朴素贝叶斯、LDA 或其他传统基线
数据视图
特征缩放、类别平衡、决策边界和训练/测试划分
指标
准确率/F1、混淆矩阵、边距、邻近行为或投影质量
失败检查
缩放、高维度、假设薄弱、泄漏或基线拟合差
期望产出
经典机器学习基线结果,以及一条局限性说明
  • 把这里的 LDA 和主题模型 LDA 混淆。
  • 以为 LDA 用标签,所以一定比 PCA 好。
  • 忘记两个类别时,LDA 最多只能投影到一个分量。

添加第三个类别,并设置 n_components=2。打印新的投影形状,并解释为什么最大分量数变了。

项目交付参考与讲解

有三个类别时,LDA 最多可以投影到 类别数 - 1 = 2 个判别分量,前提是特征维度也允许。如果你给类别 2 增加三个样本,并设置 n_components=2,变换后的数据应该有两列;如果现在共有九行,形状会类似 (9, 2)

关键解释是:LDA 的方向用于分开类别。两个类别最多只需要一个分离方向;三个类别可能需要两个方向。