K-Means 算法质心未放置在簇中
K-Means algorithm Centroids are not placed in the clusters
我有问题。我想聚类我的数据集。不幸的是,我的质心不在集群内,而是在集群外。我已经读过
Python k-mean, centroids are placed outside of the clusters关于这个。
但是,我不知道是什么原因。我怎样才能正确聚类?
找到数据集
import pandas as pd
from sklearn.cluster import KMeans
from scipy.cluster import hierarchy
import seaborn as sns
from sklearn import metrics
from sklearn.metrics import silhouette_samples
import matplotlib as mpl
import matplotlib.pyplot as plt
df = pd.read_csv(r'https://gist.githubusercontent.com/Coderanker3/24c948d2ff0b7f71e51b3774c2cc7b22/raw/253ba0660720de3a9cf7dee2a2d25a37f61095ca/Dataset')
df.shape
features_clustering = ['review_scores_accuracy',
'distance_to_center',
'bedrooms',
'review_scores_location',
'review_scores_value',
'number_of_reviews',
'beds',
'review_scores_communication',
'accommodates',
'review_scores_checkin',
'amenities_count',
'review_scores_rating',
'reviews_per_month',
'corrected_price']
df_cluster = df[features_clustering].copy()
X = df_cluster.copy()
model = KMeans(n_clusters=4, random_state=53, n_init=10, max_iter=1000, tol=0.0001)
clusters = model.fit_predict(X)
df_cluster["cluster"] = clusters
fig = plt.figure(figsize=(8, 8))
sns.scatterplot(data=df_cluster, x="amenities_count", y="corrected_price", hue="cluster", palette='Set2_r')
sns.scatterplot(x=model.cluster_centers_[:,0], y=model.cluster_centers_[:,1], color='blue',marker='*',
label='centroid', s=250)
plt.legend(bbox_to_anchor=(1.05, 1), loc=2, borderaxespad=0.)
#plt.ylim(ymin=0)
plt.xlim(xmin=-0.1)
plt.show()
model.cluster_centers_
inertia = model.inertia_
sil = metrics.silhouette_score(X,model.labels_)
print(f'inertia {inertia:.3f}')
print(f'silhouette {sil:.3f}')
[OUT]
inertia 4490.076
silhouette 0.156
您的主要问题的答案:聚类中心不在您的聚类之外。
1:您正在对 features_clustering
列表中显示的 14 个特征进行聚类。
2 :您正在二维 space 上查看集群,任意选择数据 amenities_count
和 corrected_price
以及集群中心的两个坐标 x=model.cluster_centers_[:,0], y=model.cluster_centers_[:,1]
不对应相同的特征。
由于这些原因,您将得到奇怪的结果;他们真的没有任何意义。
底线是您无法查看二维上的 14 维聚类。
为了更清楚地显示点 2,将簇线的绘图更改为
sns.scatterplot(x=model.cluster_centers_[:,10], y=model.cluster_centers_[:,13], color='blue',marker='*', label='centroid', s=250)
根据与数据相同的特征绘制聚类中心。
关于聚类中心在聚类数据之外的 SO 答案的 link 是关于在聚类之前将数据缩放到 0 和 1 之间,然后在绘图时不缩放聚类中心与真实数据。这与您此处的问题不同。
您正在制作多维聚类并且希望它们适合二维地图,它本身是行不通的。让我解释一下,一个变量是一个维度:x1,x2,x3,...,xn 如果你找到簇,它会给你结果 y1,y2,y3,...,yn。如果您在 2D 中映射结果,(我以您为例)
x1 是“amenities_count”,x5 是“corrected_price”。
它将创建仅包含这两个变量的 2D 地图,并且绘图仪肯定会看到您使用 2D 地图,只会从簇中提取前两个变量 y1 和 y2 进行绘图。请注意,xi 与 y1 没有直接关系。
您必须:1) 进行转换以找到其对应的 x、y 或 2) 降低您用于生成包含所有变量信息的 2D 地图的数据的维数。
对于第一种情况,我不是很确定,因为我没有做过(Remapping the data)。
但是在降维上,我推荐大家使用https://en.wikipedia.org/wiki/T-distributed_stochastic_neighbor_embedding或者经典的PCA
道德:如果你想看到一个二维集群,确保你只有 2 个变量。
我有问题。我想聚类我的数据集。不幸的是,我的质心不在集群内,而是在集群外。我已经读过 Python k-mean, centroids are placed outside of the clusters关于这个。
但是,我不知道是什么原因。我怎样才能正确聚类?
找到数据集import pandas as pd
from sklearn.cluster import KMeans
from scipy.cluster import hierarchy
import seaborn as sns
from sklearn import metrics
from sklearn.metrics import silhouette_samples
import matplotlib as mpl
import matplotlib.pyplot as plt
df = pd.read_csv(r'https://gist.githubusercontent.com/Coderanker3/24c948d2ff0b7f71e51b3774c2cc7b22/raw/253ba0660720de3a9cf7dee2a2d25a37f61095ca/Dataset')
df.shape
features_clustering = ['review_scores_accuracy',
'distance_to_center',
'bedrooms',
'review_scores_location',
'review_scores_value',
'number_of_reviews',
'beds',
'review_scores_communication',
'accommodates',
'review_scores_checkin',
'amenities_count',
'review_scores_rating',
'reviews_per_month',
'corrected_price']
df_cluster = df[features_clustering].copy()
X = df_cluster.copy()
model = KMeans(n_clusters=4, random_state=53, n_init=10, max_iter=1000, tol=0.0001)
clusters = model.fit_predict(X)
df_cluster["cluster"] = clusters
fig = plt.figure(figsize=(8, 8))
sns.scatterplot(data=df_cluster, x="amenities_count", y="corrected_price", hue="cluster", palette='Set2_r')
sns.scatterplot(x=model.cluster_centers_[:,0], y=model.cluster_centers_[:,1], color='blue',marker='*',
label='centroid', s=250)
plt.legend(bbox_to_anchor=(1.05, 1), loc=2, borderaxespad=0.)
#plt.ylim(ymin=0)
plt.xlim(xmin=-0.1)
plt.show()
model.cluster_centers_
inertia = model.inertia_
sil = metrics.silhouette_score(X,model.labels_)
print(f'inertia {inertia:.3f}')
print(f'silhouette {sil:.3f}')
[OUT]
inertia 4490.076
silhouette 0.156
您的主要问题的答案:聚类中心不在您的聚类之外。
1:您正在对 features_clustering
列表中显示的 14 个特征进行聚类。
2 :您正在二维 space 上查看集群,任意选择数据 amenities_count
和 corrected_price
以及集群中心的两个坐标 x=model.cluster_centers_[:,0], y=model.cluster_centers_[:,1]
不对应相同的特征。
由于这些原因,您将得到奇怪的结果;他们真的没有任何意义。
底线是您无法查看二维上的 14 维聚类。
为了更清楚地显示点 2,将簇线的绘图更改为
sns.scatterplot(x=model.cluster_centers_[:,10], y=model.cluster_centers_[:,13], color='blue',marker='*', label='centroid', s=250)
根据与数据相同的特征绘制聚类中心。
关于聚类中心在聚类数据之外的 SO 答案的 link 是关于在聚类之前将数据缩放到 0 和 1 之间,然后在绘图时不缩放聚类中心与真实数据。这与您此处的问题不同。
您正在制作多维聚类并且希望它们适合二维地图,它本身是行不通的。让我解释一下,一个变量是一个维度:x1,x2,x3,...,xn 如果你找到簇,它会给你结果 y1,y2,y3,...,yn。如果您在 2D 中映射结果,(我以您为例) x1 是“amenities_count”,x5 是“corrected_price”。
它将创建仅包含这两个变量的 2D 地图,并且绘图仪肯定会看到您使用 2D 地图,只会从簇中提取前两个变量 y1 和 y2 进行绘图。请注意,xi 与 y1 没有直接关系。
您必须:1) 进行转换以找到其对应的 x、y 或 2) 降低您用于生成包含所有变量信息的 2D 地图的数据的维数。
对于第一种情况,我不是很确定,因为我没有做过(Remapping the data)。 但是在降维上,我推荐大家使用https://en.wikipedia.org/wiki/T-distributed_stochastic_neighbor_embedding或者经典的PCA
道德:如果你想看到一个二维集群,确保你只有 2 个变量。