# ☀️机器学习入门☀️(四) PCA 和 LDA 降维算法 | 附加小练习（文末送书）

1. PCA 主成分分析

1.1 算法简介

1.2 实现思路

1.3 公式推算

1.3.1 PCA顺序排序

1.3.2 样本协方差矩阵

1.4 小练习

2. LDA 线性判断分析

2.1 算法简介

2.2 实现思路

2.3 小练习

3. 福利送书

1. PCA 主成分分析

1.1 算法简介

1.2 实现思路

1.3 公式推算

1.3.1 PCA顺序排序

1.3.2 样本协方差矩阵

1.4 小练习

from PIL import Image
import numpy as np
import os
from ex1.clustering_performance import clusteringMetrics
from sklearn.cluster import KMeans
from sklearn.decomposition import PCA
import matplotlib.pyplot as plt
plt.rcParams['font.sans-serif'] = 'SimHei'
plt.rcParams['axes.unicode_minus'] = False
def getImage(path):
images = []
for root, dirs, files in os.walk(path):
if len(dirs) == 0:
images.append([root + "\\" + x for x in files])
return images
# 加载图片
images_files = getImage('face_images')
y = []
all_imgs = []
for i in range(len(images_files)):
y.append(i)
imgs = []
for j in range(len(images_files[i])):
img = np.array(Image.open(images_files[i][j]).convert("L"))  # 灰度
# img = np.array(Image.open(images_files[i][j])) #RGB
imgs.append(img)
all_imgs.append(imgs)
# 可视化图片
w, h = 180, 200
pic_all = np.zeros((h * 10, w * 10))  # gray
for i in range(10):
for j in range(10):
pic_all[i * h:(i + 1) * h, j * w:(j + 1) * w] = all_imgs[i][j]
pic_all = np.uint8(pic_all)
pic_all = Image.fromarray(pic_all)
pic_all.show()
# 构造输入X
label = []
X = []
for i in range(len(all_imgs)):
for j in all_imgs[i]:
label.append(i)
# temp = j.reshape(h * w, 3) #RGB
temp = j.reshape(h * w)  # GRAY
X.append(temp)
def keams_in(X_Data, k):
kMeans1 = KMeans(k)
y_p = kMeans1.fit_predict(X_Data)
ACC, NMI, ARI = clusteringMetrics(label, y_p)
t = "ACC:{},NMI:{:.4f},ARI:{:.4f}".format(ACC, NMI, ARI)
print(t)
return ACC, NMI, ARI
# PCA
def pca(X_Data, n_component, height, weight):
X_Data = np.array(X_Data)
pca1 = PCA(n_component)
pca1.fit(X_Data)
faces = pca1.components_
faces = faces.reshape(n_component, height, weight)
X_t = pca1.transform(X_Data)
return faces, X_t
def draw(n_component, faces):
plt.figure(figsize=(10, 4))
for i in range(n_component):
plt.subplot(2, 5, i + 1)
plt.imshow(faces[i], cmap='gray')
plt.title(i + 1)
plt.xticks(())
plt.yticks(())
plt.show()
score = []
for i in range(10):
_, X_trans = pca(X, i + 1, h, w)
acc, nmi, ari = keams_in(X_trans, 10)
score.append([acc, nmi, ari])
score = np.array(score)
bar_width = 0.25
x = np.arange(1, 11)
plt.bar(x, score[:, 0], bar_width, align="center", color="orange", label="ACC", alpha=0.5)
plt.bar(x + bar_width, score[:, 1], bar_width, color="blue", align="center", label="NMI", alpha=0.5)
plt.bar(x + bar_width*2, score[:, 2], bar_width, color="red", align="center", label="ARI", alpha=0.5)
plt.xlabel("n_component")
plt.ylabel("精度")
plt.legend()
plt.show()

2. LDA 线性判断分析

2.1 算法简介

2.2 实现思路

(𝒛_𝟏 ) ̅和(𝒛_2 ) ̅离的越远越好

𝒁_𝒊 中的元素集中在(𝒛_𝒊 ) ̅附近越好

1.计算类内散度矩阵 Sw；

2.计算类间散度矩阵 Sb;

3.计算矩阵S的负一次方wSb;

4.计算S的负一次方wSb的最大的k个特征值和对应的k个特征向量(w1, w2, …, wk)，得到投影矩阵W

5.对样本集中的每一个样本特征xi转化为新的样本zi=WTxi

6.得到输出样本集〖{𝒛_𝒊,𝒚_𝒊}〗_(𝒊=𝟏)^𝒏.

2.3 小练习

from sklearn import datasets#引入数据集
from sklearn.neighbors import KNeighborsClassifier #KNN
from sklearn.decomposition import PCA
from sklearn.discriminant_analysis import LinearDiscriminantAnalysis
from sklearn.model_selection import train_test_split
import numpy as np
import matplotlib.pyplot as plt #plt用于显示图片
from matplotlib import offsetbox
def calLDA(k):
# LDA
lda = LinearDiscriminantAnalysis(n_components=k).fit(data,label) # n_components设置降维到n维度
dataLDA = lda.transform(data)  # 将规则应用于训练集
return dataLDA
def calPCA(k):
# PCA
pca = PCA(n_components=k).fit(data)
# 返回测试集和训练集降维后的数据集
dataPCA = pca.transform(data)
return dataPCA
def draw():
# matplotlib画图中中文显示会有问题，需要这两行设置默认字体
fig = plt.figure('example', figsize=(11, 6))
# plt.xlabel('X')
# plt.ylabel('Y')
# plt.xlim(xmax=9, xmin=-9)
# plt.ylim(ymax=9, ymin=-9)
color = ["red","yellow","blue","green","black","purple","pink","brown","gray","Orange"]
colors = []
for target in label:
colors.append(color[target])
plt.subplot(121)
plt.title("LDA 降维可视化")
plt.scatter(dataLDA.T[0], dataLDA.T[1], s=10,c=colors)
plt.subplot(122)
plt.title("PCA 降维可视化")
plt.scatter(dataPCA.T[0], dataPCA.T[1], s=10, c=colors)
#plt.legend()
plt.show()
def plot_embedding(X,title=None):
x_min, x_max = np.min(X, 0), np.max(X, 0)
X = (X - x_min) / (x_max - x_min)  # 对每一个维度进行0-1归一化，注意此时X只有两个维度
colors = ['#5dbe80', '#2d9ed8', '#a290c4', '#efab40', '#eb4e4f', '#929591','#ababab','#eeeeee','#aaaaaa','#213832']
ax = plt.subplot()
# 画出样本点
for i in range(X.shape[0]):  # 每一行代表一个样本
plt.text(X[i, 0], X[i, 1], str(label[i]),
# color=plt.cm.Set1(y[i] / 10.),
color=colors[label[i]],
fontdict={'weight': 'bold', 'size': 9})  # 在样本点所在位置画出样本点的数字标签
# 在样本点上画出缩略图，并保证缩略图够稀疏不至于相互覆盖
if hasattr(offsetbox, 'AnnotationBbox'):
shown_images = np.array([[1., 1.]])  # 假设最开始出现的缩略图在(1,1)位置上
for i in range(data.shape[0]):
dist = np.sum((X[i] - shown_images) ** 2, 1)  # 算出样本点与所有展示过的图片（shown_images）的距离
if np.min(dist) < 4e-3:  # 若最小的距离小于4e-3，即存在有两个样本点靠的很近的情况，则通过continue跳过展示该数字图片缩略图
continue
shown_images = np.r_[shown_images, [X[i]]]  # 展示缩略图的样本点通过纵向拼接加入到shown_images矩阵中
imagebox = offsetbox.AnnotationBbox(
X[i])
#plt.xticks([]), plt.yticks([])  # 不显示横纵坐标刻度
if title is not None:
plt.title(title)
plt.show()
dataLDA = calLDA(2)
dataPCA = calPCA(2)
#draw() #普通图
plt.rcParams['font.sans-serif'] = ['SimHei']
plt.rcParams['axes.unicode_minus'] = False
plot_embedding(dataLDA,"LDA 降维可视化")
plot_embedding(dataPCA,"PCA 降维可视化")

3. 福利送书

【作者简介】

|
8天前
|

74 3
|
5天前
|

11 0
|
10天前
|

【5月更文挑战第18天】探索机器学习中的决策树算法，一种基于树形结构的监督学习，常用于分类和回归。算法通过递归划分数据，选择最优特征以提高子集纯净度。优点包括直观、高效、健壮和可解释，但易过拟合、对连续数据处理不佳且不稳定。广泛应用于信贷风险评估、医疗诊断和商品推荐等领域。优化方法包括集成学习、特征工程、剪枝策略和参数调优。
25 5
|
11天前
|

【机器学习】K-means算法与PCA算法之间有什么联系？
【5月更文挑战第15天】【机器学习】K-means算法与PCA算法之间有什么联系？
37 1
|
11天前
|

【机器学习】维度灾难问题会如何影响K-means算法？
【5月更文挑战第15天】【机器学习】维度灾难问题会如何影响K-means算法？
28 0
|
12天前
|

【机器学习】聚类算法中，如何判断数据是否被“充分”地聚类，以便算法产生有意义的结果？
【5月更文挑战第14天】【机器学习】聚类算法中，如何判断数据是否被“充分”地聚类，以便算法产生有意义的结果？
39 1
|
12天前
|

【机器学习】可以利用K-means算法找到数据中的离群值吗？
【5月更文挑战第14天】【机器学习】可以利用K-means算法找到数据中的离群值吗？
36 0
|
13天前
|

30 5
|
1天前
|

5 0
|
3天前
|

m基于GA-GRU遗传优化门控循环单元网络的电力负荷数据预测算法matlab仿真

19 4