canopy算法

(1)、将数据集向量化得到一个list后放入内存,选择两个距离阈值:T1和T2,其中T1 > T2,对应上图,实线圈为T1,虚线圈为T2,T1和T2的值可以用交叉校验来确定

      (2)、从list中任取一点P,用低计算成本方法快速计算点P与所有Canopy之间的距离(如果当前不存在Canopy,则把点P作为一个Canopy),如果点P与某个Canopy距离在T1以内,则将点P加入到这个Canopy

      (3)、如果点P曾经与某个Canopy的距离在T2以内,则需要把点P从list中删除(不过在在新的mahout采用的 不加入新的Collection 这样后面处理的时候就不包含点P),这一步是认为点P此时与这个Canopy已经够近了,因此它不可以再做其它Canopy的中心了

      (4)、重复步骤2、3,直到list为空结束


Canopy聚类是一种简单、快速、但不太准确的聚类方法。
该算法需一种快速的近似距离度量方法和两个距离阈值T1>T2。

while(没有标记的数据点){
选择一个没有强标记的数据点p
把p看作一个新Canopy c的中心
离p距离<T1的所有点都认为在c中,给这些点做上弱标记
离p距离<T2的所有点都认为在c中,给这些点做上强标记
}

Canopy聚类常作为更强聚类方法的初始步骤。
mahout Canopy聚类实现 ,采用了两个map-reduce job
第一个Job org.apache.mahout.clustering.canopy.CanopyDriver:
mapper:org.apache.mahout.clustering.canopy.CanopyMapper
对划分到每个mapper的点根据阈值T1,T2标记Canopy,输出在该mapper上所有Canopy的中心;
mahout实现对原算法略做改动,而避免需先保存所有的点
修改后的算法org.apache.mahout.clustering.canopy.addPointToCanopies
对于一个数据点,遍历已有Canopy{
该点到某Canopy距离<T1,则加入该Canopy;
若点到某Canopy距离<T2,则标记该点已于该Canopy强关联;
}
若该点不存在强关联的Canopy,则为其创建一个新Canopy
reducer:org.apache.mahout.clustering.canopy.CanopyReducer
整个Job就一个reduce任务,对mapper输出的所有点再次使用Canopy聚类,并输出中心点
第二个Job org.apache.mahout.clustering.canopy.ClusterDriver
使用第一个Job输出的中心点,采用最近距离原则对原数据点进行聚类
用Canopy聚类作为其他方法的初始步骤时,通常不执行该Job
参数调整:
当T1过大时,会使许多点属于多个Canopy,可能会造成各个簇的中心点间距离较近,各簇
间区别不明显;
当T2过大时,增加强标记数据点的数量,会减少簇个个数;T2过小,会增加簇的个数,同时
增加计算时间

另外:mahout提供了几种常见距离计算的实现 ,均实现org.apache.mahout.common.distance.DistanceMeasure接口
CosineDistanceMeasure:计算两向量间的夹角
SquaredEuclideanDistanceMeasure:计算欧式距离的平方
EuclideanDistanceMeasure:计算欧式距离
ManhattanDistanceMeasure:马氏距离,貌似图像处理中用得比较多
TanimotoDistanceMeasure:Jaccard相似度,T(a, b) = a.b / (|a|^2 + |b|^2 - a.b)
以及带权重的欧式距离和马氏距离。

需要注意:

1. 首先是轻量距离量度的选择,是选择数据模型其中的一个属性,还是其它外部属性这对canopy的分布最为重要。

2. T1, T2的取值影响到canopy重叠率f,以及canopy的粒度。
3. Canopy有消除孤立点的作用,而K-means在这方面却无能为力。建立canopies之后,可以删除那些包含数据点数目较少的canopy,往往这些canopy是包含孤立点的。
4. 根据canopy内点的数目,来决定聚类中心数目k,这样效果比较好
### Canopy聚类算法简介 Canopy聚类算法是一种快速的预处理聚类方法,通常用于大规模数据集的初步分组。它通过设定两个距离阈值 \( T_1 \) 和 \( T_2 \),其中 \( T_1 > T_2 \),将相似的数据点划分为不同的簇(称为Canopy)。这种方法的主要目的是减少后续复杂聚类算法(如K-Means)的时间开销[^1]。 #### 算法的核心思想 Canopy聚类的核心在于利用简单的距离计算来粗略划分数据点,从而降低后续精确聚类所需的计算量。具体来说,当一个数据点与某个已有的Canopy之间的距离小于\( T_1 \)时,将其分配给该Canopy;如果距离进一步缩小至\( T_2 \),则从待处理集合中移除此点以防止重复分配[^4]。 --- ### Canopy聚类算法的具体步骤 以下是基于参考材料总结的Canopy聚类算法实现步骤: 1. **初始化参数** 定义两个距离阈值 \( T_1 \) 和 \( T_2 \),并准备输入数据集 \( D \)[^4]。 2. **创建首个Canopy** 从未分配的数据集中随机取一个点作为第一个Canopy的中心,并标记为已访问。 3. **迭代分配剩余点** 对于未分配的每个数据点 \( P \): - 计算 \( P \) 到已有所有Canopy中心的距离。 - 如果存在某Canopy使得 \( d(P, C_i) < T_1 \),则将 \( P \) 添加到该Canopy中。 - 若同时满足 \( d(P, C_i) < T_2 \),则直接从数据集中移除 \( P \)[^4]。 4. **生成新Canopy** 当当前点无法被任何现有Canopy接纳时(即对于所有Canopy均有 \( d(P, C_i) >= T_1 \)),以其为中心创建一个新的Canopy。 5. **终止条件** 继续上述过程直至数据集中无剩余未分配点为止。 --- ### Python实现示例 下面是一个简化的Canopy聚类算法Python实现代码片段: ```python import numpy as np def canopy_clustering(data_points, t1, t2): canopies = [] unassigned_points = set(range(len(data_points))) while unassigned_points: # 随机择一个起始点 point_index = next(iter(unassigned_points)) center_point = data_points[point_index] current_canopy = {'center': center_point, 'points': []} to_remove = set() for i in list(unassigned_points): distance = np.linalg.norm(center_point - data_points[i]) if distance < t1: current_canopy['points'].append(i) if distance < t2: to_remove.add(i) canopies.append(current_canopy) unassigned_points -= to_remove return canopies # 测试数据 data = np.random.rand(100, 2) # 生成100个二维随机点 t1 = 0.5 t2 = 0.3 result = canopy_clustering(data, t1, t2) for idx, c in enumerate(result): print(f"Canopy {idx}: Center={c['center']}, Points={len(c['points'])}") ``` --- ### MATLAB实现概述 除了Python外,在MATLAB中同样可以通过矩阵运算高效实现Canopy聚类。其基本逻辑与Python版本一致,主要区别体现在语言特性和函数调用上[^2]。 --- ### 应用场景分析 尽管Canopy可以直接用于聚类任务,但在实际应用中更常作为辅助工具服务于其他高级聚类算法。例如,在未知最佳类别数的情况下,可借助Canopy估计合理的初始K值供K-Means使用[^3]。 ---
评论 1
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值