機器學習 K means 聚類演算法 C

2021-08-29 13:55:17 字數 3303 閱讀 3229

筆記:

尚未解決的問題 :

1. 只支援二維,而不支援三維或更高,需要模板元

2. 尚未實現如何刪除極端點, 即預處理

3. 尚未視覺化

編譯環境 ubuntu gcc 5.4 編譯選項  g++ -std=c++14

#include #include #include #include #include #include #include #include #include #include #include #include #include #include "scopeguard.h"

using point = std::tuple;

using onecluster = std::vector;

void print(const std::vector& clusters) }}

// 讀取檔案內容

std::vector< point > readdata(const std::string& path) );

auto items = 0;

in >> items;

auto x = 0.00, y = 0.00;

std::vector< point > dataset;

for(int i = 0;i < items; ++i)

for(const auto& it : dataset)

std::cout << std::get<0>(it) << "\t" << std::get<1>(it) << "\n";

return dataset;

}// 計算兩個點之間的距離, 在這裡選擇的是歐氏距離

inline double getdistance(const point& a, const point& b)

// 在這些簇中心點 centers 中, one 這個點選離自己最近的乙個,返回這個最近的中心店

const int getlabel(const point& one, const onecluster& centers)

} return label;

}// 給定乙個簇,計算簇的中心,在這裡選擇的是 x, y 均值點

point getcenter(const onecluster& one)

int scale = one.size();

return std::make_tuple(mean_x / scale, mean_y / scale);

}// 給定聚類結果 clusters, 和這些簇的中心 centers,預估聚類效果,方式多樣

const double getevaluate(const std::vector& clusters,

const onecluster& centers)

} return ans;

}// 給定資料集 dataset, 聚成 k 類, 閾值 thresholdvalue(預估差 < 閾值 就結束)

std::vector< onecluster > k_means(const onecluster& dataset, const int k,

const double thresholdvalue)

// clusters 儲存的每乙個元素都是乙個簇, 預先分配 k 個簇的空間

std::vector< onecluster > clusters;

clusters.assign(k, onecluster());

double oldvalue = 0.00, newvalue = 0.00; int cnt = 0;

while(true)

print(clusters);

// 重新計算每個簇的中心點

for(int i = 0;i < k; ++i)

// 重新衡量這次的最小函式值

oldvalue = newvalue; // 先儲存上次的最小均方差之和

newvalue = getevaluate(clusters, centers);

if(abs(newvalue - oldvalue) < thresholdvalue) // 如果變化小於閾值,就結束

return clusters; // nvo

// 每次聚類,得到的聚類都是不一樣的,所以上次的記錄要清空

for(auto &it : clusters)

it.clear();

} return std::vector< onecluster >();

}int main()

/* 尚未解決的問題 :

1. 只支援二維,而不支援三維或更高,需要模板元

2. 尚未實現如何刪除極端點, 即預處理

3. 尚未視覺化

*/

生成測試資料的**:

利用 c++ 生成隨機小數, 聲稱自己的資料集:

#include #include #include #include #include "scopeguard.h"

int main() );

int num = 380;

out << num << "\n";

std::default_random_engine e(time(0));

std::uniform_real_distributiona(0, 4);

std::uniform_real_distributionb(6, 8);

std::uniform_real_distributionc(-3, -6);

for(int i = 0;i < num - 80; ++i)

case 1 :

case 2 :

} }std::uniform_real_distributiond(-10, 10); // 剩下的是大範圍內隨機, 1, 2, 3, 4象限都有

for(int i = 0; i < 80; ++i)

out << d(e) << " " << d(e) << "\n";

return 0;

}

測試結果:

可見元素基本集中在三個象限中

機器學習之聚類演算法 K Means

參考 聚類演算法可以分為 中心點方法 層次聚類方法 基於密度方法 基於網格 基於模型方法。其中最為經典的是k means演算法 k means屬於中心點方法 也有叫劃分方法 演算法經典簡單。演算法 人工選取k值,並選取k個點作為k個簇的質心 對所有樣本分別計算到k個簇的質心的距離 歐式或者曼哈頓 取...

機器學習演算法 之K means聚類

1.模型 k means演算法並沒有顯式的數學模型,演算法的目的是從資料集中得到k個中心點,每個中心點及其周圍的點形成乙個聚簇。k means是一種無監督的學習模型。k means的學習目標如下圖所示 2.策略 k mean演算法採用的損失函式是平方損失函式。每個簇的點距離中心的平方距離之和構成損失...

機器學習之K means聚類演算法

k均值演算法的計算過程非常直觀 1 從d中隨機取k個元素,作為k個簇的各自的中心。2 分別計算剩下的元素到k個簇中心的相異度,將這些元素分別劃歸到相異度最低的簇。3 根據聚類結果,重新計算k個簇各自的中心,計算方法是取簇中所有元素各自維度的算術平均數。4 將d中全部元素按照新的中心重新聚類。5 重複...