forked from Mryangkaitong/python-Machine-learning
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathK-Means.py
More file actions
92 lines (77 loc) · 3.41 KB
/
Copy pathK-Means.py
File metadata and controls
92 lines (77 loc) · 3.41 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
#K-Means
import numpy as np
import matplotlib.pyplot as plt
from sklearn.cluster import KMeans
from sklearn.externals import joblib #模块二
import pandas as pd
import matplotlib as mpl
from scipy.spatial.distance import cdist #模块一
from sklearn import metrics #模块一
#从磁盘读取城市经纬度数据
X = []
f = open('city.txt')
for v in f:
X.append([float(v.split(',')[1]),float(v.split(',')[2])])
f.close()
#转换成numpy array,形如:[[1.2 , 3.2],[2.3 , 6.3 ],[1.0 , 2.3]],转化前X是一个列表
X = np.array(X)
mpl.rcParams['font.sans-serif'] = [u'SimHei'] #绘图时用来正常显示中文标签
mpl.rcParams['axes.unicode_minus'] = False #绘图时用来正常显示负号
'''
#模块一:
#通过平均畸变程度来确定类簇的数量,通过轮廓系数(Silhouette Coefficient)评价聚类算法(具体来自https://blog.csdn.net/wangxiaopeng0329/article/details/53542606)
#d=cdist(X,Y,'euclidean')#假设X有M个元素,Y有N个元素,最终会生成M行N列的array,用来计算X、Y中每个相对元素之间的欧拉距离
#numpy.min(d,axis=1) #如果d为m行n列,axis=0时会输出每一列的最小值,axis=1会输出每一行最小值
n_clusters = range(2,5) #假设分别在2,3,4中选取一个最合适的n_clusters
meandistortions=[]
metrics_silhouette=[]
for k in n_clusters:
clf=KMeans(n_clusters=k)
cls = clf.fit(X)
meandistortions.append(sum(np.min(cdist(X,clf.cluster_centers_,'euclidean'),axis=1))/X.shape[0])#平均畸变程度值,越小越好
metrics_silhouette.append(metrics.silhouette_score(X,clf.labels_,metric='euclidean')) #轮廓系数,越接近1越好
#平均畸变程度图
plt.subplot(121)
plt.plot(n_clusters,meandistortions,'rx-')
plt.xlabel('k')
plt.ylabel('平均畸变程度')
plt.title('K-Means平均畸变程度图(越小越好) ')
#轮廓系数图
plt.subplot(122)
plt.plot(n_clusters,metrics_silhouette,'bx-')
plt.ylabel('轮廓系数')
plt.xlabel('k')
plt.title('K-Means轮廓系数(越接近1越好)')
#显示
plt.show()
'''
'''
#模块二:
#核心代码:现在把数据和对应的分类放入聚类函数中进行聚类
#其中n_clusters 需要聚成几类,init代表初始点怎么找,max_iter代表迭代次数, n_jobs用的cpu,precompute_distances预先需不需要计算距离
n_clusters=4
clf=KMeans(n_clusters=n_clusters)
cls = clf.fit(X)
#聚类结果的显示,其中用clf和cls均可
print(cls.labels_) #显示每个样本所属的簇
print(clf.cluster_centers_) #4个中心点的坐标
print(clf.inertia_) #用来评估簇的个数是否合适,代表所有点到各自中心的距离和,距离越小说明簇分的越好,选取临界点的簇个数
r1 = pd.Series(cls.labels_).value_counts()
print(r1) #统计每个类别下样本个数
#用聚类的学习结果去预测
X1=[[121.35,26.41],[123.5,45.35]]
print(clf.predict(X1))
#保存模型,加载模型(加载后是类别标签)
joblib.dump(clf,'d:/test/km.txt')
clf = joblib.load('d:/test/km.txt')
#画图
markers = ['x','o','*','+']
colors=['b','r','y','g']
for i in range(n_clusters):
members = cls.labels_ == i
plt.scatter(X[members,0],X[members,1],s=60,marker=markers[i],c=colors[i],alpha=0.5)
plt.xlabel('经度')
plt.ylabel('纬度')
plt.title('K-Means聚合结果(n_clusters=4)')
plt.show()
'''