1904年,英国心理学家CharlesSpearman研究了33名学生在古典语、法语和英语三门成绩,三门成绩的相关性系数如下:
三门成绩的高度相关会不会是由于它们三个成绩的背后有一个共同的因素,来决定这三门成绩的?比如语言能力?
对于个原始变量
来说,那些高度相关的变量很可能会遵循一个共同的潜在结构——或可称之为公共因子 (Common factor) 。简单的说就是:公共因子是用一个共同的因素来刻画几个高度相关的变量。
然而,这些“公共因子”通常是无法观测的,故称为潜变量 (latentvariables)。这在心理学、社会学及行为科学等学科中非常常见,比如
“智力”和“社会阶层”。
因子分析(Factor analysis)旨在提出因子模型(Factor model)来研究如何用几个公共因子,记作,通常
,来刻画原始变量之间的相关性。
Charles Spearman基于学生3门语言成绩的数据提出了单因子模型(Single factor model):
其中代表公共因子(Common factor),
代表特殊因子(Specific factor),即代表
的特殊部分;
代表系数/载荷(Loading),即来说明公共因子
对
的解释力。
当然,大多数时候一个公共因子是不够的,错综复杂的变量可能需要多个公共因子刻画,这就是我们将要学习的正交因子模型(Orthogonal factor model)
假设可观测随机向量的均值为
,协方差矩阵为
。正交因子模型假定
线性依赖于
个不可观测公共因子
和
个不可观测的特殊因子 (specific factors)
,通常
:
系数称为第
个变量在第
个因子上的载荷(loading),体现了该公共因子对此变量的解释力。
使用矩阵记号,上述模型可写为
,其中
即称作载荷矩阵(loading matrix)。
我们知道公共因子是虚拟的,不可观测的,所以理论上,我们可以给其任意的假设,为了分析方便,我们给它一种最简单的假设,其中和
假设满足:
①(单位阵,即
假设是正交的,
的方差假设为1,
和
之间假设是不相关的)
②(对角阵)
③而且和
是无关的:
有了这些假设,我们就可以回头来看,载荷矩阵到底是如何解释原始变量
和公共因子
的关系的?
已知模型如下:
矩阵形式模型:
元素形式模型:
我们可以计算原始变量和公共因子
的协方差矩阵:
综上,我们得到结论:,即
刻画的是
和
之间的协方差,因此载荷
测度了第
个变量与第
个公共因子之间的关联
。
原始变量的协方差矩阵
其中中每一个对角线元素
其中
体现了共同性(communality),指由
个公共因子贡献的方差。
称为唯一性(uniqueness)或个体方差(specific variance),指无法由公共因子贡献的方差部分。
我们也可以看和
之间的关系:
。
1.1、基本方法
已知矩阵形式模型:
如何估计载荷矩阵?
上面得到的因子模型的协方差矩阵分解:
对比以下两个式子:
当最后个特征值很小的时候,我们可以忽略掉
,此时:
,此时我们定义:
,即为
的前
列;得到了
,我们就可以算出
:
,即理解为:
对角阵的每一个元素就是
的方差没有被
刻画的部分。
在样本层面,可用样本协方差矩阵
代替。这种估计方法称为主成分法 (Principal component method),或主成分解(Principal component solution)
定理(主成分解)
为样本协方差矩阵
的特征值-标准化特征向量,其中
。 记
为公共因子的数目。那么因子载荷矩阵估计的主成分解为
。估计的个体方差是
的对角元素,即
,其中
(
代表个体方差,
代表总方差,
代表共同度
)。
【小贴士】
1.2、因子的方差(信息量)贡献
第个因子对总方差
的贡献为
(主成分中,第
个主成分的方差贡献也为
,要注意的是主成分当中,
代表的是第
个主成分的方差;但是在因子分析当中,各个公共因子的方差我们假设为1,
代表的是同一个公共因子(例如
)对
的方差贡献之和
),贡献比例为
。
以第2个因子为例,我们知道
由对应的公共因子
贡献的方差是
,则总方差
也可以看做是
的方差之和,则第2个因子对总方差的贡献为
,即为载荷矩阵
的第2列的平方和,载荷矩阵
的第2列的估计为
,
。
1.3、基于标准化变量的主成分法
正如主成分分析中提到的,当变量的度量单位/量纲相差很多时,建议使用标准化后的变量(相关系数矩阵)进行因子分析,这等价于基于样本相关系数矩阵使用主成分法,即将
换成
。
比
更常用,是大多数软件包的默认设置。
基于标准化变量的主成分分析详见《机器学习——数据降维——主成分分析(PCA)和奇异值分解(SVD)》第一章第4节。
1.4、因子的个数的选择
心理学,社会科学或者其他行为科学的研究者们可能基于他们的具体领域或经验来指定因子的个数。
如果没有先验信息(例如前面对于各科成绩,我们事先确定一个公共因子——语言能力),如何确定?
因此,可以参考主成分分析,评估被忽略的特征值的贡献,即可以使用百分比截点、平均截点和碎石图。主成分个数的选择详见《机器学习——数据降维——主成分分析(PCA)和奇异值分解(SVD)》第一章第5节。
1.5、案例
一个12岁的女孩对她身边的7个人进行9分制评分。评分基于五个维度进行的,分别是“友好(kind)”、“聪明(intelligent)”、“快乐(happy)”、“受人喜爱(likeable)”和“公正( just)”:
1.5.1、计算相关系数矩阵
corr=data.corr()
corr
输出:
根据相关系数的大小,变量可能分为两组:{0, 2, 3} 和 {1, 4},因此我们期望通过2个因子解释变量间的相关性。
1.5.2、求载荷矩阵
eigVals,eigVects=np.linalg.eig(np.mat(corr)) #协方差矩阵的特征值和特征向量
Loading=np.sqrt(eigVals)*np.array(eigVects) #主成分乘上权重,λ的开平方,注意:此时eigVects中一列是代表着一个特征向量
Loading
输出:
array([[ 0.9694553 , 0.23114797, -0.07845059, nan, -0.02392768],
[ 0.5194021 , -0.80694535, 0.28034884, nan, -0.02156826],
[ 0.78451739, 0.58724124, 0.16754548, nan, 0.10774369],
[ 0.97087045, 0.20994906, -0.03935088, nan, -0.10855173],
[ 0.70396444, -0.66692688, -0.23125766, nan, 0.07850152]])
我们使用个因子,基于相关系数矩阵
的主成分法得到的载荷矩阵估计(
)、共同度及个体方差如下:
L_=pd.DataFrame(Loading[:,:2],columns=['lj1','lj2'],index=['Kind','Intelligent','Happy','Likeabel','Just'])
L_['共同度']=(Loading[:,:2]*Loading[:,:2]).sum(axis=1)
L_['个体方差']=1-L_['共同度']
L_
输出:
由和
可知这两个公共因子是如何决定原始变量的,如
,
,
,三个原始变量在两个公共因子的表现(权重)基本都不低,这样就导致一个问题:公共因子的可解释性很差。在后面的章节我们会介绍一种方法——因子旋转,来解决此类问题。
1.5.3、方差贡献和方差贡献率
eigVals[:2].sum()/eigVals.sum()
输出:
0.9613695373197961
通过两个公共因子能刻画96%的方差,通过以上碎石图能够更加直观的看出:
1.5.4、验算:根据,用两个公共因子能否复原原来的协方差矩阵
(或者相关系数矩阵
)?
pd.DataFrame(np.dot(Loading[:,:2],(Loading[:,:2].T))+np.diag(1-(Loading[:,:2]*Loading[:,:2]).sum(axis=1)))
输出:
计算过程:对比原来的相关系数矩阵
:
可以看出,很好的复原了原来的相关性系数矩阵,由两个公共因子刻画原始变量是足够的。
在主成分方法中,我们忽略,对
或
进行谱分解。
而主因子法/主轴法(principal factor/axis method),则使用一个初始的估计值,从而对
或
使用与主成分方法相同
的操作进行因子分析。
我们可以迭代地更新估计值以及
或
的分解,直到收敛。
大致步骤如下:
给定一个初始的估计值,常用的
初值:使用
时,初值为
;使用
时,初值为
。
对或
使用与主成分方法相同的操作(谱分解)进行因子分析,得到载荷矩阵
的估计。
重复2和3步骤,使得越来越接近真值(收敛)。
缺陷:
因为或
有可能不是正定的,这个方法有可能得到负的特征值,使得结果较难解释(负的方差),如下图。
下表对由主成分和主因子法得到的载荷估计进行比较:
【小贴士】
性质:正定矩阵的特征值都是正的。
当样本和
服从联合正态分布,
也因此独立同分布地服从
分布时(其中
),
的似然函数可以如下表示:
其中(
表示
的极大似然估计)已经代入上式,将
代入上式,然后极大化这一个方程,
和
的极大似然估计就可以通过迭代计算得到。
因子是不可观测的,我们可以将其看作虚拟的,所以其实不唯一的。故以上因子模型等价于,其中
,
,
是满足
的任意正交矩阵。
【小贴士】
任意正交阵乘以其自身转置的结果,为单位阵。
新的载荷矩阵仍然满足
。
新的仍然满足
。
所以因子及其载荷矩阵并不唯一,可以按照任意的正交矩阵提供的方向旋转。这种不唯一性为“因子旋转”提供了理论基础。
我们的最终目标是寻找使因子及载荷结构更简单、解释更清晰的旋转方向。
我们旋转因子就相当于旋转载荷矩阵
,其本质上是在做同一件事情。我们对处理载荷矩阵
更加熟悉,载荷矩阵
代表原始变量和公共因子之间的关系(协方差/相关系数,取决于使用协方差矩阵还是用相关系数矩阵进行谱分解)。
我们希望得到的是,每个原始变量都由某个因子主要决定(对应载荷数值很大),而与其他因子关系不大(对应载荷绝对值接近0,则此公共因子对原始变量没有作用),即我们想要得到一个结果尽量简单(稀疏)的载荷矩阵,便于我们解释。
从几何的角度,的第
行的载荷构成了原始变量
在因子/载荷空间的坐标。所以因子旋转的目标,是让坐标轴靠近尽可能多的点。
回到12岁女孩调查的案例:
上图中的载荷矩阵我们可以投射到如下的载荷(因子)空间当中的5个点。载荷矩阵的每一行可以表示为一个点的坐标。需要注意的是,图中的直角三角形的,根据勾股定理的,即对应的载荷平方和,等于共同度,共同度,即点到原点的距离平方。
总结:因子旋转的目的是得到更加好解释、定义和理解的因子方向(因为因子是虚拟的)。 即通过“旋转坐标轴”的方式,尽可能使新的坐标轴靠近更多的点,这边“旋转坐标轴”有两种方式:正交旋转和斜交旋转。
正交旋转(Orthogonal rotation):
3.1、图像法
如果,我们可以通过观察因子载荷坐标系决定如何旋转坐标轴。
我们选择一个角度来让坐标轴尽可能靠近更多的点 。新的旋转载荷
可以通过
(旋转坐标轴)得到,其中
。
矩阵旋转的角度:顺时针旋转则为负值,逆时针旋转则为正值,更多关于旋转矩阵的内容,详见《线性代数——线性变换——旋转矩阵(泰勒公式、虚数、欧拉公式)》。
通过的旋转,我们得到了下面的载荷矩阵:
旋转后的载荷与原载荷对比:旋转之后的载荷,有一些很大(下图红色框),有一些接近于0(下图蓝色框),无限接近于0的我们可以忽略,这样就会使结果更加好解释、简洁。
旋转后的载荷很容易解释:
第一个因子主要由intelligence和just构成,可解释为人的逻辑思维能力。
第二个因子与变量kind, happy, likeable高度相关,可描述为亲和力。
3.2、最大方差法——最常用的正交因子旋转
使用图像法来正交旋转局限于,因为只有二维的空间,才能在图像上呈现出来。
对,有更多解析的方法已经被提出。最常用的为最大方差法(Varimax method),也就是寻找能够最大化载荷矩阵中每一列载荷平方的方差的旋转载荷。
最大方差法(Varimax method)原理:
对,我们也可以用最大方差法,设因子载荷矩阵
,正交阵
,旋转过后的载荷矩阵设为
,我们要做的是,选定合适的
可以令旋转过后的载荷矩阵
的列向量的方差之和(
,
)达到最大。
当载荷矩阵的列时,我们可以逐次对每两个因子进行上述旋转,直至
个因子全部配对旋转,即需要旋转
次,全部旋转完毕算作一轮循环。一般来说,一轮循环是不够的,需要经过多轮旋转,直至方差无法再增大为止。
回到12岁女孩的数据,最大方差法得到的旋转因子载荷与图像法得到的旋转十分接近:
斜交旋转(Oblique rotation):
回想12岁女孩的例子,如果旋转后的坐标轴允许不再垂直(即斜交旋转),代表的轴可以更加靠近第1个和第4个变量对应的点。
正交旋转的好处是:角度和距离都保持不变。共同度也不变。
不像正交旋转中使用正交矩阵,斜交旋转使用一个更一般的非奇异变换矩阵
(可逆即可)来得到
,那么
,因此新的因子之间是相关的,不是正交的。
由于距离和角度不再保持不变,的共同度与
的也不同。
斜交旋转的好处是,当不要求坐标轴相互垂直时,旋转后的坐标轴更容易“穿过”多数坐标点。
例:我们收集了25个家庭的第一胎和第二胎婴儿头围测量数据(头长和头宽),如下图,右图为相关系数矩阵:
直观的选择2个公共因子,分别做正交旋转(下图左)和斜交旋转(下图右) :
与最大方差旋转载荷(正交旋转)相比,斜交旋转载荷的结构更加简洁(更加0-1两极化),但解释起来完全一样,即主要解释第二胎的头长和头宽,
主要解释第一胎的头长和头宽。
斜交旋转得到的两个坐标轴的夹角为38°,两个旋转后的因子之间的相关性则为0.79(可以由的非对角元得到,或由
得到)。故我们总结一个结论:两坐标轴间的夹角小于45°,可只选择一个因子。
有时研究者则希望得到因子得分(Factor score),,即每个因子在不同个体上的取值,从而我们可以
查看不同个体的因子表现情况(比如智力问题)
将因子得分作为“观测值”后续进行其他分析,如分类(降维之后再分类)
我们先回顾回归模型:
在标准线性回归中我们需要找到是误差最小的, 即预测的
值与真实的
值之间的差值。
使用矩阵表示将会是的求解和程序更为简单:
将对
求导可得:
【注意】
矩阵求导性质:
使其等于0,便可得到:
求得:
类比回归模型,我们在以下的因子模型当中
因子模型:
前面我们已经将载荷矩阵估计出来了,现在目标是估计
:
。
由于的方差不相同,我们可以通过加权最小二乘法来估计
:
。
【小贴士】
加权最小二乘法的残差平方和为
,其中
,和标准最小二乘法的差别在于:
使得具有较小的方差的样本具有较大权重,经过这般调整,使其方差相同。最后求得
,详细加权最小二乘估计可见《加权最小二乘法与局部加权线性回归》
将已估计的参数,
和
(样本均值)代入上式:
,最后得到的
是一个
维的矩阵。
基于正态假设:假设和
服从
则在给定
时的条件分布为正态分布,均值为
,于是我们就可以利用给定的
来估计
。
我们就可以得到第个因子得分的估计:
,或者
【小贴士】
子向量的条件正态性:
假设
,现在对
、
、
以第
个元素为界进行分割如下:
,
,
,这里
是
的,并且
。
于是在给定
时,
的条件分布仍然是多元正态:
。
注意:
是关于
的线性方程,同时
不依赖
。
sklearn当中也有因子分析的库sklearn.decomposition.FactorAnalysis,但是是采用极大似然估计的方式计算结果,不能旋转。不能旋转的因子分析对原始维度缺少一定的解释力,并且因子间可能存在一定的相关性,达不到因子分析的既定效果。
故我们可以用factor_analyzer.FactorAnalyzer:既可做因子分析也能做因子的旋转,格式如下:FactorAnalyzer(rotation=None, n_factors=n, method='principal')
案例:回到第6章中考试成绩的例子。52位学生6门功课的考试分数: 到
依次表示数学、物理、化学、语文、历史、英语成绩。部分数据如下:
同案例的主成分分析(PCA)过程可见《机器学习——数据降维——主成分分析(PCA)和奇异值分解(SVD)》
目的:对比于主成分分析(PCA),因子分析可以更好的解释这两科的差异性,可以由“文科”和“理科”来刻画,或者是否有其他更合理解释角度?
2.1、计算相关系数矩阵
corr=data.corr()
corr
输出:
从相关性系数矩阵上看,前三个变量(,
,
)更加相关,后三个变量(
,
,
)更加相关,我们暂定用
个公共因子来刻画,待估计的因子模型初步定为:
。
2.2、估计载荷矩阵
2.2.1、极大似然法
from factor_analyzer import FactorAnalyzer
fa = FactorAnalyzer(rotation=None, #是否旋转因子
n_factors=2, #取两个因子
method='ml' #极大似然估计
)
data_=fa.fit_transform(data)
fa.loadings_ #载荷矩阵
输出:
array([[-0.67553954, 0.5618195 ],
[-0.59919972, 0.42715296],
[-0.48652622, 0.65618063],
[ 0.91689514, 0.1039815 ],
[ 0.85579329, 0.23917605],
[ 0.88275542, 0.26616829]])
取2个公共因子的载荷矩阵(极大似然估计)如上。
fa.get_factor_variance()
输出:
(array([3.40443772, 1.06753672]),
array([0.56740629, 0.17792279]),
array([0.56740629, 0.74532907]))
第一行表示前两个因子对总体方差的贡献,第二行表示方差贡献的占比,第三行表示方差贡献的累积占比,我们可以看出,前两个因子的方差贡献率在74.53%。
2.2.2、主成分法
from factor_analyzer import FactorAnalyzer
fa = FactorAnalyzer(rotation=None, #是否旋转因子
n_factors=2, #取两个因子
method='principal' #主成分法
)
data_=fa.fit_transform(data)
fa.loadings_ #载荷矩阵
输出:
array([[-0.79365794, 0.42244881],
[-0.73419111, 0.40079553],
[-0.63972828, 0.63215697],
[ 0.88829277, 0.31294912],
[ 0.81009848, 0.46605162],
[ 0.82849201, 0.45674661]])
取2个公共因子的载荷矩阵(主成分法)如上,注意:以上是未经过旋转的载荷矩阵。
fa.get_factor_variance()
输出:
(array([3.70990438, 1.26248122]),
array([0.6183174 , 0.21041354]),
array([0.6183174 , 0.82873093]))
第一行表示前两个因子对总体方差的贡献,第二行表示方差贡献的占比,第三行表示方差贡献的累积占比,我们可以看出,前两个因子的方差贡献率在82.87%。比上面的极大释然估计的方差贡献率(74.53%)要高的,极大释然估计是基于正态分布的,也许原始样本分布并不是很接近“正态分布”。所以我们后续的结果倾向于继续使用主成分法来讨论。
2.3、计算旋转因子载荷——基于主成分法
from factor_analyzer import FactorAnalyzer
fa = FactorAnalyzer(rotation='varimax', #最大方差法因子旋转
n_factors=2, #取两个因子
method='principal' #主成分法
)
data_=fa.fit_transform(data)
fa.loadings_ #载荷矩阵
输出:
取2个公共因子的载荷矩阵(主成分法)如上。
fa.get_factor_variance()
输出:
(array([2.66060044, 2.31178516]),
array([0.44343341, 0.38529753]),
array([0.44343341, 0.82873093]))
第一行表示前两个因子对总体方差的贡献,第二行表示方差贡献的占比,第三行表示方差贡献的累积占比,我们可以看出,前两个因子的方差贡献率在82.87%。与未旋转的方差贡献率相比没有变化。
但是两个因子的载荷与未旋转之前相比差了很多:
两个公共因子,我们可以画图展现出来更加直观:
import matplotlib.pyplot as plt
plt.rcParams['font.sans-serif']=['SimHei'] #用来显示中文标签
plt.rcParams['axes.unicode_minus']=False #用来正常显示负号
fig=plt.figure(figsize=(10,4)) #表示绘制图形的画板尺寸为6*4.5;
ax=fig.add_subplot(1,2,1)
loading=fa_1.loadings_ #未旋转的因子载荷
plt.scatter(loading[:,[0]],loading[:,[1]])
plt.xlabel('第一个公共因子')
plt.ylabel('第二个公共因子')
for i in range(len(loading)):
plt.text(loading[i,0],loading[i,1],'Y%s'%(i+1),ha='left',va='top',fontsize=12,rotation=0,alpha=50) #columns.index(i)返回下标,#ha=‘right'表示点在注释右边,va='bottom'表示点在注释底部,alpha表示透明程度
plt.title('未旋转的因子载荷')
ax=fig.add_subplot(1,2,2)
loading=fa_2.loadings_ #旋转的因子载荷
plt.scatter(loading[:,[0]],loading[:,[1]])
plt.xlabel('第一个公共因子')
plt.ylabel('第二个公共因子')
for i in range(len(loading)):
plt.text(loading[i,0],loading[i,1],'Y%s'%(i+1),ha='left',va='top',fontsize=12,rotation=0,alpha=50) #columns.index(i)返回下标,#ha=‘right'表示点在注释右边,va='bottom'表示点在注释底部,alpha表示透明程度
plt.title('旋转过后的因子载荷')
输出:
从图中我们可以看到,旋转过后的因子载荷矩阵,更加两级分化(更靠近轴和
轴),解释起来将更加清晰。
旋转过后的公共因子,第一个公共因子主要决定后面三个变量(,
,
,即语文、英语、历史),对应的可以概括为“文科因子” ,第二个公共因子主要决定前面三个变量(
,
,
,即数学、物理、化学),对应的可以概括为“理科因子” 。即我们通过因子分析,可以将我们的变量分成两类,具体分类如下:
2.4、计算样本因子得分——基于主成分法
即计算所有的学生在这两个因子上面的表现情况:
from factor_analyzer import FactorAnalyzer
fa_2 = FactorAnalyzer(rotation='varimax', #最大方差法因子旋转
n_factors=2, #取两个因子
method='principal' #主成分法
)
data_=fa_2.fit_transform(data)
data_
输出:
array([[ 0.66680653, -0.69388904],
[-1.08617442, -0.15723761],
[-1.61684799, -1.90160396],
[-0.72920389, 0.15382713],
[-1.76907501, -1.13891434],
[-1.85801275, 0.64436162],
[-1.31915844, 1.26530921],
[-1.74117705, -1.23097618],
[ 0.95725666, -0.6764035 ],
[-0.84648864, 0.35102727],
[-0.90511521, -0.1115654 ],
[ 0.57900914, -0.24869373],
[-0.30651906, 1.18778613],
[ 0.58064712, 0.56696106],
[-0.77862214, -0.8278795 ],
[-0.60582854, 0.58630962],
[ 0.06228757, 0.58790371],
[ 1.26041827, 0.09990526],
[ 1.6165137 , -0.36917334],
[ 0.89554779, 0.99821778],
[ 1.37610116, 0.20272853],
[-0.05046723, 1.42552427],
[ 0.12385714, 1.64671775],
[-0.10702467, 0.24068394],
[-0.73672797, 1.32010354],
[ 0.90379062, 1.71032496],
[-0.11252153, -0.69081664],
[-0.1599815 , -1.738235 ],
[ 0.36325364, -0.35529494],
[ 2.16545793, -1.06019214],
[ 0.5120452 , -1.75445471],
[ 0.24420505, -1.47332172],
[ 1.41023729, 1.35395876],
[-0.79261961, 0.83837722],
[-0.03566869, 0.40380043],
[-0.79881006, -0.63984564],
[-0.13342206, -1.64587618],
[-1.21747732, 0.92526294],
[ 0.35162225, -0.20707309],
[ 0.02153877, 1.42305047],
[ 0.78520054, -0.03781809],
[-0.34213278, -0.17680972],
[ 0.05145438, 1.1367464 ],
[-1.08960807, -0.70504028],
[-0.9456918 , 2.06015672],
[-0.56815626, -1.00460889],
[ 0.58396812, 0.36319028],
[-0.1713918 , -1.01788887],
[ 2.3945996 , -0.90107041],
[ 0.09178151, -0.84650009],
[ 1.61876748, 0.2735249 ],
[ 1.20755702, -0.1545769 ]])
我们已知:第一个公共因子可以概括为“文科因子” ,第二个公共因子可以概括为“理科因子”。所以,例如第一个学生:则表现为文科好,理科差的情况,第二个学生则是文理都相对较差。注意:因子都是正向去决定变量的,正值则代表在因子的表现上较好,负值则代表在因子的表现上较差。
我们可以将所有学生在因子上的表现画在图上:
fig=plt.figure(figsize=(10,10)) #表示绘制图形的画板尺寸为6*4.5;
plt.scatter(data_[:,[0]],data_[:,[1]])
plt.xlabel('文科公共因子')
plt.ylabel('理科公共因子')
#画横纵坐标参考线
plt.hlines(y=0,xmin=-2,xmax=2.5,linestyles='dashdot')
plt.vlines(x=0,ymin=-2,ymax=2.5,linestyles='dashdot')
#画样本点标签
for i in range(len(data_)):
plt.text(data_[i,0],data_[i,1],'Y%s'%(i+1),ha='left',va='top',fontsize=10,rotation=0,alpha=50) #columns.index(i)返回下标,#ha=‘right'表示点在注释右边,va='bottom'表示点在注释底部,alpha表示透明程度
#画原始参考坐标系
for i in range(len(loading)):
plt.annotate('Y%s'%(i+1) #箭头的文字
,xy=(0,0) #箭头的终点
,xytext=(loading[i,0]*2,loading[i,1]*2) #起点
,color='r' #文字的类型
,arrowprops=dict(arrowstyle="<-",color='red',connectionstyle="arc3") #箭头的样式
)
#打标题
plt.title('因子得分')
输出:
我们可以将各个同学在因子空间上的得分分成四个象限:第一象限即可以表示为“学霸”类型,第二和第四象限可以表示为“偏科”类型,第三象限即为要“好好努力”类型。
同样我们可以将原始变量空间表现在我们的因子载荷空间上(图中的红色坐标系)。我们发现:,
,
主要由第二个因子决定,
,
,
主要由第一个因子决定。
区别:
联系:
因子分析可以很好地满足维度分析的需求;
对于没有业务经验的数据分析人员来讲,是通过观察每个原始变量在因子上的权重绝对值来给因子取名成的。而对于业务知识丰富的数据分析人员,已经对变量的分类有一个预判,并通过进行不同的变量转换(标准化)方式和旋转方式使得预判别为同一组的原始变量在共同的因子上权重绝对值最大化。所以因子分析的要点在于选择变量转换方式。
因子分析作为维度分析的手段,是构造合理的聚类模型的有效步骤。