聚类算法效果衡量标准及图片压缩案例

聚类算法效果衡量标准及图片压缩案例

1.SSE:误差平方和

误差平方和:计算每个簇内的样本到该簇质心的距离平方,然后加和,然后把每个簇的距离平方和再相加,公式如下:
聚类算法效果衡量标准及图片压缩案例_第1张图片
SSE比较
聚类算法效果衡量标准及图片压缩案例_第2张图片

2. “肘”方法(Elbow method)

“肘”方法(Elbow method):
(1)对于n个点的数据集,迭代计算k from 1 to n,每次聚类完成后计算每个点到其所属的簇中心的距离的平方和;
(2)平方和是会逐渐变小的,直到k==n时平方和为0,因为每个点都是它所在的簇中心本身。
(3)在这个平方和变化过程中,会出现一个拐点也即“肘”点,下降率突然变缓时即认为是最佳的k值。
聚类算法效果衡量标准及图片压缩案例_第3张图片

3. 轮廓系数法(Silhouette Coefficient)

结合了聚类的凝聚度(Cohesion)和分离度(Separation),用于评估聚类的效果。
聚类算法效果衡量标准及图片压缩案例_第4张图片

  • a是Xi与同簇的其他样本的平均距离,称为凝聚度(Cohesion);
  • b是Xi与最近簇中所有样本的平均距离,称为分离度(Separation)。

最近簇的定义:
聚类算法效果衡量标准及图片压缩案例_第5张图片

  • p是某个簇Ck中的样本。即,用Xi到某个簇所有样本平均距离作为衡量该点到该簇的距离后,选择离Xi最近的一个簇作为最近簇。
  • 求出所有样本的轮廓系数后再求平均值就得到了平均轮廓系数。
  • 平均轮廓系数的取值范围为[-1,1],系数越大,聚类效果越好。
  • 簇内样本的距离越近,簇间样本距离越远

4. Calinski-Harabasz Index

Calinski-Harabasz:类别内部数据的协方差越小越好,类别之间的协方差越大越好,这样的Calinski-Harabasz分数s会高,分数s高则聚类效果越好。
聚类算法效果衡量标准及图片压缩案例_第6张图片

  • m为训练集样本数,k为类别数,tr为矩阵的迹。
  • Bk为类别之间的协方差矩阵,Wk为类别内部数据的协方差矩阵。

用尽量少的类别聚类尽量多的样本,同时获得较好的聚类效果。

总结

  1. 肘部法
    下降率突然变缓时即认为是最佳的k值
  2. SC系数
    取值为[-1, 1],其值越大越好
  3. CH系数
    分数s高则聚类效果越好

代码案例3: 聚类算法的图片压缩实战应用

运用Kmeans算法实现图像压缩,并观察压缩后图像的变化

# 导包
import numpy as np
import matplotlib.pyplot as plt
from sklearn.cluster import KMeans
from sklearn.metrics import pairwise_distances_argmin
from sklearn.datasets import load_sample_image
from sklearn.utils import shuffle
from time import time

# 导入图片,设定参数
n_colors = 32

# 加载sklearn内部图片
china = load_sample_image("china.jpg")
# china

# 转换为浮点数,而不是默认的8位整数编码。为了使得plt.Imshow在浮点数数据上更好的显示(需要在[0-1]范围内)
china = np.array(china, dtype=np.float64) / 255

# 将图片由三维转化到二维
w, h, d = original_shape = tuple(china.shape)
assert d == 3
image_array = np.reshape(china, (w * h, d))

# 在小样本数据上拟合模型
t0 = time()
image_array_sample = shuffle(image_array, random_state=0)[:1000] # 打乱样本数据顺序(对应打乱)
kmeans = KMeans(n_clusters=n_colors, random_state=0).fit(image_array_sample)
print("done in %0.3fs." % (time() - t0))

#为所有点赋标签
t0 = time()
labels = kmeans.predict(image_array)
print("done in %0.3fs." % (time() - t0))

# 压缩聚类
def recreate_image(codebook, labels, w, h):
    """从code book和labels中重新创建(压缩)图像 """
    d = codebook.shape[1]
    image = np.zeros((w, h, d)) #生成三维数组,用0填充
    label_idx = 0 
    for i in range(w):
        for j in range(h):
            image[i][j] = codebook[labels[label_idx]] # 每个像素点用聚类后的标签填充
            label_idx += 1
    return image

# 可视化
plt.figure(1)
plt.clf()
ax = plt.axes([0, 0, 1, 1])
plt.axis('off')
plt.title('原始图片 (96,615 colors)')
plt.imshow(china)

plt.figure(2)
plt.clf()
ax = plt.axes([0, 0, 1, 1])
plt.axis('off')
plt.title('聚类后的图片(32 colors, K-Means)')
plt.imshow(recreate_image(kmeans.cluster_centers_, labels, w, h))

聚类算法图像压缩原理(自总结):先将图片转化为二维ndarray,根据给定k值(n_colors = 32)应用聚类算法(Kmeans)进行聚类,给每个样本赋予聚类后的标签,用标签值和图片维度重新生成图片,达到压缩效果(用更少的颜色来表达图片)。

你可能感兴趣的:(聚类,算法)