From 6de78e20e3dad94cb011c733e00db1484837fdf4 Mon Sep 17 00:00:00 2001 From: Ole Schulz-Trieglaff Date: Sat, 6 Jun 2015 15:25:17 +0100 Subject: [PATCH] Dunn Index as evaluation metric --- 04-Clustering/c++/Makefile | 6 + 04-Clustering/c++/clusters.dat | 300 ++++++++++++++++----------------- 04-Clustering/c++/kmeans | Bin 105852 -> 0 bytes 04-Clustering/c++/kmeans.cpp | 65 ++++++- 4 files changed, 213 insertions(+), 158 deletions(-) create mode 100644 04-Clustering/c++/Makefile delete mode 100755 04-Clustering/c++/kmeans diff --git a/04-Clustering/c++/Makefile b/04-Clustering/c++/Makefile new file mode 100644 index 0000000..0de3dae --- /dev/null +++ b/04-Clustering/c++/Makefile @@ -0,0 +1,6 @@ +CXXFLAGS=-O3 + +all: kmeans + +clean: rm kmeans + diff --git a/04-Clustering/c++/clusters.dat b/04-Clustering/c++/clusters.dat index 42ef2b3..ebf4787 100644 --- a/04-Clustering/c++/clusters.dat +++ b/04-Clustering/c++/clusters.dat @@ -1,150 +1,150 @@ -6.3 2.8 5.1 1.5 1 -6.3 3.4 5.6 2.4 1 -5 3.4 1.5 0.2 2 -4.9 2.5 4.5 1.7 0 -5 3.6 1.4 0.2 2 -5.4 3.9 1.7 0.4 2 -4.6 3.4 1.4 0.3 2 -4.7 3.2 1.3 0.2 2 -4.4 2.9 1.4 0.2 2 -4.9 3.1 1.5 0.1 2 -5.4 3.7 1.5 0.2 2 -4.8 3.4 1.6 0.2 2 -4.8 3 1.4 0.1 2 -4.3 3 1.1 0.1 2 -5.8 4 1.2 0.2 2 -5.7 4.4 1.5 0.4 2 -5.4 3.9 1.3 0.4 2 -5.1 3.5 1.4 0.3 2 -5.7 3.8 1.7 0.3 2 -5.1 3.8 1.5 0.3 2 -5.4 3.4 1.7 0.2 2 -5.1 3.7 1.5 0.4 2 -4.6 3.6 1 0.2 2 -5.1 3.3 1.7 0.5 2 -4.8 3.4 1.9 0.2 2 -5 3 1.6 0.2 2 -5 3.4 1.6 0.4 2 -5.2 3.5 1.5 0.2 2 -5.2 3.4 1.4 0.2 2 -4.7 3.2 1.6 0.2 2 -4.8 3.1 1.6 0.2 2 -5.4 3.4 1.5 0.4 2 -5.2 4.1 1.5 0.1 2 -5.5 4.2 1.4 0.2 2 -4.9 3.1 1.5 0.1 2 -5 3.2 1.2 0.2 2 -5.5 3.5 1.3 0.2 2 -4.9 3.1 1.5 0.1 2 -4.4 3 1.3 0.2 2 -5.1 3.4 1.5 0.2 2 -5 3.5 1.3 0.3 2 -4.5 2.3 1.3 0.3 2 -4.4 3.2 1.3 0.2 2 -5 3.5 1.6 0.6 2 -5.1 3.8 1.9 0.4 2 -4.8 3 1.4 0.3 2 -5.1 3.8 1.6 0.2 2 -4.6 3.2 1.4 0.2 2 -5.3 3.7 1.5 0.2 2 -5 3.3 1.4 0.2 2 -7 3.2 4.7 1.4 1 -6.4 3.2 4.5 1.5 0 -6.9 3.1 4.9 1.5 1 -5.5 2.3 4 1.3 0 -6.5 2.8 4.6 1.5 0 -5.7 2.8 4.5 1.3 0 -6.3 3.3 4.7 1.6 0 -4.9 2.4 3.3 1 3 -6.6 2.9 4.6 1.3 0 -5.2 2.7 3.9 1.4 0 -5 2 3.5 1 3 -5.9 3 4.2 1.5 0 -6 2.2 4 1 0 -6.1 2.9 4.7 1.4 0 -5.6 2.9 3.6 1.3 0 -6.7 3.1 4.4 1.4 0 -5.6 3 4.5 1.5 0 -5.8 2.7 4.1 1 0 -6.2 2.2 4.5 1.5 0 -5.6 2.5 3.9 1.1 0 -5.9 3.2 4.8 1.8 0 -6.1 2.8 4 1.3 0 -6.3 2.5 4.9 1.5 0 -6.1 2.8 4.7 1.2 0 -6.4 2.9 4.3 1.3 0 -6.6 3 4.4 1.4 0 -6.8 2.8 4.8 1.4 1 -6.7 3 5 1.7 1 -6 2.9 4.5 1.5 0 -5.7 2.6 3.5 1 0 -5.5 2.4 3.8 1.1 0 -5.5 2.4 3.7 1 0 -5.8 2.7 3.9 1.2 0 -6 2.7 5.1 1.6 0 -5.4 3 4.5 1.5 0 -6 3.4 4.5 1.6 0 -6.7 3.1 4.7 1.5 1 -6.3 2.3 4.4 1.3 0 -5.6 3 4.1 1.3 0 -5.5 2.5 4 1.3 0 -5.5 2.6 4.4 1.2 0 -6.1 3 4.6 1.4 0 -5.8 2.6 4 1.2 0 -5 2.3 3.3 1 3 -5.6 2.7 4.2 1.3 0 -5.7 3 4.2 1.2 0 -5.7 2.9 4.2 1.3 0 -6.2 2.9 4.3 1.3 0 -5.1 2.5 3 1.1 3 -5.7 2.8 4.1 1.3 0 -6.3 3.3 6 2.5 1 -5.8 2.7 5.1 1.9 0 -7.1 3 5.9 2.1 1 -6.3 2.9 5.6 1.8 1 -6.5 3 5.8 2.2 1 -7.6 3 6.6 2.1 1 -4.6 3.1 1.5 0.2 2 -7.3 2.9 6.3 1.8 1 -6.7 2.5 5.8 1.8 1 -7.2 3.6 6.1 2.5 1 -6.5 3.2 5.1 2 1 -6.4 2.7 5.3 1.9 1 -6.8 3 5.5 2.1 1 -5.7 2.5 5 2 0 -5.8 2.8 5.1 2.4 1 -6.4 3.2 5.3 2.3 1 -6.5 3 5.5 1.8 1 -7.7 3.8 6.7 2.2 1 -7.7 2.6 6.9 2.3 1 -6 2.2 5 1.5 0 -6.9 3.2 5.7 2.3 1 -5.6 2.8 4.9 2 0 -7.7 2.8 6.7 2 1 -6.3 2.7 4.9 1.8 1 -6.7 3.3 5.7 2.1 1 -7.2 3.2 6 1.8 1 -6.2 2.8 4.8 1.8 0 -6.1 3 4.9 1.8 1 -6.4 2.8 5.6 2.1 1 -7.2 3 5.8 1.6 1 -7.4 2.8 6.1 1.9 1 -7.9 3.8 6.4 2 1 -6.4 2.8 5.6 2.2 1 -5.1 3.5 1.4 0.2 2 -6.1 2.6 5.6 1.4 1 -7.7 3 6.1 2.3 1 -4.9 3 1.4 0.2 2 -6.4 3.1 5.5 1.8 1 -6 3 4.8 1.8 0 -6.9 3.1 5.4 2.1 1 -6.7 3.1 5.6 2.4 1 -6.9 3.1 5.1 2.3 1 -5.8 2.7 5.1 1.9 0 -6.8 3.2 5.9 2.3 1 -6.7 3.3 5.7 2.5 1 -6.7 3 5.2 2.3 1 -6.3 2.5 5 1.9 1 -6.5 3 5.2 2 1 -6.2 3.4 5.4 2.3 1 -5.9 3 5.1 1.8 1 +28.8 12.8 24 7.2 0 +27.6 12.8 22.8 9.2 3 +23.2 10.4 16 4.8 2 +27.2 12.8 23.6 9.2 3 +20 14 6.4 2.4 4 +21.6 15.6 6.8 1.6 4 +18.4 13.6 5.6 1.2 4 +20 13.6 6 0.8 4 +17.6 11.6 5.6 0.8 4 +19.6 12.4 6 0.4 4 +21.6 14.8 6 0.8 4 +19.2 13.6 6.4 0.8 4 +19.2 12 5.6 0.4 4 +17.2 12 4.4 0.4 4 +23.2 16 4.8 0.8 4 +22.8 17.6 6 1.6 4 +21.6 15.6 5.2 1.6 4 +20.4 14 5.6 1.2 4 +22.8 15.2 6.8 1.2 4 +20.4 15.2 6 1.2 4 +21.6 13.6 6.8 0.8 4 +20.4 14.8 6 1.6 4 +18.4 14.4 4 0.8 4 +20.4 13.2 6.8 2 4 +19.2 13.6 7.6 0.8 4 +20 12 6.4 0.8 4 +20 13.6 6.4 1.6 4 +20.8 14 6 0.8 4 +20.8 13.6 5.6 0.8 4 +18.8 12.8 6.4 0.8 4 +19.2 12.4 6.4 0.8 4 +21.6 13.6 6 1.6 4 +20.8 16.4 6 0.4 4 +22 16.8 5.6 0.8 4 +19.6 12.4 6 0.4 4 +20 12.8 4.8 0.8 4 +22 14 5.2 0.8 4 +19.6 12.4 6 0.4 4 +17.6 12 5.2 0.8 4 +20.4 13.6 6 0.8 4 +20 14 5.2 1.2 4 +18 9.2 5.2 1.2 4 +17.6 12.8 5.2 0.8 4 +20 14.4 5.6 0.8 4 +20.4 15.2 7.6 1.6 4 +19.2 12 5.6 1.2 4 +20.4 15.2 6.4 0.8 4 +18.4 12.8 5.6 0.8 4 +21.2 14.8 6 0.8 4 +20 13.2 5.6 0.8 4 +28 12.8 18.8 5.6 1 +25.6 12.8 18 6 1 +27.6 12.4 19.6 6 1 +22 9.2 16 5.2 2 +26 11.2 18.4 6 1 +22.8 11.2 18 5.2 2 +25.2 13.2 18.8 6.4 1 +19.6 9.6 13.2 4 2 +26.4 11.6 18.4 5.2 1 +20.8 10.8 15.6 5.6 2 +20 8 14 4 2 +23.6 12 16.8 6 2 +24 8.8 16 4 2 +24.4 11.6 18.8 5.6 1 +22.4 11.6 14.4 5.2 2 +26.8 12.4 17.6 5.6 1 +22.4 12 18 6 2 +23.2 10.8 16.4 4 2 +24.8 8.8 18 6 1 +22.4 10 15.6 4.4 2 +23.6 12.8 19.2 7.2 1 +24.4 11.2 16 5.2 2 +25.2 10 19.6 6 1 +24.4 11.2 18.8 4.8 1 +25.6 11.6 17.2 5.2 1 +26.4 12 17.6 5.6 1 +27.2 11.2 19.2 5.6 1 +26.8 12 20 6.8 1 +24 11.6 18 6 1 +22.8 10.4 14 4 2 +22 9.6 15.2 4.4 2 +22 9.6 14.8 4 2 +23.2 10.8 15.6 4.8 2 +24 10.8 20.4 6.4 1 +21.6 12 18 6 2 +24 13.6 18 6.4 1 +26.8 12.4 18.8 6 1 +25.2 9.2 17.6 5.2 1 +22.4 12 16.4 5.2 2 +22 10 16 5.2 2 +22 10.4 17.6 4.8 2 +24.4 12 18.4 5.6 1 +18.8 12.8 5.2 0.8 4 +20 9.2 13.2 4 2 +22.4 10.8 16.8 5.2 2 +22.8 12 16.8 4.8 2 +22.8 11.6 16.8 5.2 2 +24.8 11.6 17.2 5.2 1 +20.4 10 12 4.4 2 +22.8 11.2 16.4 5.2 2 +25.2 13.2 24 10 3 +23.2 10.8 20.4 7.6 1 +28.4 12 23.6 8.4 0 +25.2 11.6 22.4 7.2 3 +26 12 23.2 8.8 3 +30.4 12 26.4 8.4 0 +19.6 10 18 6.8 2 +29.2 11.6 25.2 7.2 0 +26.8 10 23.2 7.2 3 +28.8 14.4 24.4 10 0 +26 12.8 20.4 8 3 +25.6 10.8 21.2 7.6 3 +27.2 12 22 8.4 3 +22.8 10 20 8 1 +23.2 11.2 20.4 9.6 3 +25.6 12.8 21.2 9.2 3 +26 12 22 7.2 3 +30.8 15.2 26.8 8.8 0 +30.8 10.4 27.6 9.2 0 +24 8.8 20 6 1 +19.6 12 5.6 0.8 4 +22.4 11.2 19.6 8 1 +30.8 11.2 26.8 8 0 +25.2 10.8 19.6 7.2 1 +26.8 13.2 22.8 8.4 3 +20.4 14 5.6 0.8 4 +24.8 11.2 19.2 7.2 1 +24.4 12 19.6 7.2 1 +25.6 11.2 22.4 8.4 3 +28.8 12 23.2 6.4 0 +29.6 11.2 24.4 7.6 0 +31.6 15.2 25.6 8 0 +25.6 11.2 22.4 8.8 3 +25.2 11.2 20.4 6 1 +24.4 10.4 22.4 5.6 1 +30.8 12 24.4 9.2 0 +25.2 13.6 22.4 9.6 3 +25.6 12.4 22 7.2 3 +24 12 19.2 7.2 1 +27.6 12.4 21.6 8.4 3 +26.8 12.4 22.4 9.6 3 +27.6 12.4 20.4 9.2 3 +23.2 10.8 20.4 7.6 1 +18.4 12.4 6 0.8 4 +26.8 13.2 22.8 10 3 +26.8 12 20.8 9.2 3 +25.2 10 20 7.6 1 +26 12 20.8 8 3 +24.8 13.6 21.6 9.2 3 +23.6 12 20.4 7.2 1 diff --git a/04-Clustering/c++/kmeans b/04-Clustering/c++/kmeans deleted file mode 100755 index c8dc637d79791f69ab014dcf89e23b38ad0fa206..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 105852 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 C>jDk{ diff --git a/04-Clustering/c++/kmeans.cpp b/04-Clustering/c++/kmeans.cpp index 38dfd24..4c7c629 100644 --- a/04-Clustering/c++/kmeans.cpp +++ b/04-Clustering/c++/kmeans.cpp @@ -12,8 +12,7 @@ using namespace std; // number of clusters -size_t K=4; - +size_t K=5; struct Point { Point(double x1,double x2, double x3, double x4) @@ -63,8 +62,9 @@ fwditer random_unique(fwditer begin, fwditer end, size_t num_random) { return begin; } + bool getCentroid(const DataVec& data, const int cluster, Point& centroid) { - size_t num(1); + size_t num(0); Point new_centroid(0.0,0.0,0.0,0.0); for (DataVec::const_iterator ct=data.begin();ct!=data.end();++ct) { if (ct->cluster_ == cluster) { @@ -76,6 +76,13 @@ bool getCentroid(const DataVec& data, const int cluster, Point& centroid) { ++num; } } + + if (num==0) { + std::cout << "Cluster unchanged \n"; + return true; + } + + new_centroid.x1_ /= num; new_centroid.x2_ /= num; new_centroid.x3_ /= num; @@ -83,6 +90,7 @@ bool getCentroid(const DataVec& data, const int cluster, Point& centroid) { double d = dist(centroid,new_centroid); std::cout << "getCentroid: d=" << d << "\n"; + std::cout << "num=" << num << "\n"; bool changed = d>0.05 ? true : false; centroid = new_centroid; return changed; @@ -118,25 +126,62 @@ bool fit(DataVec& data, DataVec& centroids) { return converged; } +double dunnIndex(DataVec& data, DataVec& centroids) { + double res = 0.0; + + // compute max cluster diameter + double max_clust_diam = 0.0; + for (size_t i=0;icluster_ == i) { + double d = dist(*ct,centroids[K]); + clust_diam += d; + ++n; + } + } + std::cout << "clust_diam = " << clust_diam << "\n"; + if (n>0) clust_diam /= n; + std::cout << "clust_diam = " << clust_diam << "\n"; + if (clust_diam > max_clust_diam) max_clust_diam = clust_diam; + } + + // compute min intercluster distance + double min_clust_dist = std::numeric_limits::max(); + for (size_t i=0;i0 && d 0) res = min_clust_dist / max_clust_diam; + return res; +} int main(int argc, char** argv) { // seed random generator - //srand(time(NULL)); + srand(time(NULL)); ifstream infile("../iris.data"); string line; DataVec data; + double fac = 4.0; while (std::getline(infile, line)) { std::vector fields; boost::split(fields,line, boost::is_any_of(",")); assert(fields.size() == 5); - double x1 = atof(fields[0].c_str()); - double x2 = atof(fields[1].c_str()); - double x3 = atof(fields[2].c_str()); - double x4 = atof(fields[3].c_str()); + double x1 = atof(fields[0].c_str())*fac; + double x2 = atof(fields[1].c_str())*fac; + double x3 = atof(fields[2].c_str())*fac; + double x4 = atof(fields[3].c_str())*fac; Point p(x1,x2,x3,x4); //std::cout << p << std::endl; @@ -163,6 +208,10 @@ int main(int argc, char** argv) { std::cout << done << "\n"; } + double idx = dunnIndex(data,centroids); + cout << "Dunn Index for this clustering " << idx << "\n"; + + // write clustering to file ofstream of("clusters.dat"); for (DataVec::iterator it = data.begin(); it!=data.end(); ++it) { of << *it << std::endl;