基于CSV数据集构建KMeans聚类模型的绘图与运行异常问询
KMeans聚类代码故障排查与修复
核心问题汇总
所有导致散点图不显示、聚类无法验证的问题如下:
- 非法数据类型转换:将人口、经度、纬度数值列强制转为
bytes类型,matplotlib无法解析字节类型作为坐标值,无法渲染数据点 - 二维/三维绘图接口混用:原生
plt.scatter是二维绘图方法,不支持传入z轴坐标,配套的plt.zlim()、plt.zlabel()均为3D绘图专属方法,直接调用会触发属性错误中断绘图 - 坐标轴范围设置完全不符合真实值:经度取值范围为-180180、纬度为-9090,设置的0~5000范围会导致所有真实数据点落在坐标轴可视区域外
- 变量拼写错误:聚类结果变量名拼写前后不一致,先写的
indentified_clusters(正确拼写为identified,少写1个f),后续赋值时调用未定义的identified_clusters会触发名称错误 - 语法错误:最后一行散点图代码中,纬度列参数后缺失逗号,直接拼接
c=参数,会触发语法错误 - KMeans特征选择错误:使用
iloc[:,1:3]仅选取了2列特征,遗漏了人口列,且重复调用fit()和fit_predict()做了两次无意义的聚类计算 - 3D绘图未初始化投影:如果要绘制三维散点图,必须提前创建带
3d投影的子图对象,否则无法渲染z轴
修复后完整代码
import numpy as np import matplotlib.pyplot as plt from sklearn.cluster import KMeans import pandas as pd # 读取数据,需确认列名和CSV内列名完全匹配,注意大小写 data = pd.read_csv("data.csv") # 剔除空值,避免聚类计算报错 data = data.dropna(subset=['population', 'longitude', 'latitude']) print(data.head()) # ---------------------- 原始数据3D可视化 ---------------------- fig = plt.figure(figsize=(10,7)) ax = fig.add_subplot(projection='3d') # 直接传入数值列,禁止转bytes类型 ax.scatter(x=data['population'], y=data['longitude'], z=data['latitude']) # 设置匹配真实数据的坐标轴范围,可根据自有数据集调整 ax.set_xlim(0, data['population'].max()*1.1) ax.set_ylim(-130, -60) # 美国本土经度范围,其他地区数据可自行修改 ax.set_zlim(20, 55) # 美国本土纬度范围,其他地区数据可自行修改 ax.set_xlabel('Population') ax.set_ylabel('Longitude') ax.set_zlabel('Latitude') ax.set_title('Raw Data Distribution', fontsize=10) plt.show() # ---------------------- KMeans聚类计算 ---------------------- # 选取全部三个特征:人口、经度、纬度 x = data[['population', 'longitude', 'latitude']] # 初始化聚类模型,固定random_state保证结果可复现 kmeans = KMeans(n_clusters=3, random_state=42) # 单次计算得到聚类结果,无需重复fit identified_clusters = kmeans.fit_predict(x) # 打印聚类结果和聚类中心,直接验证算法是否正常运行 print("各样本所属簇标签:", identified_clusters) print("各簇中心坐标(人口、经度、纬度):", kmeans.cluster_centers_) # ---------------------- 聚类结果可视化 ---------------------- data_with_clusters = data.copy() data_with_clusters['Clusters'] = identified_clusters fig = plt.figure(figsize=(10,7)) ax = fig.add_subplot(projection='3d') # 补全缺失的逗号,按簇映射不同颜色 scatter = ax.scatter( data_with_clusters['population'], data_with_clusters['longitude'], data_with_clusters['latitude'], c=data_with_clusters['Clusters'], cmap='rainbow' ) # 标记聚类中心,方便直观验证聚类效果 ax.scatter( kmeans.cluster_centers_[:,0], kmeans.cluster_centers_[:,1], kmeans.cluster_centers_[:,2], c='black', marker='*', s=200, label='Cluster Centers' ) ax.set_xlabel('Population') ax.set_ylabel('Longitude') ax.set_zlabel('Latitude') ax.set_title('KMeans Clustering Result (3 Clusters)', fontsize=10) plt.legend() plt.colorbar(scatter, label='Cluster ID') plt.show()
效果验证标准
- 代码运行无报错,第一张原始数据分布图可正常显示所有数据点、坐标轴标签
- 控制台会打印每个样本的簇标签、3个聚类中心的坐标值,可手动核对中心位置是否匹配数据分布
- 第二张聚类结果图中,不同颜色代表不同簇,黑色星号标记的聚类中心落在对应颜色点群的中心位置,即代表聚类正常生效
提示:如果使用的不是美国城市数据集,需要自行调整经纬度的坐标轴范围,避免数据点被可视区域遮挡
内容的提问来源于stack exchange,提问作者rraja30
相关产品推荐
相关产品推荐

