机器学习:对数据进行降维(PCA和SVD)
创作时间:
2025-01-22 04:43:42
作者:
@小白创作中心
机器学习:对数据进行降维(PCA和SVD)
数据降维是将高维数据转换为较低维度的过程,同时尽量保留数据中的关键信息。这有助于减少计算复杂性、减轻噪声影响,并可能揭示数据中的潜在模式。常用的降维技术包括主成分分析(PCA)、奇异值分解(SVD)等。
一、PCA
1.PCA是什么?
主成分分析(PCA)是一种降维技术,用于将数据投影到低维空间,同时尽可能保留数据的方差。使用 PCA 可以提高计算效率,减少噪音,并发现数据中的重要模式。
2.PCA的实现使用步骤
- 数据标准化:将数据缩放到均值为0、方差为1的标准范围,以确保不同特征对分析的贡献相同。
- 计算协方差矩阵:通过计算特征之间的协方差,来了解特征间的关系。
- 求解特征值和特征向量:对协方差矩阵进行特征值分解,得到特征值和对应的特征向量。
- 选择主成分:根据特征值的大小选择前几个最大的特征值所对应的特征向量,这些特征向量构成新的特征空间。
- 转换数据:将原始数据投影到新的特征空间中,得到降维后的数据。
3.PCA参数解释
from sklearn.decomposition import PCA
PCA(n_components=None, copy=True, whiten=False, svd_solver='auto', tol=0.0,
iterated_power='auto', random_state=None)
主要参数:
- n_components:这个参数可以帮我们指定希望PCA降维后的特征维度数目。简单来说:指定整数,表示要降维到的目标,【比如十维的数据,指定n_components=5,表示将十维数据降维到五维】如果为小数,表示累计方差百分比。0.9
- copy :类型:bool,True或者False,缺省时默认为True。
意义:表示是否在运行算法时,将原始训练数据复制一份。若为True,则运行PCA算法后,原始训练数据的值不会有任何改变,因为是在原始数据的副本上进行运算;若为False,则运行PCA算法后,原始训练数据的值会改,因为是在原始数据上进行降维计算。【按默认为True】 - whiten:判断是否进行白化。所谓白化,就是对降维后的数据的每个特征进行归一化,让方差都为1.对于PCA降维本身来说,一般不需要白化。如果你PCA降维后有后续的数据处理动作,可以考虑白化。默认值是False,即不进行白化。
主要属性:
- components_:array, shape (n_components, n_features) 指表示主成分系数矩阵
- explained_variance_:降维后的各主成分的方差值。方差值越大,则说明越是重要的主成分。
- explained_variance_ratio_:降维后的各主成分的方差值占总方差值的比例,这个比例越大,则越是重要的主成分。【一般看比例即可 >90%】
4.代码实现
- 这段代码是对鸢尾花的数据进行降维,然后使用逻辑回归进行分类
'''PCA降维只能捕捉线性关系,不适用于非线性数据'''
import pandas as pd
data = pd.read_excel('hua.xlsx')
x = data.iloc[:, :-1]
y = data.iloc[:, -1]
'''对特征进行降维'''
from sklearn.decomposition import PCA
pca = PCA(n_components=0.9) # 设置n_components=0.9表示保留足够的主成分 以解释至少90%的数据方差
pca.fit(x) # 使用数据 x 训练PCA模型,计算数据的主成分。
print(f"特征所占百分比:{sum(pca.explained_variance_ratio_)}")
print(pca.explained_variance_ratio_)
print(pca.explained_variance_)
new_x = pca.transform(x) # 将原始数据 x 投影到选定的主成分上 new_x = pca.fit_transform(x) 可以省去pca.fit(x)
print(new_x)
from sklearn.model_selection import train_test_split
x_train, x_test, y_train, y_test = \
train_test_split(new_x, y, test_size=0.2, random_state=0)
from sklearn.linear_model import LogisticRegression
lg = LogisticRegression(C=2)
lg.fit(x_train, y_train)
from sklearn import metrics
train_pre = lg.predict(x_train)
print(metrics.classification_report(y_train, train_pre))
test_pre = lg.predict(x_test)
print(metrics.classification_report(y_test, test_pre))
'''不进行降维'''
from sklearn.model_selection import train_test_split
x_train, x_test, y_train, y_test = \
train_test_split(x, y, test_size=0.2, random_state=0)
from sklearn.linear_model import LogisticRegression
lg = LogisticRegression()
lg.fit(x_train, y_train)
from sklearn import metrics
train_pre = lg.predict(x_train)
print(metrics.classification_report(y_train, train_pre))
test_pre = lg.predict(x_test)
print(metrics.classification_report(y_test, test_pre))
输出:
- 上面一个混淆矩阵是降维之后的
- 下面一个混淆矩阵是降维之前的
- 说明进行降维不一定能提高模型的正确率
特征所占百分比:0.9287327483408421
[0.84389796 0.08483479] # 主成分特征所占百分比
[1.2415529 0.12480997] # 主成分特征的方差
precision recall f1-score support
0 0.92 0.96 0.94 25
1 0.96 0.93 0.94 27
accuracy 0.94 52
macro avg 0.94 0.94 0.94 52
weighted avg 0.94 0.94 0.94 52
precision recall f1-score support
0 0.96 0.92 0.94 25
1 0.93 0.96 0.95 27
accuracy 0.94 52
macro avg 0.94 0.94 0.94 52
weighted avg 0.94 0.94 0.94 52
5.PCA的优缺点
- 优点:
- 1.计算方法简单,容易实现。
- 2.可以减少指标筛选的工作量。
- 3.消除变量间的多重共线性。
- 4.在一定程度上能减少噪声数据。
- 缺点:
- 1.特征必须是连续型变量。
- 2.无法解释降维后的数据是什么。
- 3.贡献率小的成分有可能更重要。
二、SVD
1.SVD是什么?
奇异值分解(SVD)是一种矩阵分解技术,用于将任意矩阵 A 分解为三个矩阵的乘积: ** A=UΣVT**
其中:
- U 是一个正交矩阵,包含了 A 的左奇异向量。
- Σ 是一个对角矩阵,包含了奇异值。
- VT 是 A 的右奇异向量的转置。
2.SVD的实现步骤
- 计算协方差矩阵(如果适用):对于数据矩阵,计算其协方差矩阵。
- 进行 SVD 分解:将矩阵 A 分解为 U, Σ, 和 VT,即 A=UΣVT。
- 提取奇异值:从 Σ 中提取奇异值,按降序排列。
- 选择主成分(如需要):选择前几个最大的奇异值对应的列,从 U 和 VT 中提取相应的向量。
- 构建低秩近似(如需要):使用选定的奇异值和对应的向量构建矩阵的低秩近似。
3.代码实现
- 因为SVD是对矩阵进行降维,所以先把图片转换成矩阵格式,即数组
- 然后对其进行奇异值分解,得到u,sig和vt三个矩阵
- 然后选取u矩阵前k行,sig的对角矩阵和vt矩阵前k列组合压缩之后的图片
import numpy as np
import matplotlib.pyplot as plt
from PIL import Image
def pic_compress(k, pic_array):
global u, sigma, vt, sig, new_pic
u, sigma, vt = np.linalg.svd(pic_array) # 进行奇异值分解
sig = np.eye(k) * sigma[:k]
new_pic = np.dot(np.dot(u[:, :k], sig), vt[:k, :])
size = u.shape[0] * k + sig.shape[0] * sig.shape[1] + k * vt.shape[1]
return new_pic, size
img = Image.open('a.jpg')
ori_img = np.array(img)
new_img, size = pic_compress(100, ori_img) # 压缩的维度
print('original size:' + str(ori_img.shape[0] * ori_img.shape[1]))
print('original size:' + str(size))
fig, ax = plt.subplots(1, 2)
ax[0].imshow(ori_img, cmap='gray')
ax[0].set_title('before compress')
ax[1].imshow(new_img, cmap='gray')
ax[1].set_title('after compress')
plt.show()
输出:
第一行是原图所占空间大小,第二行是压缩之后所占空间大小
original size:1365760
compress size:244700
总结
数据降维不一定能提高模型的正确率,但是可以帮助我们更快速地处理数据
热门推荐
香港西贡海岛探秘:厦门湾果冻海与桥咀洲天使之路
周庄古镇的绝美秋景打卡点
探访苏州水乡古镇:虎丘塔的秘密
秋冬打卡苏州水乡古镇:周庄、甪直、同里的绝美风光
山西花馍:春节餐桌上的非遗美味
深度剖析,葛天重案六组——犯罪侦查的艺术与智慧
唐探1900:老 IP 新火花,凭啥赢得观众心?
庙湾岛:珠海万山群岛中的一颗“海上明珠”
涠洲岛:火山与海的交响曲
唐山文旅新选择:探访开滦与启新博物馆,感受百年工业魅力
唐山南湖春节灯会:三大主题灯区+花车巡游+无人机表演,打造沉浸式体验
为什么明明窗户关紧了,家里却总是漏风?解密四个关键问题
公主病:不只是身体疼痛,还有心理健康隐患
爱与规矩:如何避免孩子患上“公主病”
九峰山风貌提升工程:自然与文化的完美融合
原来上海滩真有一个斧头帮,不仅不欺压良善,还惩奸除恶
大年初五:接财神与北方饺子的文化盛宴
闹大了!李玫瑾连发三文批评《繁花》登上热搜,评论区已沦陷!
三亚冬季度假:必打卡三大岛屿
三亚尾波冲浪:458元包船,新手也能玩!
冬日打卡:三亚亚龙湾&呀诺达热带雨林
新疆赛里木湖:四季如画,美到窒息!
赛里木湖:秋冬摄影团的最佳目的地
秋冬徒步打卡:赛里木湖的绝美风光
GB/T 1355 vs LS/T 3244:面粉选购不再困惑
新国标引领面粉产业转型升级:地方经济的新机遇
新标准引领新变革:2025年中国面粉行业高质量发展之路
冠心病,如何防范,你关心“它”了吗?
衣服粘到油渍怎么办?别担心,试一试这些妙招
春节档三强争霸:中国传统文化的现代演绎