【机器学习】主成分分析(PCA)技术对鸢尾花数据集进行降维

目标

本实验通过主成分分析(PCA)技术对鸢尾花数据集进行降维,旨在:使用PCA将原始4维数据降到2维,并进行可视化。分析降维前后数据的分布和类别区分情况。评估PCA对数据方差解释率的贡献,以便在最少维度中保留最多信息。

环境

Python编程语言

Scikit-learn库

Matplotlib(用于数据可视化)

NumPy和Pandas库(用于数据处理)

Jupyter Notebook或类似IDE(用于代码编写和结果展示)

实验数据集

本实验使用的是鸢尾花数据集(Iris dataset),它是一个经典的多分类数据集,包含150个样本,4个特征(花萼长度、花萼宽度、花瓣长度、花瓣宽度),以及3个目标类别(Setosa、Versicolor、Virginica)。

步骤

1. 数据加载与初步探索

加载鸢尾花数据集,获取特征数据X和目标标签y。

2. 标准化特征

使用StandardScaler对特征数据进行标准化,使每个特征的均值为0,方差为1,以便消除量纲差异。

3. 原始数据可视化

使绘制原始数据的前两个特征,以便在降维前观察数据的分布。

4. 应用PCA降维

使用PCA将标准化后的数据从4维降到2维。

5. 降维后数据可视化

将降维后的2维数据进行可视化,用颜色区分类别,展示PCA在二维空间中的数据表现。

6. 方差解释率分析

计算每个主成分对方差的解释率,并绘制累计方差解释率图,观察PCA如何保留主要信息。

结果展示

原始数据的前两个特征图:展示了降维前的原始数据(4维中的两个特征)的分布情况。

降维后的2维数据图:在降维后的二维空间中显示各类别数据点的分布情况,展示了PCA保留的主要信息。

累计方差解释率图:通过累计方差解释率图观察不同数量主成分对信息量的保留情况,以帮助决定在降维中需要保留的维度数。

实验代码

以下是一个PCA实现的实验代码(使用鸢尾花数据集):

导入必要的库

imporimport numpy as np  # 数值计算库,用于数组操作
import matplotlib.pyplot as plt  # 绘图库,用于数据可视化
from sklearn.datasets import load_iris  # 数据集模块,用于加载鸢尾花数据集
from sklearn.preprocessing import StandardScaler  # 数据标准化模块
from sklearn.decomposition import PCA  # 主成分分析模块

加载鸢尾花数据集(Iris Dataset)

# 加载鸢尾花数据集,X为特征数据,y为类别标签,target_names为类别名称
iris = load_iris()
X = iris.data  # 特征矩阵 (150x4)
y = iris.target  # 类别标签 (0, 1, 2)
target_names = iris.target_names  # 类别名称 ('setosa', 'versicolor', 'virginica')

数据标准化

# 通过StandardScaler将数据进行标准化,使每个特征均值为0,方差为1,消除量纲差异
scaler = StandardScaler()
X_standardized = scaler.fit_transform(X)

原始数据的前两个特征可视化(4维降到2维前的对比)

# 可视化原始数据的前两个特征,以便与PCA降维后的数据进行对比
plt.figure(figsize=(10, 8))  # 增加图形大小
colors = ["navy", "turquoise", "darkorange"]
markers = ['o', 's', 'x']  # 为每个类别设置不同的标记点样式
target_names = ["Setosa", "Versicolour", "Virginica"]
for i, color, marker, label in zip(range(len(target_names)), colors, markers, target_names):
    plt.scatter(
        X[y == i, 0], X[y == i, 1],  # 前两个特征
        color=color, alpha=0.7, edgecolor='k', label=label, marker=marker, s=100
    )


# 设置标题和坐标轴标签的字体
plt.xlabel("Feature 1 (Sepal length)", fontsize=14, fontweight='bold')
plt.ylabel("Feature 2 (Sepal width)", fontsize=14, fontweight='bold')
plt.title("Original Data: First Two Features", fontsize=16, fontweight='bold')

# 添加网格线和图例
plt.grid(color='gray', linestyle='--', linewidth=0.5, alpha=0.7)
plt.legend(fontsize=12, frameon=True, shadow=True, loc="upper right")

# 美化刻度
plt.xticks(fontsxize=12)
plt.yticks(fontsize=12)

# 调整图形边距
plt.tight_layout()
plt.show()

图1

应用PCA将数据降维到2维

# 使用PCA将数据从4维降到2维,以便在2D图中进行可视化
pca = PCA(n_components=2)# 设置降维的目标维度为2
X_pca = pca.fit_transform(X_standardized)# 对标准化数据进行PCA降维

降维后的数据可视化

# 可视化降维后的2维数据,展示PCA在2维空间中重构的主要信息
plt.figure(figsize=(10, 8))  # 调整图形大小


colors = ["navy", "turquoise", "darkorange"]  # 定义颜色
markers = ['o', 's', 'x']  # 不同类别的标记点样式
target_names = ["Setosa", "Versicolour", "Virginica"]

# 绘制降维后的数据散点图
for i, color, marker, label in zip(range(len(target_names)), colors, markers, target_names):
    plt.scatter(
        X_pca[y == i, 0], X_pca[y == i, 1],  # 主成分 1 和 2
        color=color, alpha=0.7, edgecolor='k', label=label, marker=marker, s=120
    )


# 设置标题和轴标签
plt.xlabel("Principal Component 1", fontsize=14, fontweight='bold')
plt.ylabel("Principal Component 2", fontsize=14, fontweight='bold')
plt.title("PCA: Data Projected to 2D", fontsize=16, fontweight='bold')


# 添加网格线和图例
plt.grid(color='gray', linestyle='--', linewidth=0.5, alpha=0.7)
plt.legend(fontsize=12, frameon=True, shadow=True, loc="best")


# 优化刻度
plt.xticks(fontsize=12)
plt.yticks(fontsize=12)


# 调整图形布局
plt.tight_layout()
plt.show()

图2

方差解释率

pca_full = PCA()
pca_full.fit(X_standardized)
explained_variance_ratio = np.cumsum(pca_full.explained_variance_ratio_)  # 累计方差解释率
explained_variance_ratio

图3

使用完整的PCA分析各主成分的方差贡献率

# 绘制主成分数量与累计方差解释率的关系曲线

plt.figure(figsize=(10, 6))  # 调整图形大小
#xplained_variance_ratio 是累积方差解释率


# 绘制曲线
plt.plot(
    range(1, len(explained_variance_ratio) + 1),  # x轴:主成分数量
    explained_variance_ratio,  # y轴:累计方差解释率
    marker='o', color='royalblue', linestyle='-', linewidth=2, markersize=8, label="Cumulative Variance"
)


# 添加每个点的值标注
for i, value in enumerate(explained_variance_ratio, start=1):
    plt.text(i, value + 0.02, f"{value:.2f}", fontsize=10, ha='center', color='black')


# 设置坐标轴标签和标题
plt.xlabel("Number of Principal Components", fontsize=14, fontweight='bold')
plt.ylabel("Cumulative Explained Variance Ratio", fontsize=14, fontweight='bold')
plt.title("Cumulative Explained Variance by Number of Components", fontsize=16, fontweight='bold')


# 设置y轴范围
plt.ylim(0, 1.05)


# 添加网格线
plt.grid(color='gray', linestyle='--', linewidth=0.5, alpha=0.7)


# 优化刻度
plt.xticks(range(1, len(explained_variance_ratio) + 1), fontsize=12)
plt.yticks(fontsize=12)



# 添加图例
plt.legend(fontsize=12, loc="lower right")


# 显示图形
plt.tight_layout()
plt.show()

图4

降成三维如图所示

import matplotlib.pyplot as plt

# unused but required import for doing 3d projections with matplotlib < 3.2
import mpl_toolkits.mplot3d  # noqa: F401
import numpy as np

from sklearn import datasets, decomposition


np.random.seed(5)
iris = datasets.load_iris()
X = iris.data
y = iris.target
fig = plt.figure(1, figsize=(4, 3))
plt.clf()

ax = fig.add_subplot(111, projection="3d", elev=48, azim=134)
ax.set_position([0, 0, 0.95, 1])
plt.cla()
pca = decomposition.PCA(n_components=3)
pca.fit(X)
X = pca.transform(X)
for name, label in [("Setosa", 0), ("Versicolour", 1), ("Virginica", 2)]:
    ax.text3D(
        X[y == label, 0].mean(),
        X[y == label, 1].mean() + 1.5,
        X[y == label, 2].mean(),
        name,
        horizontalalignment="center",
        bbox=dict(alpha=0.5, edgecolor="w", facecolor="w"),
    )

# Reorder the labels to have colors matching the cluster results
y = np.choose(y, [1, 2, 0]).astype(float)
ax.scatter(X[:, 0], X[:, 1], X[:, 2], c=y, cmap=plt.cm.nipy_spectral, edgecolor="k")
ax.xaxis.set_ticklabels([])
ax.yaxis.set_ticklabels([])
ax.zaxis.set_ticklabels([])
plt.show()

图5

Pca与LAD对比

import matplotlib.pyplot as plt
from sklearn import datasets
from sklearn.decomposition import PCA
from sklearn.discriminant_analysis import LinearDiscriminantAnalysis

iris = datasets.load_iris()
X = iris.data
y = iris.target
target_names = iris.target_names
pca = PCA(n_components=2)
X_r = pca.fit(X).transform(X)
lda = LinearDiscriminantAnalysis(n_components=2)
X_r2 = lda.fit(X, y).transform(X)
# Percentage of variance explained for each components
print(
    "explained variance ratio (first two components): %s"
    % str(pca.explained_variance_ratio_)
)
plt.figure()
colors = ["navy", "turquoise", "darkorange"]
lw = 2
for color, i, target_name in zip(colors, [0, 1, 2], target_names):
    plt.scatter(
        X_r[y == i, 0], X_r[y == i, 1], color=color, alpha=0.8, lw=lw, label=target_name
    )
plt.legend(loc="best", shadow=False, scatterpoints=1)
plt.title("PCA of IRIS dataset")
plt.figure()
for color, i, target_name in zip(colors, [0, 1, 2], target_names):
    plt.scatter(
        X_r2[y == i, 0], X_r2[y == i, 1], alpha=0.8, color=color, label=target_name
    )
plt.legend(loc="best", shadow=False, scatterpoints=1)
plt.title("LDA of IRIS dataset")
plt.show()

PCA 降维

  • 方法:主成分分析(PCA),是一种无监督学习的降维方法。
  • 目标:在保持数据最大方差的基础上,找到新的特征空间,并将数据投影到二维平面上。
  • 图内容
    • 三种鸢尾花类别分别以不同颜色绘制(navy、turquoise、darkorange)。
    • 每个点代表一个样本,其位置是原始数据通过 PCA 投影后的坐标。
    • 特征解释:图中显示了原始数据在前两个主成分上的分布情况,主成分 1 和主成分 2 是捕捉最大方差的两个方向。
    • 适用场景:观察数据整体分布、类别间的分离程度和数据的主要变化趋势。

图6

LDA 降维

  • 方法:线性判别分析(LDA),是一种监督学习的降维方法。
  • 目标:最大化类别间的距离,同时最小化类别内的散度,以增强类别可分性。
  • 图内容
    • 同样用三种颜色表示三个类别。
    • 每个点的位置是原始数据通过 LDA 映射到二维空间后的坐标。
    • 特征解释:图中的两个轴是通过 LDA 计算得到的判别方向。LDA 优化了类别的可分性,因此可以看出不同类别之间的分离程度更明显。
    • 适用场景:分类问题的降维与可视化,强调类别间的分隔效果。


图7

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值