结合PCA降维的DBSCAN聚类方法(附Python代码)

news2025/1/12 4:56:48

目录

前言介绍:

1、PCA降维:

(1)概念解释:

(2)实现步骤:

(3)优劣相关: 

2、DBSCAN聚类:

(1)概念解释:

(2)算法原理:

(3)优劣相关:

代码实现:

0、数据准备:

1、PCA降维:

2、DBSCAN聚类:

3、代码汇总:

实现效果:

1、降维效果:

2、聚类效果:

写在最后:


前言介绍:

1、PCA降维:

(1)概念解释:

PCA,全称Principal Component Analysis,即主成分分析。是一种降维方法,实现途径是提取特征的主要成分,从而在保留主要特征的情况下,将高维数据压缩到低维空间。

在经过PCA处理后得到的低维数据,其实是原本的高维特征数据在某一低维平面上的投影只要维度较低,都可以视为平面,例如三维相对于四维空间也可以视为一个平面)。虽然降维的数据能够反映原本高维数据的大部分信息,但并不能反映原本高维空间的全部信息,因此要根据实际情况,加以鉴别使用

        (2)实现步骤:

        PCA主要通过6个步骤加以实现:

        1、标准化(将原始数据进行标准化,一般是去均值,如果特征在不同量级上,还要将矩阵除以标准差)

        具体:

        其中,E为原始矩阵,Emean为均值矩阵,Enorm为标准化矩阵。

        2、协方差(计算标准化数据集的协方差矩阵)

        具体:

        其中,Cov为协方差矩阵,m为样本的数量,Enorm为均值矩阵。

        3、特征值(计算协方差矩阵的特征值和特征向量)

        具体:

        假设实数λ、n行(原始矩阵E的列数即为n)1列的矩阵X(即n维向量)满足下式:

        则λ为Cov的特征值,其中Cov为协方差矩阵。

        4、K 特征(保留特征值最大的前K个特征(K是降维后,我们期望达到的维度))

        具体:

        若有多个特征值,则保留前K个最大的特征值,以满足之后的计算需求。

        5、K 向量(找到这K个特征值对应的特征向量)

        具体:

        通过步骤3中的公式得到每个特征值对应的特征向量。

        6、得降维(将标准化数据集乘以该K个特征向量,得到降维后的结果)

        具体:

        

        其中,Epca为最后要求得的PCA降维矩阵,Enorm为标准化矩阵,X1、X2、X3、...、Xk为对K个特征值对应的特征向量。

        (3)优劣相关: 

        优点:   

        1.PCA降维之后的各个主成分之间相互正交,可消除原始数据之间相互影响的因素

        2.PCA降维的计算过程并不复杂,因实现起来较简单容易

        3.在保留大部分主要信息的前提下,起到了降维,简便化计算效果。

        缺点

        1.特征主成分的定义具有模糊性解释性差

        2.PCA降维选取令原数据在新坐标轴上方差最大的主成分的标准,使得一些方差小的特征较易丢失,有损失重要信息的可能性

2、DBSCAN聚类:

        (1)概念解释:

        密度聚类亦称“基于密度的聚类”(Density-Based Clustering),此类算法假设聚类结构能通过样本分布的紧密程度确定。通常情形下,密度聚类算法从样本密度的角度来考察样本之间的可连续性,并基于可连接样本不断扩展聚类簇以获得最终的聚类结果。

        DBSCAN(Density-Based Spatial Clustering of Applications with Noise)就是这样一种聚类算法,该算法基于一组“领域”(neighborhood)参数(ε,MinPts)来刻画样本分布的紧密程度

        (2)算法原理:

        给定数据集D={x1,x2,...,xm},定义下面这几个概念:

 

         理解了相关概念之后,下面给出算法实现的伪代码

 

        (3)优劣相关:

              优点:

              1、能够识别任意形状的样本。

              2、该算法将具有足够密度的区域划分为簇,并在具有噪声的空间数据库中发现任意形状的簇。

              3、无需指定簇个数,而是由算法自主发现。

              缺点:

              1、需要指定最少点个数(MinPts)与半径(ε)。(但其实相对其他聚类算法来说,已经具有较大的自由性。)

              2、最少点个数与半径对算法的影响较大,一般需多次调试。

代码实现:

0、数据准备:

              在这里,我们使用sklearn库的鸢尾花iris数据集(sklearn.datasets.load_iris)作为测试数据样本。iris数据集包含150个样本,每个样本包含四个属性特征(花萼长度、花萼宽度、花瓣长度、花瓣宽度)和一个类别标签(分别用0、1、2表示山鸢尾、变色鸢尾和维吉尼亚鸢尾)。

              首先,我们要安装sklearn库。安装此库,还是通过pip install命令,但是并不是pip install sklearn,而是pip install scikit-learn。正如我们调用opencv是import cv2,而安装却是通过pip install opencv一样。 

pip install scikit-learn

              然后,获取数据集,其中x为鸢尾花的特征数据集(数据类型为数组numpy.adarray),y为鸢尾花的标签数据集(数据类型为数组numpy.adarray) 。

from sklearn.datasets import load_iris
x = load_iris().data
y = load_iris().target

1、PCA降维:

import numpy as np

def PCA_DimRed(dataMat,topNfeat): #PCA_DimRed--PCA dimension reduction,PCA降维
    meanVals = np.mean(dataMat, axis=0)
    meanRemoved = dataMat - meanVals  # 标准化(去均值)
    covMat = np.cov(meanRemoved, rowvar=False)
    eigVals, eigVets = np.linalg.eig(np.mat(covMat))  # 计算矩阵的特征值和特征向量
    eigValInd = np.argsort(eigVals)  # 将特征值从小到大排序,返回的是特征值对应的数组里的下标
    eigValInd = eigValInd[:-(topNfeat + 1):-1]  # 保留最大的前K个特征值
    redEigVects = eigVets[:, eigValInd]  # 对应的特征向量
    lowDDatMat = meanRemoved * redEigVects  # 将数据转换到低维新空间
    # reconMat = (lowDDatMat * redEigVects.T) + meanVals  # 还原原始数据
    return lowDDatMat

2、DBSCAN聚类:

import numpy as np
import random
import copy

def DBSCAN_cluster(mat,eps,min_Pts): #进行DBSCAN聚类,优点在于不用指定簇数量,而且适用于多种形状类型的簇
    k = -1
    neighbor_list = []  # 用来保存每个数据的邻域
    omega_list = []  # 核心对象集合
    gama = set([x for x in range(len(mat))])  # 初始时将所有点标记为未访问
    cluster = [-1 for _ in range(len(mat))]  # 聚类
    for i in range(len(mat)):
        neighbor_list.append(find_neighbor(mat, i, eps))
        if len(neighbor_list[-1]) >= min_Pts:
            omega_list.append(i)  # 将样本加入核心对象集合
    omega_list = set(omega_list)  # 转化为集合便于操作
    while len(omega_list) > 0:
        gama_old = copy.deepcopy(gama)
        j = random.choice(list(omega_list))  # 随机选取一个核心对象
        k = k + 1
        Q = list()
        Q.append(j)
        gama.remove(j)
        while len(Q) > 0:
            q = Q[0]
            Q.remove(q)
            if len(neighbor_list[q]) >= min_Pts:
                delta = neighbor_list[q] & gama
                deltalist = list(delta)
                for i in range(len(delta)):
                    Q.append(deltalist[i])
                    gama = gama - delta
        Ck = gama_old - gama
        Cklist = list(Ck)
        for i in range(len(Ck)):
            cluster[Cklist[i]] = k
        omega_list = omega_list - Ck
    return cluster

3、代码汇总:

from sklearn.datasets import load_iris
import numpy as np
import random
import copy
import matplotlib.pyplot as plt

def PCA_DimRed(dataMat,topNfeat): #PCA_DimRed--PCA dimension reduction,PCA降维
    meanVals = np.mean(dataMat, axis=0)
    meanRemoved = dataMat - meanVals  # 标准化(去均值)
    covMat = np.cov(meanRemoved, rowvar=False)
    eigVals, eigVets = np.linalg.eig(np.mat(covMat))  # 计算矩阵的特征值和特征向量
    eigValInd = np.argsort(eigVals)  # 将特征值从小到大排序,返回的是特征值对应的数组里的下标
    eigValInd = eigValInd[:-(topNfeat + 1):-1]  # 保留最大的前K个特征值
    redEigVects = eigVets[:, eigValInd]  # 对应的特征向量
    lowDDatMat = meanRemoved * redEigVects  # 将数据转换到低维新空间
    # reconMat = (lowDDatMat * redEigVects.T) + meanVals  # 还原原始数据
    return lowDDatMat

def find_neighbor(data,pos,eps): #寻找相邻点函数
    N = list()
    temp = np.sum((data-data[pos])**2, axis=1)**0.5
    N = np.argwhere(temp <= eps).flatten().tolist()
    return set(N)

def DBSCAN_cluster(data,eps,min_Pts): #进行DBSCAN聚类,优点在于不用指定簇数量,而且适用于多种形状类型的簇,如果使用K均值聚类的话,对于这次实验的数据(条状簇)无法得到较好的分类结果
    k = -1
    neighbor_list = []  # 用来保存每个数据的邻域
    omega_list = []  # 核心对象集合
    gama = set([x for x in range(len(data))])  # 初始时将所有点标记为未访问
    cluster = [-1 for _ in range(len(data))]  # 聚类
    for i in range(len(data)):
        neighbor_list.append(find_neighbor(data, i, eps))
        if len(neighbor_list[-1]) >= min_Pts:
            omega_list.append(i)  # 将样本加入核心对象集合
    omega_list = set(omega_list)  # 转化为集合便于操作
    while len(omega_list) > 0:
        gama_old = copy.deepcopy(gama)
        j = random.choice(list(omega_list))  # 随机选取一个核心对象
        k = k + 1
        Q = list()
        Q.append(j)
        gama.remove(j)
        while len(Q) > 0:
            q = Q[0]
            Q.remove(q)
            if len(neighbor_list[q]) >= min_Pts:
                delta = neighbor_list[q] & gama
                deltalist = list(delta)
                for i in range(len(delta)):
                    Q.append(deltalist[i])
                    gama = gama - delta
        Ck = gama_old - gama
        Cklist = list(Ck)
        for i in range(len(Ck)):
            cluster[Cklist[i]] = k
        omega_list = omega_list - Ck
    return cluster

if __name__ == "__main__":
    #1、准备数据
    x = load_iris().data
    y = load_iris().target

    #2、PCA降维
    pro_data = PCA_DimRed(x,2)

    #3、DBSCAN聚类(此步中要保证数据集类型为数组,以配合find_neighbor函数)
    pro_array = np.array(pro_data)
    thecluster = DBSCAN_cluster(pro_array,eps=0.8,min_Pts=30)

    #4、展示降维效果:
    print("下面是降维之前的鸢尾花数据集特征集:")
    print(x)
    print("下面是降维之后的鸢尾花数据集特征集:")
    print(pro_data)

    #5、展示聚类效果:
    plt.figure()
    plt.scatter(pro_array[:, 0], pro_array[:, 1], c=thecluster)
    plt.show()

实现效果:

1、降维效果:

降维之前的鸢尾花数据集特征集:

 

降维之后的鸢尾花数据集特征集:

 

2、聚类效果:

可以看出来,DBSCAN聚类方法并不能很准确地根据PCA降维后的鸢尾花特征集对鸢尾花样本进行聚类,原因是变色鸢尾与维吉尼亚鸢尾的样本特征较近,两者更类似于同属于一个密度空间,因而导致了该实验的不准确性。

但是,其实也可以看出,山鸢尾与其他两种鸢尾能够进行较好的区别 ,说明该方法仍适用于不同类别样本间差距较大的聚类情形

写在最后:

本篇文章主要介绍了PCA降维、DBSCAN聚类这两个机器学习操作的基本原理,以及两者结合的用于实际数据处理的方法

可能基于PCA降维的DBSCAN聚类的方法不是很适用于sklearn库中的鸢尾花数据集,但是该方法既具有处理高维数据的能力,也能够处理各种形状的簇,说明其作为一套较为完整的聚类方法,仍然具有较为广阔的应用场景

希望大家能够积极应用这个方法,使得其拥有更多的应用可能性。谢谢各位!

参考书籍:

周志华.机器学习[M].北京:清华大学出版社,2016.01

参考文章:

六种常见聚类算法:http://t.csdn.cn/Urhn9

Python PCA(主成分分析法)降维的两种实现:http://t.csdn.cn/NlAeU

DBSCAN聚类算法Python实现:http://t.csdn.cn/lkFhF

PCA降维原理 操作步骤与优缺点:http://t.csdn.cn/QiEJM

 

 好了以上就是所有的内容,希望大家多多关注,点赞,收藏,这对我有很大的帮助。谢谢大家了!

好了,这里是Kamen Black 君。祝国康家安,大家下次再见喽!!!溜溜球~~ 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/416362.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

关于镜头畸变问题的总结

1、问题背景最近在做的项目有畸变校正的需求&#xff0c;但测试镜头畸变时&#xff0c;发现畸变的形态不太正常。如下图所示中间向内凹、四周向外凸&#xff0c;感觉像是曲线型的。但常见的畸变就两种&#xff0c;一种是向内收的枕形畸变&#xff0c;另一种是向外凸的桶形畸变&…

SpringCloud:ElasticSearch之DSL查询文档

elasticsearch的查询依然是基于JSON风格的DSL来实现的。 1.1.DSL查询分类 Elasticsearch提供了基于JSON的DSL&#xff08;Domain Specific Language&#xff09;来定义查询。常见的查询类型包括&#xff1a; 查询所有&#xff1a;查询出所有数据&#xff0c;一般测试用。例如…

第04章_IDEA的安装与使用(上)

第04章_IDEA的安装与使用&#xff08;上&#xff09; 讲师&#xff1a;尚硅谷-宋红康&#xff08;江湖人称&#xff1a;康师傅&#xff09; 官网&#xff1a;http://www.atguigu.com 本章专题与脉络 【Why IDEA ?】 【注】JetBrains官方说明&#xff1a; 尽管我们采取了多种…

从二叉树角度看归并排序

归并排序本质上可以看作二叉树的后序遍历 里面用到的核心思想 > 分治 分&#xff1a;二叉树算法思想中的分解问题思想 治&#xff1a;链表中双指针技巧&#xff08;将两条链表合并成一条有序链表&#xff09; sort首先将数组分成左半边和右半边 > 然后分别对左右两…

Log库和配置系统结构

Log库&#xff1a; 类关系 首先有3个大类&#xff1a;LogEvent、LogAppender、Logger、LogFormat&#xff1b; 关系如下&#xff1a; Logger&#xff1a;具体log的实现 LogAppender&#xff1a;将Log信息传输到不同的目的地&#xff0c;根据不同的需求派生出不同的类 LogF…

Java 系列 Nacos

Java 系列文章 文章目录Java 系列文章前言一、Nacas 介绍及安装1. 什么是Nacos2. 为什么使用Nacos3. Nacos 下载和安装二、Nacos服务提供者注册1. Nacos代替Eureka2. Nacos服务注册中心3. Nacos Discovery引入1. 创建新项目2. POM3. YML文件4. 启动类5. 业务类6. 测试&#xff…

Git如何推送当前代码到远程仓库

第一种方法 &#xff08;建立在已经配置好用户变量和ssh基础上&#xff09; 在本地创建git仓库 git init 绑定远程仓库&#xff0c;origin是给远程仓库起的别名&#xff0c;也可以起其他名字&#xff0c;但是如果用origin&#xff0c;git push时可以不指出名字&#xff0c;如果…

【2023 · CANN训练营第一季】昇腾AI入门课(Pytorch)——第一章学习笔记

第一章 昇腾AI基础知识介绍 第2节 昇腾AI全栈架构 昇腾 AI 全栈可以分成四个大部分&#xff1a; 1&#xff0e;应用使能层面&#xff0c;此层面通常包含用于部署模型的软硬件&#xff0c;例如 API 、 SDK 、部署平台&#xff0c;模型库等等。 2. AI 框架层面&#xff0c;此层…

【C语言】 程序员的自我修养之(程序编译过程)

在ANSI C(标准C)的任何一种实现中&#xff0c;存在两个不同的环境。 第1种是翻译环境&#xff0c;在这个环境中源代码被转换为可执行的机器指令。第2种是执行环境&#xff0c;它用于实际执行代码。 今天我们就讲解他们在这环境过程都做了什么。 文章目录详解编译链接翻译环境编…

【数据库原理 • 七】数据库并发控制

前言 数据库技术是计算机科学技术中发展最快&#xff0c;应用最广的技术之一&#xff0c;它是专门研究如何科学的组织和存储数据&#xff0c;如何高效地获取和处理数据的技术。它已成为各行各业存储数据、管理信息、共享资源和决策支持的最先进&#xff0c;最常用的技术。 当前…

【19】核心易中期刊推荐——人工智能 | 遥感信息处理

🚀🚀🚀NEW!!!核心易中期刊推荐栏目来啦 ~ 📚🍀 核心期刊在国内的应用范围非常广,核心期刊发表论文是国内很多作者晋升的硬性要求,并且在国内属于顶尖论文发表,具有很高的学术价值。在中文核心目录体系中,权威代表有CSSCI、CSCD和北大核心。其中,中文期刊的数…

redis——优化

键值设计bigKey例子批处理单机 pipeline集群服务器持久化慢查询安全内存集群问题集群完整性集群带宽数据倾斜客户端性能命令的集群兼容性lua和事务&#xff1a;集群下不支持键值设计 长度 < 44 节省内存。string的底层数据结构中&#xff0c;编码格式embstr&#xff08;连续…

LeetCode:455. 分发饼干——贪心算法

&#x1f34e;道阻且长&#xff0c;行则将至。&#x1f353; &#x1f33b;算法&#xff0c;不如说它是一种思考方式&#x1f340;算法专栏&#xff1a; &#x1f449;&#x1f3fb;123 贪心算法是在每个阶段选取局部最优解&#xff0c;最终得到全局最优解的一种思想。贪心算法…

操作系统论文导读(四):Minimizing Memory Utilization of Real-Time Task Sets in Single and…

目录 一、论文核心思想&#xff1a; 二、降低RAM的思想 三、基本的相关定义 四、单处理器方面 五、优化单处理器中的堆栈使用 六、多处理器方面 七、基本的相关调度 八、协议特点 Minimizing Memory Utilization of Real-Time Task Sets in Single and Multi-Processor…

算法记录 | Day29 回溯算法

491.递增子序列 思路&#xff1a; 1.确定回溯函数参数&#xff1a;定义全局遍历存放res集合和单个path&#xff0c;还需要 nums数组startindex&#xff08;int&#xff09;为下一层for循环搜索的起始位置。 2.终止条件&#xff1a;当startindex >len(nums)&#xff0c;r…

C++初阶—vector深度剖析及模拟实现

目录 ➡️0. 前言 &#x1f60a;1.简易框架实现 &#x1f414;1. 无参构造 &#x1f414;2. 容量capacity — 长度size() &#x1f414;3. 动态增长 — push_back—pop_back — reserve &#x1f414;4. 迭代器的实现 &#x1f414;4.front和back的实现 &#x1f60a;2…

你知道C语言的typedef关键字吗?

本篇博客主要讲解C语言中的typedef关键字。typedef的作用是类型重定义&#xff0c;可以理解为给类型起一个别名。我主要从3个方面来讲解&#xff1a; typedef内置类型。typedef自定义类型。typedef和#define的区别。 1.typedef内置类型 typedef可以给一个类型起“别名”。比如…

服务器部署前后端分离项目

服务器部署前后端分离项目 目录服务器部署前后端分离项目一、安装环境安装jdk1、在/usr/local目录下创建jdk文件夹&#xff0c;并将jdk安装包放到/usr/local/jdk包下并解压1.1通过文件传输工具将jdk包上传到服务器上1.2输入解压命令1.3解压完成&#xff0c;生成下面的文件2、配…

学习周报4/9

文章目录前言文献阅读摘要简介方法结论时间序列预测总结前言 本周阅读文献《Improving LSTM hydrological modeling with spatiotemporal deep learning and multi-task learning: A case study of three mountainous areas on the Tibetan Plateau》&#xff0c;文章主要基于…

多种方法解决SLF4J: Defaulting to no-operation (NOP) logger implementation的错误

文章目录1. 复现错误2. 分析错误3. 解决错误4. 解决该错误的其他方法1. 复现错误 今天在编写使用Quartz执行定时任务的方法&#xff0c;如下代码所示&#xff1a; public class QuartzTest {public static void main(String[] args) throws SchedulerException {// 1、创建Sch…