首页 / 资讯中心 / 文章详情

PCA双标图怎么看:载荷箭头、夹角与变量解读实战

PCA双标图怎么看:载荷箭头、夹角与变量解读实战 ★ FEATURED ARTICLE
1. 先说清楚PCA 图上那根箭头到底在表达什么第一次看 PCA 双标图biplot的人十有八九会被满屏的箭头劝退。散点还好理解——每个点是一个样本聚在一起说明相似散开说明差异大。可那些从原点伸出来的箭头是什么为什么有的长有的短为什么有的指向样本聚集区有的指向空白地带我把这个问题拆开讲PCA 图里的箭头本质上是原始变量特征在降维后坐标系中的载荷向量loading vector的几何可视化。它回答的是这个主成分到底是被哪些变量撑起来的这个问题。一个 PCA 模型输出的核心信息有两块一块是得分score即每个样本在新坐标轴上的投影位置画出来就是那些散点另一块是载荷loading即每个原始变量对每个主成分的贡献权重画出来就是箭头。这两块信息共享同一个坐标平面所以能叠在一张图上这就是 biplot 名字的由来——bi 指的是 bi-plot样本与变量同图。箭头的方向含义很直白箭头指向哪个方向就说明这个变量在该方向上的取值增大时会把样本往那个方向拉。箭头的长度含义同样直白长度越长说明这个变量在这个二维平面里被保留的信息越多对这两个主成分的贡献越大长度接近 0 的箭头说明这个变量的变化几乎没体现在这两个主成分上解释力很弱。这里有个特别容易踩的坑我得提前说箭头的长度不是重要性排名。很多新手看到某个箭头特别短就直接把这个变量删掉这个操作非常危险。短只代表在这两个主成分构成的面内投影短它可能在第三、第四主成分上有很高的载荷只是你当前只画了前两个维度而已。我见过不止一次有人据此删变量结果模型换了个主成分数量之后结论完全反过来。还有一个概念得先摆正箭头和散点不在同一个度量尺度上。散点的坐标是样本得分箭头的坐标是变量载荷两者数值量级往往差很多。所以绝大多数绘图库在画 biplot 时会对其中一方做缩放scaling常见做法是把载荷乘以一个系数或者对得分做标准化。这就导致一个现象你换一个软件、换一个参数箭头的长度会变但方向基本不变变量之间的相对角度关系也不变。记住这一点后面讲解读的时候会反复用到。至于适合谁看这个问题——只要你在做多变量数据的探索性分析不管是实验数据、问卷数据、用户行为指标还是成分检测数据这张图都用得上。看懂箭头你就能从样本怎么分类进阶到为什么会这样分类这是从描述现象到解释机理的关键一步。2. 先搞懂底层逻辑载荷、方向余弦与夹角余弦要真正把箭头读明白得回到数学。我不打算堆公式但几个核心关系必须讲透否则后面所有解读技巧都是空中楼阁。2.1 载荷向量的几何本质假设你有 p 个变量、n 个样本做了标准化之后跑 PCA。每个主成分是一组单位正交向量第 k 个主成分对应的载荷向量就是 p 维空间里的一个方向。把这个 p 维向量投影到你选定的两个主成分比如 PC1 和 PC2张成的平面上得到的就是二维坐标 (loading_pc1, loading_pc2)从原点画到该点就是图上那根箭头。所以箭头的位置信息包含三层横坐标是该变量在 PC1 上的载荷纵坐标是在 PC2 上的载荷长度是这两个载荷的平方和开根号。这个长度有个专门的名字叫变量在因子平面上的共同度communality的平方根。共同度衡量的是这个变量的方差有多少被这两个主成分解释了。举个具体数字帮你建立感觉。假设某个变量在 PC1 上载荷 0.8PC2 上载荷 0.6那么箭头长度是 sqrt(0.640.36)1.0说明这个变量的方差有 100% 被前两个主成分解释因为标准化后总方差为 1。如果载荷是 0.2 和 0.15长度约 0.25共同度只有 0.0625意味着这个变量的信息 94% 都散落在后面那些没画出来的主成分里。看这就是为什么盯着短箭头做决策会翻车。2.2 夹角余弦等于相关系数这是解读 biplot 时最有用的一个性质也是最多人不知道的两个箭头之间夹角的余弦值近似等于这两个变量之间的相关系数。夹角接近 0 度余弦接近 1说明两个变量强正相关它们同向变化夹角接近 90 度余弦接近 0说明两个变量基本不相关各自独立变化夹角接近 180 度余弦接近 -1说明两个变量强负相关此消彼长夹角 120 度左右余弦约 -0.5中等强度的负相关。这个性质不是精确成立的前提是这两个变量在前两个主成分上的共同度都比较高也就是箭头都比较长。如果箭头很短角度就没有参考意义——这一点我必须强调因为网上很多教程直接说夹角就是相关系数省掉了这个前提害人不浅。我在实际项目里验证过这个性质。做用户行为指标分析时日均访问次数和页面浏览深度两个箭头夹角大约 20 度算出来相关系数 0.93和原始数据的 Pearson 相关系数就是 0.93几乎一致。而日均访问次数和平均单次停留时长夹角接近 100 度原始相关系数是 -0.17吻合得也很好。这种验证建议你也做一次能极大增强你对图的可信度。2.3 箭头与散点的投影关系第三个性质讲的是箭头和样本点的关系同样基于内积把某个样本点向某根箭头所在直线做垂线投影投影点的位置相对于原点近似反映该样本在这个变量上的取值高低。这句话有点绕我换成操作化的说法拿一把尺子沿着箭头方向延长然后看样本点落在这条线上的位置。越靠近箭头尖端方向说明这个样本在该变量上的原始值越高越靠近反方向值越低。这个技巧在判断右上角那堆点到底哪个指标高时非常好用。但要提醒的是这个性质同样受共同度约束。如果某个变量的箭头很短用它去判断样本取值就不靠谱。而且 biplot 的缩放方式不同后面会讲这个投影的精确度也会有差异。所以我的经验是用这个性质做定性判断可以做精确排序不行。真要排序老老实实回到原始数据去算。3. 实操拆解从原始数据到一张能读的 PCA 双标图理论讲完进入动手环节。我按完整流程走一遍中间穿插参数选择的理由和踩坑记录。3.1 数据预处理标准化不是可选项PCA 对量纲极度敏感这一点必须放在第一步说。假设你的数据里有年收入单位万元范围 5 到 200和满意度评分1 到 5不标准化直接跑 PCAPC1 基本会被年收入独占因为它的方差天然大得多。这不是数据本身的规律纯粹是量纲造成的假象。标准做法是z-score 标准化即每个变量减去均值再除以标准差让所有变量的方差都变成 1。用 Python 的话import numpy as np import pandas as pd # df 是原始数据框行为样本列为变量 X df.select_dtypes(include[np.number]).values X_std (X - X.mean(axis0)) / X.std(axis0, ddof1)如果你用的是 scikit-learn 的 Pipeline直接调StandardScaler就行。但我更推荐在探索阶段用 numpy 手写一遍因为你会被迫检查每一步的输出能更早发现缺失值和异常值。注意标准化之前一定要处理缺失值和极端离群点。PCA 对离群点极其敏感一个坐标值差了三个数量级的样本能把整条主成分轴拽偏。我习惯先算每个变量到中位数的稳健距离超出阈值超过 3 倍的样本单独标记出来看一眼确认是录入错误还是真实极端值再决定剔除还是保留。还有一个经常被忽略的决策是否该标准化。如果你的所有变量本来就是同量纲、同尺度比如都是一批同类型传感器的读数不标准化反而能保留方差结构的原始信息。我的判断原则是变量之间量纲不一致就必须标准化量纲一致时两种都试一下看结果稳定性如果结论差异大说明数据本身结构不稳需要回头检查。3.2 计算主成分与载荷矩阵标准流程用 SVD 或者特征分解都行结果等价。核心是拿到特征值、特征向量和得分三样东西。# 协方差矩阵标准化后即相关系数矩阵 cov np.cov(X_std, rowvarFalse) eigvals, eigvecs np.linalg.eigh(cov) # 按特征值降序排列 idx np.argsort(eigvals)[::-1] eigvals eigvals[idx] eigvecs eigvecs[:, idx] # 载荷矩阵特征向量乘以对应特征值的平方根 loadings eigvecs * np.sqrt(eigvals) # 得分矩阵 scores X_std eigvecs这里有个小细节值得说载荷有两种定义。一种是特征向量乘以特征值平方根上面这种另一种就是直接用特征向量。前者保证载荷的平方和等于特征值后者保证载荷的平方和等于 1。不同软件默认不一样所以在对比不同工具的输出前先确认它用的是哪种约定。这不是死知识但能帮你在为什么我的载荷算出 0.8别人算出 0.3这种困惑里少走弯路。解释方差比例也要算出来写在图上标注轴标题explained eigvals / eigvals.sum() print(fPC1: {explained[0]*100:.1f}%, PC2: {explained[1]*100:.1f}%)通常前两个主成分累计解释 50% 以上就是不错的起点。低于 40% 的话我建议慎重解读这张二维图因为它丢掉的信息太多图上的规律可能只是噪声的投影。这种情况要么增加维度看三维图要么换方法。3.3 绘制双标图与缩放参数主流工具我都用过说下各自的适用场景。工具优势注意事项Python sklearn matplotlib完全可控缩放自定义需要手动算载荷绘图代码较长R ggplot2 factoextra一键出图样式美观默认缩放方式要确认fviz_pca_biplot默认会对变量做缩放R ggbiplot传统 academic 风格维护频率低新版 R 可能装不上Origin / GraphPad无需编程适合手工数据载荷导出后自己画缩放系数不透明手绘 biplot 的关键在于得分为载荷的缩放比例要匹配。常用做法是把载荷乘以一个系数让箭头长度和散点云的范围大致相当。一个简单可靠的做法import matplotlib.pyplot as plt # 缩放系数让最长的箭头约为散点最大半径的 0.8 倍 score_max np.abs(scores[:, :2]).max() loading_max np.abs(loadings[:, :2]).max() scale 0.8 * score_max / loading_max fig, ax plt.subplots(figsize(9, 8)) ax.scatter(scores[:, 0], scores[:, 1], s30, alpha0.6, edgecolorsk, linewidths0.3) for i, var in enumerate(df.columns[:num_vars]): ax.arrow(0, 0, loadings[i,0]*scale, loadings[i,1]*scale, head_width0.02*score_max, colorcrimson, alpha0.85, length_includes_headTrue) ax.text(loadings[i,0]*scale*1.08, loadings[i,1]*scale*1.08, var, fontsize9) ax.axhline(0, colorgray, lw0.6, linestyle--) ax.axvline(0, colorgray, lw0.6, linestyle--) ax.set_xlabel(fPC1 ({explained[0]*100:.1f}%)) ax.set_ylabel(fPC2 ({explained[1]*100:.1f}%)) plt.tight_layout()注意scale这个系数只影响视觉可读性不影响任何数值结论。别把它当成某种需要精确设定的参数调到一个看着舒服、箭头不压住散点的值就行。但一定要在图的说明文字里写清楚变量载荷已按 X 倍缩放否则拿去投稿或者汇报时会被追问。3.4 变量数量过多时的取舍策略实际数据动辄几十上百个变量全画上去就是一团乱麻。我有几个处理顺序可参考第一步按共同度筛。只画共同度前两个主成分的载荷平方和超过 0.4 的变量剩下的默认不显示但在图注里说明一共多少个变量、显示了几个、筛选阈值多少。这个操作是纯展示优化不涉及删除数据。第二步按领域知识合并。如果你有十几个高度相关的变量可以先做一次相关性聚类同一簇选一个代表变量上图标其余在图注里注明该箭头代表 A、B、C 等 6 个高相关变量。这样图能读懂信息也没丢。第三步换图。如果变量实在太多二维 biplot 就不合适了。可以考虑用载荷热力图变量为行、主成分为列替代或者用相关性圆圈图。工具是死的目的始终是让读图的人抓住结构。4. 读图实战六种典型模式与对应结论这一节是全篇最实操的部分。我把常见的箭头分布模式总结成六种每种给出读法、可能的成因和验证方式。4.1 模式一箭头呈扇形均匀分布所有箭头从原点向不同方向散开长度相近夹角大致均匀。这种图通常对应变量之间相关性较低、数据维度分散的情况说明原始变量各自独立贡献信息PCA 的降维收益有限。遇到这种图我的建议是不要强行解释主成分的物理含义。因为每个主成分都由许多变量以相近权重构成你很难给它起一个有意义的名字。这时候更该考虑的是是不是应该用因子旋转varimax来获得更清晰的结构或者干脆放弃降维用其他方法做变量筛选。4.2 模式二箭头分成两三个紧密簇箭头明显聚成几团团内夹角小团间夹角接近 90 度或 180 度。这是信息量最大的模式说明变量背后存在少数几个潜在维度。每簇变量可以视为同一个潜在因子的不同侧面。操作上先对每簇变量做内部相关性检查确认簇内相关系数都在 0.6 以上然后给每簇起一个概括性的名字这个名字就是你后续解释主成分的依据。注意两个簇如果夹角接近 180 度它们代表的是同一个维度的两端可以理解为此消彼长的两个方面命名时要体现这种对立关系比如效率导向对质量导向。4.3 模式三只有一两根长箭头其余都很短这种情况要警惕。可能是数据里确实存在一个主导变量比如某个指标的量程远大于其他也可能是某个变量有严重离群值。排查顺序是先看那根长箭头对应的变量分布直方图再看它的最大值和最小值。我遇到过一回订单金额这个变量箭头特别长独占 PC1 的 70% 方差。查下来发现有个测试账户下了一笔异常大的订单标准化后 z 值超过 15。剔除这一条记录后图完全变了长箭头缩回正常长度其他变量也显现出来了。这就是离群点的破坏力。4.4 模式四箭头与样本簇的对应关系把箭头和散点叠起来看能建立样本为什么聚在这里的因果链。读法是某个样本簇位于某根箭头的延长线方向说明该簇样本在这个变量上取值偏高位于箭头反方向则取值偏低。举个例子做设备状态监测时散点分成三簇一簇落在振动幅度箭头正方向且运行时长箭头反方向这簇样本基本就是刚上机、振动大的磨合期设备另一簇落在运行时长正方向、温度接近零载荷的区域对应稳定运行期。这种解释比单纯说分了三类有价值得多因为它直接指向了可操作的判断依据。要提醒的是这个读法只在箭头足够长时可靠我在 2.3 节已经说过原因。实际操作中我会做个交叉验证对某一簇样本回去算它在关键变量上的均值和全体均值比较看方向和图上读出来的是否一致。不一致就说明图读错了或者缩放干扰了判断。4.5 模式五箭头全部挤在原点附近整张图散点铺得很开但箭头短得像一堆小刺。这说明前两个主成分主要反映的是样本间的整体差异而不是变量结构。可能的原因有两个一是数据本身噪声大信号分散在多个维度二是样本量远小于变量数主成分不稳定。这种情况下二维图基本没有解释价值。我的处理是看碎石图scree plot检查特征值是否呈现明显的断崖。如果没有断崖说明数据没有低维结构PCA 不适合这个数据集应该换方法。4.6 模式六箭头重叠严重两个或多个箭头几乎完全重合说明这些变量高度共线。这在问卷数据、指标体系中极为常见。重合本身不是问题反而是个有用信号你可以只保留其中一个变量其余的作用是互相验证。但要注意高度共线的变量会让载荷的解释变得不稳定。样本稍微变一点载荷可能在这几个共线变量之间跳来跳去。所以如果你要做的是变量重要性排序先做共线性诊断算 VIF 或变量间相关矩阵把相关超过 0.9 的变量合并处理再跑 PCA。5. 常见问题与排查速查这一节整理我在实际工作中被问得最多、以及自己踩过的坑。表格形式方便对照。现象可能原因排查与处理换软件后箭头长度全变了载荷定义或缩放约定不同检查是特征向量还是特征向量乘 sqrt(特征值)确认绘图库的缩放参数方向不变即为正常箭头方向解读和业务常识相反符号翻转特征向量方向不唯一PCA 主成分的正负号本身没有意义整体乘 -1 不改变结果解读时以变量间相对关系为准某变量箭头极短该变量在前两个 PC 上共同度低查该变量在 PC3、PC4 上的载荷不要据此删除变量样本聚类界限模糊前两个 PC 解释方差不足看累计解释率低于 40% 时考虑增加维度或换方法箭头长度和变量重要性排序不一致混淆了共同度与变量重要性变量重要性应综合多个主成分的载荷或用其他方法如随机森林重要性交叉验证图上一根箭头对应不上任何变量名变量数量多标签重叠调整标签偏移、用交互式绘图或按共同度筛选后重画关于符号翻转这一条我要多说两句因为它是新手最容易被绕晕的地方。PCA 求解的是特征向量而特征向量乘以 -1 仍然是同一个特征向量。不同软件、甚至同一软件的不同版本输出的符号可能相反。这意味着 PC1 轴的正方向可能是高值在右也可能是高值在左完全取决于实现细节。提示解读时永远不要依赖PC1 正方向代表什么这种绝对表述。稳妥的读法是看变量之间的相对位置以及样本相对于箭头的方位。这两类关系在符号翻转下保持不变。另一个高频问题是箭头能不能用来算具体数值。答案是不能直接算。箭头只给出方向和相对强度不给出斜率或截距。如果你需要定量关系回到原始数据做回归或者算相关系数。PCA 图的作用是提出假设、发现结构不是做精确推断。我在汇报时习惯把这句话写进图注避免听众过度解读。还有个很实际的坑变量名太长导致图完全没法看。处理办法有三个一是缩短变量名但要保留在附表里做对照二是用编号代替V1、V2...配合附表三是改成只标注长箭头、短箭头不标。我个人最推荐第二种虽然读图时需要查表但图面干净汇报时不容易被文字淹没。6. 几个不写在文档里的实操心得做完这些年后我对 PCA 双标图的态度是它是一张提问图不是一张结论图。它最大的价值是让你快速看到变量之间可能存在的关系然后带着这些假设去做更严格的验证。第一条心得先看共同度再看方向。很多人一上来就分析箭头指向但如果共同度低方向本身就不稳定。我现在的固定流程是先导出一张变量共同度表按共同度排序只看前 60% 的变量在图上的箭头其余的视为信息未展示。这个习惯让我避免了不少误判。第二条心得双标图一定要配合原始相关矩阵看。箭头夹角给出的相关性是近似的、二维的而相关矩阵是精确的、全维的。两者一致时你可以放心解读不一致时以相关矩阵为准并回头想为什么二维投影会失真。这个对账动作花不了几分钟但能显著提升结论可信度。第三条心得别在一张图上塞太多东西。样本按类别着色、变量箭头、置信椭圆、样本标签全加上去图就废了。我的做法是分两张图一张只画样本聚类和着色用来回答怎么分另一张只画箭头用来回答为什么这么分。两张图各自清爽讲的时候也有节奏。第四条心得符号和缩放的怪现象先别怀疑数据。遇到箭头方向反了、长度不对九成是绘图约定的问题不是数据问题。先确认工具的输出定义再去看数据。这个顺序能省掉大量无谓的排查时间。最后分享一个我在做变量筛选时常用的组合拳先用 PCA 双标图识别出高度共线的变量簇每簇保留一个代表再用保留后的变量重跑一次 PCA对比两次的样本聚类结构是否稳定。如果稳定说明冗余变量确实可以去掉如果结构变了说明那些被去掉的变量承载了独立信息得留着。这个去变量—重跑—对比的循环我做过多轮比单纯看载荷数值阈值要可靠得多因为它检验的是对最终结论的影响而不只是统计指标。
阅读完成 · 觉得有帮助?
咨询建站