1. 程式人生 > >5 分鐘帶你弄懂 k-means 聚類

5 分鐘帶你弄懂 k-means 聚類

聚類與分類的區別

分類:類別是已知的,通過對已知分類的資料進行訓練和學習,找到這些不同類的特徵,再對未分類的資料進行分類。屬於監督學習。

聚類:事先不知道資料會分為幾類,通過聚類分析將資料聚合成幾個群體。聚類不需要對資料進行訓練和學習。屬於無監督學習。

關於監督學習和無監督學習,這裡給一個簡單的介紹:是否有監督,就看輸入資料是否有標籤,輸入資料有標籤,則為有監督學習,否則為無監督學習。更詳盡的解釋會在後續博文更新,這裡不細說。

k-means 聚類

聚類演算法有很多種,K-Means 是聚類演算法中的最常用的一種,演算法最大的特點是簡單,好理解,運算速度快,但是隻能應用於連續型的資料,並且一定要在聚類前需要手工指定要分成幾類。

K-Means 聚類演算法的大致意思就是“物以類聚,人以群分”:

  1. 首先輸入 k 的值,即我們指定希望通過聚類得到 k 個分組;
  2. 從資料集中隨機選取 k 個數據點作為初始大佬(質心);
  3. 對集合中每一個小弟,計算與每一個大佬的距離,離哪個大佬距離近,就跟定哪個大佬。
  4. 這時每一個大佬手下都聚集了一票小弟,這時候召開選舉大會,每一群選出新的大佬(即通過演算法選出新的質心)。
  5. 如果新大佬和老大佬之間的距離小於某一個設定的閾值(表示重新計算的質心的位置變化不大,趨於穩定,或者說收斂),可以認為我們進行的聚類已經達到期望的結果,演算法終止。
  6. 如果新大佬和老大佬距離變化很大,需要迭代3~5步驟。

說了這麼多,估計還是有點糊塗,下面舉個非常形象簡單的例子:
有6個點,從圖上看應該可以分成兩堆,前三個點一堆,後三個點另一堆。現在我手工地把 k-means 計算過程演示一下,同時檢驗是不是和預期一致:
這裡寫圖片描述

1.設定 k 值為2

2.選擇初始大佬(就選 P1 和 P2)

3.計算小弟與大佬的距離:

這裡寫圖片描述
從上圖可以看出,所有的小弟都離 P2 更近,所以次站隊的結果是:

A 組:P1
B 組:P2、P3、P4、P5、P6

4.召開選舉大會:

A 組沒什麼可選的,大佬就是自己
B 組有5個人,需要重新選大佬,這裡要注意選大佬的方法是每個人 X 座標的平均值和 Y 座標的平均值組成的新的點,為新大佬,也就是說這個大佬是“虛擬的”。因此,B 組選出新大哥的座標為:P 哥((1+3+8+9+10)/5,(2+1+8+10+7)/5)=(6.2,5.6)。
綜合兩組,新大哥為 P1(0,0),P哥(6.2,5.6),而P2-P6重新成為小弟。

5.再次計算小弟到大佬的距離:
這裡寫圖片描述

這時可以看到P2、P3離P1更近,P4、P5、P6離P哥更近,所以第二次站隊的結果是:

A 組:P1、P2、P3
B 組:P4、P5、P6(虛擬大哥這時候消失)

6.第二屆選舉大會:
同樣的方法選出新的虛擬大佬:P哥1(1.33,1),P哥2(9,8.33),P1-P6都成為小弟。

7.第三次計算小弟到大佬的距離:
這裡寫圖片描述
這時可以看到 P1、P2、P3 離 P哥1 更近,P4、P5、P6離 P哥2 更近,所以第二次站隊的結果是:
A 組:P1、P2、P3
B 組:P4、P5、P6

我們可以發現,這次站隊的結果和上次沒有任何變化了,說明已經收斂,聚類結束,聚類結果和我們最開始設想的結果完全一致。

K-Means 聚類 MATLAB 實現

關於 K-Means 的演算法具體程式碼,網上有各種版本,這裡也不贅述了,下面結合 MATLAB 中的一些函式給出一個較為簡潔的版本:

X2 = zscore(X);      % zscore方法標準化資料  
Y2 = pdist(X2);      % 計算距離(預設歐式距離)
Z2 = linkage(Y2);    % 定義變數之間的連線,用指定的演算法計算系統聚類樹
T = cluster(Z2,6);   % 建立聚類
H = dendrogram(Z2);  %作出系譜圖

最終聚類系譜圖如下所示:
這裡寫圖片描述

當然,MATLAB 也提供了 kmeans() 函式可供直接聚類使用,詳情可參與其文件。