K-means(K-均值)由簇中样本的均值代表整个簇,而K-medoids(K-中心点)由处在簇中心区域的某个样本代表整个簇。
K-means聚类:
基本思想:初始随机给定k个簇中心,按着最近邻原则把待分类样本点分到各个簇中,单后按照平均法重新计算各个簇的质心,从而确定新的簇心,一直迭代,直到簇心的移动小于给定的值,或者达到最大迭代次数。
优缺点:
优点:
1,可扩展性好,算法复杂度为O(nkt),其中n:样本个数,k:簇的个数,t:是最大迭代次数。
缺点:
1,需要事先指定k,难以选定。
2,初始聚类中心的选择对聚类结果有较大的影响
3,不适合发现非球状簇
4,对噪声和离群点不敏感。
算法的评价准则:
误差平方和
平均误差平方和:
簇间平均距离:
评价聚簇的效果:
"""
1,随机取K个中心点
2,计算所有点到中心点的距离
将所有点分别放入到中心点所在的簇
更新中心点
如果中心点不变,结束迭代
迭代
"""
import numpy as np
import matplotlib.pyplot as plt
#获取数据集
def loadDataSet(filename):
return np.loadtxt(filename, delimiter=",", dtype=np.float)
#取出k个中心点
def initCenters(dataset,k):
"""
返回刻个中心点
:param dataset:数据集
param k:聚类中心
return
"""
cenrersIndex = np.random.choice(len(dataset), k, replace=False)
return dataset[cenrersIndex]
#计算距离公式
def distance(x,y):
return np.sqrt(np.sum((x-y)**2))
#kmeans的核心算法
def kemans(dataset,k):
"""
返回k个簇
:param dataset:数据集
:param k:中心点的个数
return:
"""
#初始化中心
centers = initCenters(dataset, k)
# print(centers)
n,m = dataset.shape
# print(n)
#用于存储每个样本属于哪个簇
clusters = np.full(n,np.nan)
#迭代标志
flag = True
while flag:
flag = False
#计算所有点到簇中心的距离
for i in range(n):
# print(clusters[i])
minDist,clustersIndex = 99999999999,0
for j in range(len(centers)):
dist = distance(dataset[i],centers[j])
if dist<minDist:
#为样本分簇
minDist = dist
clustersIndex = j
if clusters[i]!=clustersIndex:
clusters[i] = clustersIndex
flag = True
#更新簇中心
for i in range(k):
subdataset = dataset[np.where(clusters == i)]
centers[i] = np.mean(subdataset,axis=0)
return clusters,centers
#显示
def show(dataset,k,clusters,centers):
n,m=dataset.shape
if m>2:
print("维度大于2")
return 1
#根据簇不同,颜色不同
colors = ["r","g","k","b"]
for i in range(n):
clusterIndex = clusters[i].astype(np.int)
plt.plot(dataset[i][0],dataset[i][1],color=colors[clusterIndex],marker="o")
for i in range(k):
plt.scatter(centers[i][0],centers[i][1],marker="s")
plt.show()
K-medoids:
基本思想:选取有代表性的样本(而不是均值)来表示整个簇,即选取最靠近中心的点(medoid)d的样本点代表整个簇。
核心:如果代表样本能被非代表样本点所取代,则替代产生的代价S是所有样本产生的代价总和。
总代价定义:
其中:n代表样本集的个数,Cpjh代表中心点样本oj被非中心点oh替代后的样本点p的代价。