大家好,今天咱们聊聊关于聚类算法的方方面面。
今天的内容非常详细,大家可以先收藏起来,慢慢学习~
涉及到的算法有:
下面,一起来看看~
K均值聚类(K-Means)是一种常用的无监督学习算法,用于将数据集分成具有相似特征的K个不同的组(簇)。这个算法被广泛应用于数据挖掘、图像处理和模式识别等领域。
K均值聚类算法的目标是将数据点划分到K个簇中,使得每个数据点都属于与其最近的簇的中心点。这意味着,每个簇的中心点代表了该簇内所有数据点的平均值。
1. 初始化:选择K个随机的中心点作为初始簇中心。 2. 分配数据点:将每个数据点分配到距离其最近的中心点所属的簇。 3. 更新簇中心:重新计算每个簇的中心,即取簇内所有数据点的平均值。 4. 重复步骤2和3,直到簇中心不再发生变化,或者达到预定的迭代次数。
1. 距离度量:欧氏距离公式
其中,是第i个数据点,是第j个簇中心,是特征的数量。
2. 簇中心更新:计算每个簇的中心
其中,是第j个簇中的所有数据点集合。
import numpy as np
from sklearn.datasets import make_blobs
from sklearn.cluster import KMeans
import matplotlib.pyplot as plt
# 创建一个示例数据集
X, _ = make_blobs(n_samples=300, centers=4, cluster_std=0.60, random_state=0)
# 使用K均值算法进行聚类
kmeans = KMeans(n_clusters=4)
kmeans.fit(X)
# 获取簇中心和簇分配结果
centers = kmeans.cluster_centers_
labels = kmeans.labels_
# 绘制聚类结果
plt.scatter(X[:, 0], X[:, 1], c=labels, cmap='viridis')
plt.scatter(centers[:, 0], centers[:, 1], marker='o', s=200, color='red')
plt.show()
层次聚类(Hierarchical Clustering)是一种聚类方法,它通过构建一个层次化的聚类树来组织数据。这种方法不需要预先指定聚类的数量,因为它可以根据数据的结构自动形成不同层次的聚类。
层次聚类是一种自底向上或自顶向下的方法,它将数据点逐步合并或拆分,形成一个聚类树(也称为树状图或树状聚类图)。在树状图的叶节点,每个数据点都是一个单独的聚类,而在树的根节点,所有数据点都属于一个聚类。
1. 自底向上聚合(凝聚式聚类):从每个数据点作为一个单独的聚类开始,然后逐步合并相似的聚类,直到所有数据点都在一个聚类中为止。 2. 自顶向下分裂(分裂式聚类):从所有数据点作为一个整体的聚类开始,然后逐步将其分裂成更小的子聚类,直到每个数据点都成为一个单独的聚类为止。
1. 相似性度量:使用欧氏距离作为相似性度量的公式
其中,和分别是两个数据点,是特征的数量。
2. 聚类间距离:根据连接方式的不同,可以有不同的距离计算公式,如单链接(最小距离)、完全链接(最大距离)和平均链接(平均距离)等。
import numpy as np
import matplotlib.pyplot as plt
from scipy.cluster.hierarchy import dendrogram, linkage
# 创建示例数据集
X = np.array([[1, 2], [2, 3], [3, 4], [5, 6], [7, 8]])
# 计算链接矩阵
Z = linkage(X, 'ward')
# 绘制树状图
plt.figure(figsize=(10, 5))
dendrogram(Z)
plt.title('Hierarchical Clustering Dendrogram')
plt.xlabel('Data point index')
plt.ylabel('Distance')
plt.show()
DBSCAN(Density-Based Spatial Clustering of Applications with Noise)是一种基于密度的空间聚类算法,它可以识别具有足够高密度的区域作为簇,并且可以在数据中识别噪声点。DBSCAN算法不需要预先指定聚类的数量,并且能够有效地处理具有不规则形状的簇。
DBSCAN算法通过定义两个参数:邻域半径(eps)和最小样本数(min_samples)来进行聚类。它的核心思想是,将具有足够高密度的区域划分为一个簇,并将稀疏的区域视为噪声。DBSCAN的输出是一组簇,每个簇包含至少包含min_samples个数据点,且每个数据点的邻域内至少有min_samples个数据点。
1. 核心点:如果一个点的邻域内至少包含min_samples个数据点,则该点称为核心点。 2. 边界点:如果一个点的邻域内包含少于min_samples个数据点,但它位于某个核心点的邻域内,则该点称为边界点。 3. 噪声点:如果一个点既不是核心点也不是边界点,则该点被标记为噪声点。
1. 邻域内数据点计算:对于每个数据点,计算其邻域内的数据点数量。 2. 核心点定义:如果邻域内的数据点数量大于等于min_samples,则将该点标记为核心点。 3. 边界点定义:如果邻域内的数据点数量小于min_samples,但该点位于某个核心点的邻域内,则将该点标记为边界点。 4. 噪声点定义:如果一个点既不是核心点也不是边界点,则将该点标记为噪声点。
from sklearn.cluster import DBSCAN
from sklearn.datasets import make_moons
import matplotlib.pyplot as plt
# 创建示例数据集
X, _ = make_moons(n_samples=200, noise=0.1)
# 使用DBSCAN算法进行聚类
dbscan = DBSCAN(eps=0.2, min_samples=5)
labels = dbscan.fit_predict(X)
# 绘制聚类结果
plt.scatter(X[:, 0], X[:, 1], c=labels, cmap='viridis')
plt.title('DBSCAN Clustering')
plt.xlabel('Feature 1')
plt.ylabel('Feature 2')
plt.show()
高斯混合模型(Gaussian Mixture Model,GMM)是一种概率模型,用于对数据进行聚类和密度估计。GMM假设数据是由多个高斯分布组合而成的,每个高斯分布称为一个组件。这种模型能够适应各种不同形状和大小的聚类,因此在实际应用中非常灵活。
GMM假设数据是由K个高斯分布组成的,每个高斯分布代表一个聚类簇。每个数据点的生成过程是从这些高斯分布中以一定的概率选择一个分布,然后从选定的分布中生成一个数据点。GMM的目标是通过最大化似然函数来估计模型参数,从而找到最佳的组件数量和每个组件的参数。
1. 数据生成过程:假设有K个高斯分布,每个高斯分布由均值向量和协方差矩阵参数化。生成每个数据点时,首先根据一组权重选择一个高斯分布,然后从选定的高斯分布中生成数据点。 2. 模型参数估计:通过最大化似然函数来估计模型的参数,包括每个高斯分布的均值、协方差矩阵和权重。通常使用期望最大化(Expectation-Maximization,EM)算法进行参数估计。 3. 聚类:通过计算每个数据点属于每个组件的后验概率来对数据进行聚类,然后将数据点分配给概率最大的组件。
1. 高斯分布概率密度函数:多元高斯分布的概率密度函数如下:
其中,是数据点,是均值向量,是协方差矩阵,是数据的维度。
2. 似然函数:假设数据集为,似然函数为每个数据点由各个高斯分布生成的概率的乘积:
其中,表示模型参数,表示组件的权重,和分别表示组件的均值和协方差矩阵。
from sklearn.mixture import GaussianMixture
from sklearn.datasets import make_blobs
import matplotlib.pyplot as plt
# 创建示例数据集
X, _ = make_blobs(n_samples=300, centers=4, cluster_std=0.6, random_state=0)
# 使用GMM算法进行聚类
gmm = GaussianMixture(n_components=4)
gmm.fit(X)
# 获取聚类结果
labels = gmm.predict(X)
# 绘制聚类结果
plt.scatter(X[:, 0], X[:, 1], c=labels, cmap='viridis')
plt.title('Gaussian Mixture Model Clustering')
plt.xlabel('Feature 1')
plt.ylabel('Feature 2')
plt.show()
密度峰值聚类(Density Peaks Clustering)是一种基于密度的聚类算法,它通过寻找数据集中的密度峰值来识别聚类中心,并将其他数据点分配给这些中心。密度峰值聚类在处理具有不同密度和形状的聚类时表现出很好的鲁棒性。
密度峰值聚类算法的核心思想是,聚类中心通常对应于数据集中的密度峰值,而非聚类中心的数据点则位于密度低谷附近。该算法首先通过计算每个数据点的局部密度和距离最近的高密度点来确定密度峰值,然后通过阈值来确定聚类中心,并通过计算每个数据点与聚类中心的距离来分配数据点到不同的聚类。
1. 局部密度:对于每个数据点,计算其在邻域内的密度,通常使用距离邻域内的数据点数量来表示。 2. 密度峰值:寻找具有较高局部密度和较远距离的数据点,这些数据点通常对应于聚类中心。 3. 聚类中心确定:通过设置阈值来确定密度峰值,这些峰值将被认为是聚类中心。 4. 数据点分配:根据每个数据点与聚类中心的距离来将数据点分配给不同的聚类。
1. 局部密度计算:对于每个数据点,计算其在邻域内的密度,通常使用距离邻域内的数据点数量来表示。 2. 密度峰值计算:寻找具有较高局部密度和较远距离的数据点,可以使用局部密度和距离来进行判断。 3. 聚类中心确定:通过设置阈值来确定密度峰值,这些峰值将被认为是聚类中心。 4. 数据点分配:根据每个数据点与聚类中心的距离来将数据点分配给不同的聚类。
import matplotlib.pyplot as plt
from sklearn.datasets import make_blobs
from sklearn_extra.cluster import KMedoids
import numpy as np
# 生成样本数据
X, _ = make_blobs(n_samples=300, centers=4, cluster_std=0.60, random_state=0)
# 使用KMedoids进行密度峰值聚类
kmedoids = KMedoids(n_clusters=4, random_state=0).fit(X)
# 预测每个样本的簇标签
labels = kmedoids.labels_
# 绘制聚类结果
plt.scatter(X[:, 0], X[:, 1], c=labels, cmap='viridis', marker='o')
plt.scatter(kmedoids.cluster_centers_[:, 0], kmedoids.cluster_centers_[:, 1], c='red', marker='x') # 绘制簇中心
plt.title('Density Peaks Clustering with KMedoids')
plt.show()
需要注意,KMedoids
算法和Density Peaks Clustering
算法并不完全相同,但是它们都是基于相似的概念,即通过某种方式找到数据的“中心点”或“峰值点”。scikit-learn
并未直接实现原始的密度峰值聚类算法,但是KMedoids
可以作为一个近似的示例。
如果大家需要原始的DPC算法实现,可能需要自己编写或者查找相关的第三方实现。
谱聚类(Spectral Clustering)是一种基于图论和线性代数的聚类方法,它通过将数据点表示为图上的节点,并利用节点之间的相似性构建图的拉普拉斯矩阵,然后利用拉普拉斯矩阵的特征向量进行降维和聚类。谱聚类在处理具有复杂结构的数据集时表现出很好的性能,特别是在处理图数据或具有非凸形状的聚类时。
谱聚类的基本思想是将数据集表示为图的形式,其中数据点对应于图中的节点,而节点之间的相似性对应于图的边。然后,通过对图的拉普拉斯矩阵进行特征分解来实现降维和聚类,具体而言,谱聚类将拉普拉斯矩阵的特征向量作为新的特征表示,并使用K均值等方法对这些特征向量进行聚类。
1. 图表示:将数据集表示为图的形式,其中数据点对应于图中的节点,而相似性度量则决定了节点之间是否有边相连。 2. 拉普拉斯矩阵:根据图的结构构建拉普拉斯矩阵,通常使用邻接矩阵和度矩阵的差来表示。 3. 特征分解:对拉普拉斯矩阵进行特征分解,得到其特征向量和特征值。 4. 降维和聚类:选择前几个特征向量(对应于最小的特征值)作为新的特征表示,然后使用K均值等方法对这些特征向量进行聚类。
1. 拉普拉斯矩阵的构建:通常使用拉普拉斯矩阵表示图的结构,其中,其中是邻接矩阵,是度矩阵。 2. 特征分解:对拉普拉斯矩阵进行特征分解,得到特征向量和特征值,即。3. 降维和聚类:选择前个特征向量作为新的特征表示,然后使用K均值等方法对这些特征向量进行聚类。
from sklearn.cluster import SpectralClustering
from sklearn.datasets import make_moons
import matplotlib.pyplot as plt
# 创建示例数据集
X, _ = make_moons(n_samples=200, noise=0.1)
# 使用谱聚类进行聚类
spectral_clustering = SpectralClustering(n_clusters=2, affinity='nearest_neighbors', random_state=0)
labels = spectral_clustering.fit_predict(X)
# 绘制聚类结果
plt.scatter(X[:, 0], X[:, 1], c=labels, cmap='viridis')
plt.title('Spectral Clustering')
plt.xlabel('Feature 1')
plt.ylabel('Feature 2')
plt.show()
OPTICS(Ordering Points To Identify the Clustering Structure)是一种基于密度的聚类算法,它可以发现具有不同密度的聚类,并以有序的方式呈现这些聚类结构。与DBSCAN相似,OPTICS也不需要预先指定聚类的数量,而是根据数据的密度来自适应地发现聚类结构。
OPTICS算法通过计算每个数据点的局部密度和距离最近的高密度点来确定聚类结构。它使用一个特殊的数据结构(可达距离图)来表示数据点之间的可达关系,然后根据这个结构构建一个有序的聚类结构。通过调整参数,OPTICS可以发现不同密度和形状的聚类。
1. 局部密度:对于每个数据点,计算其在邻域内的密度,通常使用距离邻域内的数据点数量来表示。 2. 可达距离:对于每个数据点,计算其与最近的高密度点之间的可达距离,即到达这个高密度点所需的距离。 3. 核心点:如果一个点的可达距离小于给定的阈值,则该点被认为是一个核心点。 4. 密度直方图:根据核心点和可达距离来构建一个密度直方图,用于表示数据点的密度分布。 5. 有序聚类结构:根据数据点的可达距离来构建一个有序的聚类结构,使得密度较高的聚类结构排在前面。
1. 局部密度计算:对于每个数据点,计算其在邻域内的密度,通常使用距离邻域内的数据点数量来表示。 2. 可达距离计算:对于每个数据点,计算其与最近的高密度点之间的可达距离,即到达所需的距离。 3. 核心点定义:如果一个点的可达距离小于给定的阈值,则该点被认为是一个核心点。
由于OPTICS算法在Python中没有标准的库函数可以直接调用,以下是一个使用第三方库scikit-learn
中的OPTICS实现的简化示例:
from sklearn.cluster import OPTICS
from sklearn.datasets import make_moons
import matplotlib.pyplot as plt
# 创建示例数据集
X, _ = make_moons(n_samples=200, noise=0.1)
# 使用OPTICS进行聚类
optics = OPTICS(min_samples=5)
optics.fit(X)
# 获取聚类结果
labels = optics.labels_
# 绘制聚类结果
plt.scatter(X[:, 0], X[:, 1], c=labels, cmap='viridis')
plt.title('OPTICS Clustering')
plt.xlabel('Feature 1')
plt.ylabel('Feature 2')
plt.show()
自组织映射(Self-Organizing Maps,SOM)是一种无监督学习算法,用于在高维数据中发现潜在的低维结构,并将数据点映射到一个二维或三维的网格中,以便于可视化和解释。SOM通过模拟神经元之间的竞争和合作来实现数据的聚类和降维,因此也被称为Kohonen网络。
SOM模型由芬兰科学家Teuvo Kohonen于1982年提出,它通过将数据点映射到一个二维或三维的网格中,使得相似的数据点被映射到相邻的网格单元,从而实现了数据的可视化和聚类。SOM的训练过程中,数据点通过竞争机制影响着映射单元的权重,使得权重向数据点的分布趋近。
1. 竞争学习:SOM模型中,每个映射单元(神经元)都与输入空间中的一个权重向量相关联。在训练过程中,数据点与所有的映射单元进行竞争,选取与其最相似的映射单元作为获胜单元。 2. 权重更新:获胜单元以及其邻近单元的权重向量被更新,使得它们更接近于获胜的数据点。这种更新过程沿着数据点与映射单元之间的拓扑结构进行。 3. 拓扑结构:SOM模型通常采用矩形或六边形的网格结构,这种结构使得相邻的映射单元在权重空间上也是相邻的。 4. 收敛性:通过迭代训练,SOM模型能够收敛到一个稳定状态,其中每个映射单元的权重向量代表了输入空间中的一个聚类中心。
1. 获胜单元的选择:根据输入数据点和映射单元的权重向量之间的相似度度量来选择获胜单元,通常使用欧氏距离:
2. 权重更新:根据获胜单元和其邻近单元的权重更新规则,通常使用以下公式进行更新:
其中,表示时间的权重向量,是学习率,是邻近函数,是输入数据点。
from minisom import MiniSom
from sklearn.datasets import load_iris
import numpy as np
import matplotlib.pyplot as plt
# 加载示例数据集
data, labels = load_iris(return_X_y=True)
# 归一化数据
data = data / np.max(data, axis=0)
# 设置SOM模型参数
som = MiniSom(7, 7, data.shape[1], sigma=0.5, learning_rate=0.5)
# 初始化权重
som.random_weights_init(data)
# 训练SOM模型
som.train_random(data, 100)
# 绘制聚类结果
plt.figure(figsize=(7, 7))
plt.pcolor(som.distance_map().T, cmap='bone_r')
plt.colorbar()
# 绘制聚类中心
for i, (x, t) in enumerate(zip(data, labels)):
w = som.winner(x)
plt.text(w[0] + 0.5, w[1] + 0.5, str(t), color=plt.cm.rainbow(t / 3.), fontdict={'weight': 'bold', 'size': 11})
plt.title('Self-Organizing Map')
plt.show()
Affinity Propagation(亲和传播)是一种无监督学习算法,用于在数据集中识别出代表性的数据点,并将其他数据点分配给这些代表性数据点。与传统的聚类算法不同,Affinity Propagation不需要预先指定聚类的数量,而是通过交互式地传播数据点之间的“亲和度”来确定聚类。
Affinity Propagation是由Brendan J. Frey和Delbert Dueck于2007年提出的一种聚类算法。它基于数据点之间的相似性度量(亲和度)来识别数据集中的代表性样本,这些代表性样本被称为“样本的样本”。然后,其他数据点将被分配给这些代表性样本,从而实现了聚类。
1. 亲和度矩阵:首先,Affinity Propagation计算每对数据点之间的相似性度量,形成一个亲和度矩阵,该矩阵表示了数据点之间的相互作用程度。 2. 消息传递:通过交互式地传递消息,数据点之间的亲和度被更新,其中每个数据点发送消息给其他数据点,以反映它希望成为其他数据点的代表性样本的程度。 3. 样本的样本:最终,亲和度矩阵的稳定点被认为是代表性样本,它们对应于数据集中的聚类中心。 4. 聚类分配:其他数据点根据它们与代表性样本之间的亲和度被分配到不同的聚类中。
1. 相似性度量:通过某种相似性度量(如欧氏距离、余弦相似度等)计算数据点和之间的相似性度量。
2. 亲和度矩阵更新:通过以下公式更新亲和度矩阵:
3. 责任传递:更新责任矩阵和可用性矩阵,其中表示数据点希望成为其代表性样本的程度,表示数据点成为代表性样本的程度。
4. 可用性更新:通过以下公式更新可用性矩阵:
5. 聚类分配:根据可用性矩阵确定数据点的聚类分配。
from sklearn.cluster import AffinityPropagation
from sklearn.datasets import make_blobs
import matplotlib.pyplot as plt
# 创建示例数据集
X, _ = make_blobs(n_samples=300, centers=4, cluster_std=0.6, random_state=0)
# 使用Affinity Propagation进行聚类
affinity_propagation = AffinityPropagation(damping=0.5, preference=-50)
labels = affinity_propagation.fit_predict(X)
# 绘制聚类结果
plt.scatter(X[:, 0], X[:, 1], c=labels, cmap='viridis')
plt.title('Affinity Propagation Clustering')
plt.xlabel('Feature 1')
plt.ylabel('Feature 2')
plt.show()
Affinity Propagation(亲和传播)是一种无监督学习算法,用于在数据集中识别出代表性的数据点,并将其他数据点分配给这些代表性数据点。与传统的聚类算法不同,Affinity Propagation不需要预先指定聚类的数量,而是通过交互式地传播数据点之间的“亲和度”来确定聚类。
Affinity Propagation是由Brendan J. Frey和Delbert Dueck于2007年提出的一种聚类算法。它基于数据点之间的相似性度量(亲和度)来识别数据集中的代表性样本,这些代表性样本被称为“样本的样本”。然后,其他数据点将被分配给这些代表性样本,从而实现了聚类。
1. 亲和度矩阵:首先,Affinity Propagation计算每对数据点之间的相似性度量,形成一个亲和度矩阵,该矩阵表示了数据点之间的相互作用程度。 2. 消息传递:通过交互式地传递消息,数据点之间的亲和度被更新,其中每个数据点发送消息给其他数据点,以反映它希望成为其他数据点的代表性样本的程度。 3. 样本的样本:最终,亲和度矩阵的稳定点被认为是代表性样本,它们对应于数据集中的聚类中心。 4. 聚类分配:其他数据点根据它们与代表性样本之间的亲和度被分配到不同的聚类中。
1. 相似性度量:通过某种相似性度量(如欧氏距离、余弦相似度等)计算数据点和之间的相似性度量。
2. 亲和度矩阵更新:通过以下公式更新亲和度矩阵:
3. 责任传递:更新责任矩阵和可用性矩阵,其中表示数据点希望成为其代表性样本的程度,表示数据点成为代表性样本的程度。
4. 可用性更新:通过以下公式更新可用性矩阵:
5. 聚类分配:根据可用性矩阵确定数据点的聚类分配。
from sklearn.cluster import AffinityPropagation
from sklearn.datasets import make_blobs
import matplotlib.pyplot as plt
# 创建示例数据集
X, _ = make_blobs(n_samples=300, centers=4, cluster_std=0.6, random_state=0)
# 使用Affinity Propagation进行聚类
affinity_propagation = AffinityPropagation(damping=0.5, preference=-50)
labels = affinity_propagation.fit_predict(X)
# 绘制聚类结果
plt.scatter(X[:, 0], X[:, 1], c=labels, cmap='viridis')
plt.title('Affinity Propagation Clustering')
plt.xlabel('Feature 1')
plt.ylabel('Feature 2')
plt.show()
给大家准备了《机器学习学习小册》PDF版本,16大块的内容,124个问题总结!
如果你对类似于这样的文章感兴趣。
联系客服