kmeans算法原理及opencv中的实现
算法的目的:
数据分类,聚类,识别
对象和标准:
输入:n个数据对象
输出:k个类别, 且满足方差最小的k个聚类,聚类方差度量
每个对象与聚类的相似度:一般是采用各个对象到聚类中心(一般是均值中心)的距离,距离哪个中心近,就是与哪个类的相似度高。
聚类的紧密度度量(聚类好坏的度量):所有对象到各自聚类中心的方差和。
基本算法步骤:
初始化:从 n个数据对象任意选择 k 个对象作为初始聚类中心;
迭代:
1. 根据每个聚类对象的均值(中心对象),计算每个对象与这些中心对象的距离;并根据最小距离重新对相应对象进行分类;
2. 由新的分类数据,重新计算每个(有变化)聚类的均值(中心对象);
3. 计算标准测度函数,当满足一定条件,如函数收敛时,则算法终止;如果条件不满足则循环执行。如opencv中,每次迭代,最大的聚类中心位移max_center_shift < criteria.epsilon小于精度要求时,就结束迭代。以及迭代次数超过设定的最大值时,也结束 iter >= criteria.maxCount。
结束。计算方差,及labels每个对象的分类结果,返回。
算法的时间复杂度上界为O(n*k*t), 其中t是迭代次数。属于非监督学习方法。
OpenCV中增加了参数:
attempts:使用不同的初始化条件,进行分类的次数
flag: KMEANS_RANDOM_CENTERS, KMEANS_PP_CENTERS, KMEANS_USE_INITIAL_LABELS
增加以上参数的目的,是防止kmeans算法陷入局部最优,即分类的结果不是最好的。局部最优的示例:
横向分类,纵向分类分别是两种分类结果。显然,横向分类是局部最优。
KMEANS_USE_INITIAL_LABELS是第一次采用用户自己设置的初始化的中心点进行运算,而后面的尝试则采用随机算法(或半随机)选取的中心。