【问题标题】:How to assign an new observation to existing Kmeans clusters based on nearest cluster centriod logic in python?python - 如何根据python中最近的聚类质心逻辑为现有的Kmeans聚类分配新的观察?
【发布时间】:2017-09-01 15:34:40
【问题描述】:

我使用以下代码使用 Scikit learn 创建了 k-means 集群。

kmean = KMeans(n_clusters=nclusters,n_jobs=-1,random_state=2376,max_iter=1000,n_init=1000,algorithm='full',init='k-means++')

kmean_fit = kmean.fit(clus_data)

我还使用kmean_fit.cluster_centers_ 保存了质心

然后我腌制了 K 表示对象。

filename = pickle_path+'\\'+'_kmean_fit.sav'
pickle.dump(kmean_fit, open(filename, 'wb'))

这样我就可以使用kmean_fit.predict(). 加载相同的kmeans pickle 对象并将其应用于新数据

问题:

  1. 请问加载kmeanspickle对象的方法并应用 kmean_fit.predict() 允许我将 新观察分配给 基于现有集群的质心的现有集群?这种方法是否只是在新数据上从头开始重新聚类?

  2. 如果此方法不起作用,如何将新观察分配给 鉴于我已经保存了集群,现有集群 centriods 使用高效的 p​​ython 代码?

PS:我知道使用现有集群作为因变量构建分类器是另一种方式,但由于时间紧迫,我不想这样做。

【问题讨论】:

  • 使用源代码,卢克!与其猜测和思考可能是什么,不如打开源代码看看。

标签: python scikit-learn cluster-analysis k-means text-classification


【解决方案1】:

根据Sklearn Kmeans documentation使用predict(X, sample_weight=None)在加载带有存储的Kmeans模型的pickle文件后,将预测X中每个样本所属的最近聚类。

在向量量化文献中,cluster_centers_被称为码本,predict返回的每个值都是码本中最接近的码的索引。

实用说明!
很多时候人们倾向于从model.labels_ 中获取集群标签,但是在这种预测的情况下,请确保使用返回的结果,例如以下示例中的pred_y

    from sklearn.cluster import KMeans
    import pickle

    # load the model
    model = pickle.load(open(filename, 'rb'))

    # predict using the loaded model
    pred_y = model.predict(X)

【讨论】:

    【解决方案2】:

    这个问题有点老了,但是kmeans在合适的时候设置了一个cluster_centers_参数。如果您有质心,您可以通过以下方式设置它:

    kmeans.cluster_centers_ = centroids_init

    它应该能够适应之后。

    【讨论】:

      【解决方案3】:

      是的。 sklearn.cluster.KMeans 对象是否被腌制(如果您正确地取消腌制,您将处理“相同”的原始对象)不会影响您可以使用predict方法来聚类一个新的观察。

      一个例子:

      from sklearn.cluster import KMeans
      from sklearn.externals import joblib
      
      model = KMeans(n_clusters = 2, random_state = 100)
      X = [[0,0,1,0], [1,0,0,1], [0,0,0,1],[1,1,1,0],[0,0,0,0]]
      model.fit(X)
      

      输出:

      KMeans(copy_x=True, init='k-means++', max_iter=300, n_clusters=2, n_init=10,
          n_jobs=1, precompute_distances='auto', random_state=100, tol=0.0001,
          verbose=0)
      

      继续:

      joblib.dump(model, 'model.pkl')  
      model_loaded = joblib.load('model.pkl')
      
      model_loaded
      

      输出:

      KMeans(copy_x=True, init='k-means++', max_iter=300, n_clusters=2, n_init=10,
          n_jobs=1, precompute_distances='auto', random_state=100, tol=0.0001,
          verbose=0)
      

      看看n_clustersrandom_state 参数在modelmodel_new 对象之间有何相同之处?你可以走了。

      使用“新”模型进行预测:

      model_loaded.predict([0,0,0,0])
      
      Out[64]: array([0])
      

      【讨论】:

      • 我的问题有点不同。 kmean_fit 对象真的保存了现有集群的集群质心吗? kmean_fit.predict() 是否找到新观测到所有现有集群质心的距离并分配给最近的质心?我认为 kmean_fit.predict() 只是使用最初使用的 kmeans 参数重新聚类新数据。
      • 我的问题不是酸洗是否有效,这对我来说微不足道。
      • 检查source code 以获取该方法。有一个函数叫做check_is_fitted,正如你想象的那样,它检查KMeans 对象是否已经“适合”到某个特征矩阵X。然后predict方法检查你的数据是否真的是测试数据(使用_check_test_data.
      • 您还可以查看_labels_inertia 方法。为了回答您的问题,我认为predict 方法正在寻找新观察到现有集群质心的距离(即通过fit 方法出现的那些),重新计算距离(如果您运行 fitfit_predict,就会发生这种情况。
      • @ML_Pro 您可能会混淆fitfit_predictpredict 方法。每种方法完成不同的事情。我建议梳理 KMeans 文档(可能还有 scikit-learn 中的其他模型文档)。
      猜你喜欢
      • 2020-05-03
      • 2020-09-10
      • 1970-01-01
      • 2016-11-16
      • 2011-05-22
      • 2021-10-09
      • 2018-10-12
      • 2018-08-12
      • 2011-01-28
      相关资源
      最近更新 更多