gpt4 book ai didi

python - kmeans聚类后如何在图像上绘制质心?

转载 作者:太空宇宙 更新时间:2023-11-03 23:06:37 31 4
gpt4 key购买 nike

我有一张彩色图像,想使用 OpenCV 对其进行 k 均值聚类。

This is the image

这是我要对其进行 k 均值聚类的图像。

这是我的代码:

import numpy as np
import cv2
import matplotlib.pyplot as plt

image1 = cv2.imread("./triangle.jpg", 0)
Z1 = image1.reshape((-1))

Z1 = np.float32(Z1)

criteria = (cv2.TERM_CRITERIA_EPS + cv2.TERM_CRITERIA_MAX_ITER, 10, 1.0)

K1 = 2

ret, mask, center =cv2.kmeans(Z1,K1,None,criteria,10,cv2.KMEANS_RANDOM_CENTERS)

center = np.uint8(center)
print(center)
res_image1 = center[mask.flatten()]
clustered_image1 = res_image1.reshape((image1.shape))

for c in center:
plt.hlines(c, xmin=0, xmax=max(clustered_image1.shape[0], clustered_image1.shape[1]), lw=1.)

plt.imshow(clustered_image1)
plt.show()

这是我从 center 变量中得到的。

[[112]
[255]]

这是输出图像

This is the output image

我的问题是我无法理解输出。我在 center 变量中有两个列表,因为我想要两个类。但是为什么它们只有一个值呢?

它不应该是这样的吗(这是有道理的,因为质心应该是点):

[[x1, y1]
[x2, y2]]

而不是这个:

[[x]
[y]]

如果我像这样将图像读取为彩色图像:

image1 = cv2.imread("./triangle.jpg")
Z1 = image1.reshape((-1, 3))

我得到这个输出:

[[255 255 255]
[ 89 173 1]]

彩色图像输出

color_image_output

有人可以向我解释如何获得 2d 点而不是线吗?另外,在使用彩色图像时,如何解释从 center 变量获得的输出?

如果我不清楚任何地方,请告诉我。谢谢!!

最佳答案

K-Means-clustering 找到相似值的聚类。您的输入是一组颜色值,因此您可以找到描述这 2 个簇的颜色。 [255 255 255]是白色,[ 89 173 1]是绿色。类似于 [112][255]在灰度版本中。你在做什么是color quantization

它们是正确的质心,但它们的维度是颜色,而不是位置。因此你不能在任何地方绘制它。你可以,但我看起来像这样:

enter image description here
看看“颜色位置”如何确定每个像素属于哪个类别?

这不是您可以在图像中找到的东西。您可以做的是找到属于不同簇的像素,并使用找到的像素的位置来确定它们的质心或“平均”位置。

要获得每种颜色的“平均”位置,您必须根据它们所属的类/颜色分离出像素坐标。在下面的代码中,我使用了 np.where( img <= 240)其中 240 是阈值。我不方便使用 240,但您可以使用 K-Means 来确定阈值的位置。 (inRange() 在某些时候可能有用))如果您对坐标求和并将其除以找到的像素数,您将得到我认为您正在寻找的东西:

结果:

enter image description here

代码:

import cv2 

# load image as grayscale
img = cv2.imread('D21VU.jpg',0)

# get the positions of all pixels that are not full white (= triangle)
triangle_px = np.where( img <= 240)
# dividing the sum of the values by the number of pixels
# to get the average location
ty = int(sum(triangle_px[0])/len(triangle_px[0]))
tx = int(sum(triangle_px[1])/len(triangle_px[1]))
# print location and draw filled black circle
print("Triangle ({},{})".format(tx,ty))
cv2.circle(img, (tx,ty), 10,(0), -1)


# the same process, but now with only white pixels
white_px = np.where( img > 240)
wy = int(sum(white_px[0])/len(white_px[0]))
wx = int(sum(white_px[1])/len(white_px[1]))
# print location and draw white filled circle
print("White: ({},{})".format(wx,wy))
cv2.circle(img, (wx,wy), 10,(255), -1)

# display result
cv2.imshow('Result',img)
cv2.waitKey(0)
cv2.destroyAllWindows()

关于python - kmeans聚类后如何在图像上绘制质心?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56973956/

31 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com