如何绘制K-means并打印出簇外的点

4
如何对以下数据进行K均值聚类绘图。
no,store_id,revenue,profit,state,country
0,101,779183,281257,WD,India
1,101,144829,838451,WD,India
2,101,766465,757565,AL,Japan

我的代码如下

import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
from sklearn.cluster import KMeans
df1 = pd.get_dummies(df, columns=['state','country'])
clusters = 2   
km = KMeans(n_clusters=8).fit(df1)
labels = km.predict(df1)
df1['cluster_id'] = km.labels_
def distance_to_centroid(row, centroid):
     row = row[['no','store_id','revenue','profit','state','country']]
     return euclidean(row, centroid)
df1['distance_to_center0'] = df1.apply(lambda r: distance_to_centroid(r,
                             km.cluster_centers_[0]),1)

df1['distance_to_center1'] = df1.apply(lambda r: distance_to_centroid(r,
                             km.cluster_centers_[1]),1)



dummies_df =dummies[['distance_to_center0','distance_to_center1','cluster_id']]
test = {0:"Blue", 1:"Red", 2:"Green",3:"Black",4:"Orange",5:"Yellow",6:"Violet",7:"Grey"}
sns.scatterplot(x="distance_to_center0", y="distance_to_center1", data=dummies_df, hue="cluster_id", palette = test)

为了找到中心点,下面是代码。
km = KMeans(n_clusters=7).fit(dummies)
closest, _ = pairwise_distances_argmin_min(km.cluster_centers_, dummies)
closest
  • 如何为聚类绘制散点图

  • 如何将打印点与聚类分开

就像最小异常值方法中-1是离群值(scikit learn)。kmeans.labes_仅打印1和0,如何获取离群值


你在KMeans上运行的变量是什么?但通常可以使用plt.scatter(x, y)。你所说的“将打印点远离聚类”是什么意思? - moe asal
@moeassal 我不需要预测任何东西,我只想绘制一个图形并找到远离聚类的点。 - user6882757
@moeassal,你只考虑了两个变量。 - user6882757
抱歉,您想做什么?您在绘图中想使用多少个变量? - PV8
你是否正在尝试根据位置的纬度和经度计算质心/聚类? - Matt L.
显示剩余3条评论
4个回答

2

由于您正在基于多个特征(WD,AL,India,Japan等)进行聚类,因此您需要执行以下操作之一才能可视化图表。

  1. 使用降维方法,例如PCA、TSNE或Auto-Encoders,将其转换为2个变量(用于2D图表)或3个变量(用于3D图表)

  2. 每次选择2个或3个特征进行绘图,保持其余特征不变。


1

如果维度大于3,你将无法绘制数据(在你的情况下,不计算位置,维度为4)。相反,您可以找到特征和K点之间的距离,并使用它来获得发生的一般情况。希望这有所帮助!


0

针对聚类的散点图:您只能在2D或3D中绘制/可视化,但是您示例中的数据至少具有4个特征(即4个维度)。要绘制聚类,您需要将维数降低到所需的2或3个,可以通过减少用于聚类的特征集(例如通过人工预选或使用特征缩减技术)和/或将结果投影到降低的维度上来实现(例如,如果您只有3个节点/聚类,则可以使用包含所有3个质心的平面)

远离“聚类”/异常值的点:Kmeans算法将每个点分配给一个聚类。聚类的紧密性反映在inertia_值中。获取异常值的一种简单方法是查看点与其分配质心的距离,并使用阈值(如标准偏差的倍数)分类异常值。另一种更复杂的方法是运行算法,然后删除距其分配质心最远的数据点,重新运行算法并检查平均惯性下降。重复直到没有显着下降为止。被删除的点集是异常值。

还有其他聚类算法(如DBCSAN),尝试隐式检测异常值。


0

不要听信否定者的话。虽然在2D图像中合理准确地表示超过3D数据是不可能的,但降维技术如PCATSNE可以通过在较低维度空间上使用线性(PCA)或非线性(TSNE)投影来帮助解决这个问题。

这里有一个葡萄酒数据集的例子,它有13个维度。你提供的数据只有3个数据点,所以不太具有说明性。

import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
from sklearn.preprocessing import scale
from sklearn.cluster import KMeans
from sklearn.datasets import load_wine
from sklearn.decomposition import PCA
import matplotlib.cm as cm

# Load wine dataset. It has 13 float-type features and 3 classes of wine
data = load_wine()

df = pd.DataFrame(data = scale(data.data), columns=data.feature_names)

# Create a separate dataframe for target and predictions
df_labels = pd.DataFrame(data=data.target, columns=['target'])

class_names = list(data.target_names)

# Perform K-means clustering
km = KMeans(n_clusters=3).fit(df)
df_labels['predictions'] = km.predict(df)

# Use PCA to reduce dataset dimentions to project 13 dimensional dataset onto 2 dimensions
pca = PCA(n_components=2).fit(df)

df_reduced = pd.DataFrame(data=PCA(n_components=2).fit_transform(df.values), columns=['x', 'y'])

fig, (ax_true, ax_pred) = plt.subplots(1, 2, figsize=(20, 10))

# Use red, green, and blue to color different clusters
colors = ['r', 'g', 'b']
colors_true = [colors[i] for i in df_labels['target'].values]
colors_pred = [colors[i] for i in df_labels['predictions'].values]

# Plot cluster centroids with X symbols
centroids = pca.transform(km.cluster_centers_)

x = df_reduced['x'].values
y = df_reduced['y'].values
titles = ['target', 'predictions']

for ax, colors, title in zip([ax_true, ax_pred], [colors_true, colors_pred], titles):
    ax.scatter(x, y, marker='o', s=5, linewidths=3, color=colors)

    # Plot the centroids as a black X
    ax.scatter(centroids[:, 0], centroids[:, 1],
                marker='x', s=50, linewidths=2,
                color='black', zorder=10)

    ax.set_title(title, fontsize= 14)
    ax.set_xticks(())
    ax.set_yticks(())

plt.xlim((1.1*min(x), 1.1*max(x)))
plt.ylim((1.1*min(y), 1.1*max(y)))
plt.show()

这应该会生成如下图所示的绘图: 输入图像描述

左边的颜色对应于真实聚类,右边则表示KMeans预测。将df_labels中的targetprediction进行比较,可以揭示那些被错误分类(不在任何给定聚类之内)的点。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接