使用KMeanCluster对多个区域进行聚类,并结合Matplotlib绘制中心点、最大最小距离点
*
– 1. 效果图
– 2. 源码
–
+ 2.1 原始数据——xq.txt
+ 2.2 源码
– 参考
这篇博客将演示如何使用KMeansCluster对多个区域进行聚类,并结合Matplotlib绘制中心点、最大最小区域的点。
写这篇博客源于博友的提问:期望能解决疫情防控应急服务点选址问题。
; 1. 效果图
聚类1效果图如下:
29个小区分别对应29个点,方形对应中心点,三角对应距离中心最近的小区,五角星对应距离中心最远的小区
聚类2效果图如下:
可以看到29个小区聚类为 蓝色圆点、绿色圆点2类。
其中蓝色三角、蓝色方形、蓝色五角星分别对应蓝色聚类的最小、中心、最大小区。
其中绿色三角、绿色方形、绿色五角星分别对应绿色聚类的最小、中心、最大小区。
聚类3效果图如下:
可以看到29个小区聚类为 蓝色圆点、绿色圆点、红色圆点3类。
其中蓝色三角、蓝色方形、蓝色五角星分别对应蓝色聚类的最小、中心、最大小区。
其中绿色三角、绿色方形、绿色五角星分别对应绿色聚类的最小、中心、最大小区。
其中红色三角、红色方形、红色五角星分别对应红色聚类的最小、中心、最大小区。
2. 源码
2.1 原始数据——xq.txt
1 2.00 43.01 11 10.41 41.62 21 23.39 25.23
2 2.42 7.78 12 12.72 29.17 22 23.78 20.60
3 3.34 10.05 13 13.10 16.43 23 25.17 15.81
4 3.98 12.94 14 14.63 27.27 24 26.14 17.61
5 6.12 30.66 15 15.50 24.44 25 27.40 38.08
6 6.70 18.28 16 16.59 40.15 26 29.23 26.11
7 7.17 11.96 17 17.74 35.00 27 30.47 19.66
8 7.80 32.16 18 19.04 5.86 28 31.66 36.94
9 9.03 6.38 19 20.50 44.76 29 31.92 43.53
10 9.81 22.35 20 21.18 30.12
2.2 源码
import cv2
from pylab import *
def get_points():
with open("maps/xq.txt", "r") as f:
str = f.read()
str = str.replace("\n", " ")
strs = np.array(str.split(" "))
data = np.array([float(x) for x in strs]).reshape(29, 3)
data = data[data[:, 0].argsort()]
return data
def get_distance(pt1, pt2):
return math.sqrt(math.pow(pt1[0] - pt2[0], 2) + math.pow(pt1[1] - pt2[1], 2))
def get_most_distance(center, data, color, flag=False):
dis = []
for i in data:
dis.append(get_distance(center, [i[0], i[1]]))
minIndex = dis.index(min(dis))
maxIndex = dis.index(max(dis))
plt.scatter(data[minIndex, 0], data[minIndex, 1], s=120, c=color, marker='^')
plt.scatter(data[maxIndex, 0], data[maxIndex, 1], s=120, c=color, marker='*')
if flag:
return dis.index(min(dis)) + 1
return dis.index(max(dis)) + 1
def k_means_cluster(data, n=1):
Z = data[:, 1:]
Z = np.float32(Z)
criteria = (cv2.TERM_CRITERIA_EPS + cv2.TERM_CRITERIA_MAX_ITER, 10, 1.0)
ret, label, centers = cv2.kmeans(Z, n, None, criteria, 10, cv2.KMEANS_RANDOM_CENTERS)
print('Kmeanscluster (', n, ') —— center: ', centers)
mpl.rcParams['font.sans-serif'] = ['SimHei']
mpl.rcParams['axes.unicode_minus'] = False
color_arr = np.array(['b', 'g', 'r', 'c', 'm', 'y', 'k', 'w'])
colors = color_arr[:n]
for x, y, zone in zip(data[:, 1], data[:, 2], data[:, 0]):
plt.text(x, y + 1, '%s' % int(zone), ha='center', va='bottom', fontdict={'color': 'black',
'weight': 'bold',
'size': 12})
for i, (color, center) in enumerate(zip(colors, centers)):
A = Z[label.ravel() == i]
print('cluster ', i, ' : ', len(A))
plt.scatter(A[:, 0], A[:, 1], c=color)
plt.scatter(center[0], center[1], s=120, c=color, marker='s')
plt.text(x=center[0], y=center[1] + 2, s='中心点', ha='center', va='baseline', fontdict={'color': 'black',
'weight': 'bold',
'size': 12})
get_most_distance(center, A, color, plt)
plt.xlabel('x'), plt.ylabel('y')
plt.title("emergency service location KMeanCluster" + str(n) + " res")
plt.show()
data = get_points()
k_means_cluster(data, 1)
k_means_cluster(data, 2)
k_means_cluster(data, 3)
参考
Original: https://blog.csdn.net/qq_40985985/article/details/119830685
Author: 程序媛一枚~
Title: 使用KMeanCluster对多个区域进行聚类,并结合Matplotlib绘制中心点、最大最小距离点
原创文章受到原创版权保护。转载请注明出处:https://www.johngo689.com/560288/
转载文章受原作者版权保护。转载请注明原作者出处!