KMeans 中不同簇的数量小于 n_clusters?
Number of distinct clusters in KMeans is less than n_clusters?
我有一些食物图像存储在一个文件夹中。所有图像都没有标记,也没有存储在单独的文件夹中,例如 "pasta" 或 "meat"。我目前的目标是将图像聚类到多个类别中,以便我以后可以评估同一组图像中描绘的食物的味道是否相似。
为此,我加载图像并以一种可以输入 VGG16 进行特征提取的格式对其进行处理,然后将这些特征传递给我的 KMeans 以对图像进行聚类。我使用的代码是:
path = r'C:\Users\Hi\Documents\folder'
train_dir = os.path.join(path)
model = VGG16(weights='imagenet', include_top=False)
vgg16_feature_list = []
files = glob.glob(r'C:\Users\Hi\Documents\folder\*.jpg')
for i in enumerate(files):
img = image.load_img(img_path,target_size=(224,224))
img_data=image.img_to_array(img)
img_data=np.expand_dims(img_data,axis=0)
img_data=preprocess_input(img_data)
vgg16_feature = model.predict(img_data)
vgg16_feature_np = np.array(vgg16_feature)
vgg16_feature_list.append(vgg16_feature_np.flatten())
vgg16_feature_list_np=np.array(vgg16_feature_list)
print(vgg16_feature_list_np.shape)
print(vgg16_feature_np.shape)
kmeans = KMeans(n_clusters=3, random_state=0).fit(vgg16_feature_list_np)
print(kmeans.labels_)
问题是我收到以下警告:
ConvergenceWarning: Number of distinct clusters (1) found smaller than n_clusters (3). Possibly due to duplicate points in X.
我该如何解决?
这是其中一种情况,尽管从 编程 的角度来看您的代码很好,但由于 ML 而无法产生令人满意的结果 相关问题(数据、模型或两者),因此很难 "debug"(我引用这个词,因为这不是典型的调试过程,因为代码本身运行很好)。
首先,这种情况似乎暗示您的特征没有足够的多样性来证明 3 个不同的集群是合理的。而且,只要我们保持在 K-means 上下文中,您就无能为力了;在可用的几个选项中(有关各个参数的详细信息,请参阅 documentation):
- 增加迭代次数
max_iter
(默认300)
- 增加不同质心初始化的数量
n_init
(默认10)
- 将
init
参数更改为 random
(默认值为 k-means++
),或者更好的是,提供一个 3 元素数组,每个目标簇中有一个样本(如果您已经知道这些聚类实际上可能在您的数据中)
- 运行 具有不同
random_state
值的模型
- 综合以上
如果以上方法均无效,则很可能意味着 K-means 实际上不适用于此处,您可能需要寻找替代方法(超出本主题的范围)。事实是,正如在下面的评论中正确指出的那样,K-means 通常不能很好地处理如此高维度的数据。
我有一些食物图像存储在一个文件夹中。所有图像都没有标记,也没有存储在单独的文件夹中,例如 "pasta" 或 "meat"。我目前的目标是将图像聚类到多个类别中,以便我以后可以评估同一组图像中描绘的食物的味道是否相似。
为此,我加载图像并以一种可以输入 VGG16 进行特征提取的格式对其进行处理,然后将这些特征传递给我的 KMeans 以对图像进行聚类。我使用的代码是:
path = r'C:\Users\Hi\Documents\folder'
train_dir = os.path.join(path)
model = VGG16(weights='imagenet', include_top=False)
vgg16_feature_list = []
files = glob.glob(r'C:\Users\Hi\Documents\folder\*.jpg')
for i in enumerate(files):
img = image.load_img(img_path,target_size=(224,224))
img_data=image.img_to_array(img)
img_data=np.expand_dims(img_data,axis=0)
img_data=preprocess_input(img_data)
vgg16_feature = model.predict(img_data)
vgg16_feature_np = np.array(vgg16_feature)
vgg16_feature_list.append(vgg16_feature_np.flatten())
vgg16_feature_list_np=np.array(vgg16_feature_list)
print(vgg16_feature_list_np.shape)
print(vgg16_feature_np.shape)
kmeans = KMeans(n_clusters=3, random_state=0).fit(vgg16_feature_list_np)
print(kmeans.labels_)
问题是我收到以下警告:
ConvergenceWarning: Number of distinct clusters (1) found smaller than n_clusters (3). Possibly due to duplicate points in X.
我该如何解决?
这是其中一种情况,尽管从 编程 的角度来看您的代码很好,但由于 ML 而无法产生令人满意的结果 相关问题(数据、模型或两者),因此很难 "debug"(我引用这个词,因为这不是典型的调试过程,因为代码本身运行很好)。
首先,这种情况似乎暗示您的特征没有足够的多样性来证明 3 个不同的集群是合理的。而且,只要我们保持在 K-means 上下文中,您就无能为力了;在可用的几个选项中(有关各个参数的详细信息,请参阅 documentation):
- 增加迭代次数
max_iter
(默认300) - 增加不同质心初始化的数量
n_init
(默认10) - 将
init
参数更改为random
(默认值为k-means++
),或者更好的是,提供一个 3 元素数组,每个目标簇中有一个样本(如果您已经知道这些聚类实际上可能在您的数据中) - 运行 具有不同
random_state
值的模型 - 综合以上
如果以上方法均无效,则很可能意味着 K-means 实际上不适用于此处,您可能需要寻找替代方法(超出本主题的范围)。事实是,正如在下面的评论中正确指出的那样,K-means 通常不能很好地处理如此高维度的数据。