【发布时间】:2020-06-16 22:38:44
【问题描述】:
【问题讨论】:
【问题讨论】:
假设你有一个白色像素矩阵,里面有一个非白色圆圈。为了检测圆圈,我会这样做:
for(int x = 0; x < matrix.width; x++){
for(int y = 0; y < matrix.height; y++){
if(matrix[x][y] != white) {
GetCircleCenter(x, y);
return;
}
}
}
现在,假设您知道像素 (x,y) 是圆的一部分,让我们创建一个方法来找到它的中心。
假设您找到的像素标记为黄色。我们现在的目标是找到标记为蓝色的两个像素:
要找到这个,让我们生成两个小的值 v1 和 v2,比如 v1 = v2 = 1。
我们现在对此进行测试:
Color c = matrix[x][y];
int v1 = 1, v2 = 1;
while(matrix[x - v1][y] == c) v1 *= 2;
while(matrix[x + v2][y] == c) v2 *= 2;
当此方法结束时,您知道左侧蓝色像素将介于 (x - v1) 和 (x - v1/2) 之间,右侧蓝色像素将介于 (x + v2/2) 和 (x + v2)。您可以执行二进制搜索以快速找到确切的像素。
当您找到两个像素时,您就知道圆的水平中心。现在,对垂直中心做同样的事情,你会得到你的圆心。
【讨论】:
霍夫变换通常用于边缘图像中的线检测。但是它的一个变体也可以用于圆检测。看看Wikipedia page,它甚至提供了伪代码。
一般的想法是,你的圆圈的所有边缘点都会投票给所有可能导致这些点存在于图像中的圆圈参数(对应于圆圈)。之后,获得最多票数的圆参数(通过检测所有局部最大值或通过迭代检测霍夫空间中的全局最大值直到最大票数降至阈值以下)产生定义图像中可疑圆的参数.
一旦您拥有所有圆圈规格,您就可以简单地查找每个检测到的圆圈中心的颜色。
【讨论】:
圆是具有给定周长的最大面积图形。这可用于搜索。要搜索彩色对象,您可以使用 InRange() 函数。见例子:
import cv2
import numpy as np
img=cv2.imread('calRH.jpg')
blank=np.zeros_like(img)[:,:,0]
#convert to hsv
hsv = cv2.cvtColor(img, cv2.COLOR_BGR2HSV)
#color definition
color_lower = np.array([0,50,33])
color_upper = np.array([180,255,255])
# select only color objects
mask = cv2.inRange(hsv, color_lower, color_upper)
contours,hierarchy = cv2.findContours(mask, 1, 2)
for cnt in contours:
perimeter = cv2.arcLength(cnt,True)
area = cv2.contourArea(cnt)
k=4*np.pi*area/(perimeter*perimeter)
if k>0.86: #test area/perimeter ratio
print('is circle ',k)
tmp=blank.copy()
cv2.drawContours(tmp, [cnt], 0, (255), -1)
cv2.drawContours(img, [cnt], 0, (0,255,0), 1)
m=cv2.mean(img, mask=tmp) # mean color circle
print('mean color', m[0:3])
cv2.imwrite('color_circles.png', img) #save image
【讨论】: