看起来像旋转了90度,但我不确定为什么。我不确定是因为我在霍夫(Hough)空间错了,还是因为我取消了霍夫(Hough)画线的方式。还可以有人帮助改善我的峰值检测吗?代码中使用的图像在这里
%% load a sample image; convert to grayscale; convert to binary
%create 'x' image (works well)
a = eye(255);
b = flipud(eye(255));
x = a + b;
x(128,128) = 1;
%image = rgb2gray(imread('up.png')) < 255;
%image = rgb2gray(imread('hexagon.png')) < 255;
%image = rgb2gray(imread('traingle.png')) < 255;
%%% these work
%image = x;
%image = a;
image = b;
%% set up variables for hough transform
theta_sample_frequency = 0.01;
[x, y] = size(image);
rho_limit = norm([x y]);
rho = (-rho_limit:1:rho_limit);
theta = (0:theta_sample_frequency:pi);
num_thetas = numel(theta);
num_rhos = numel(rho);
hough_space = zeros(num_rhos, num_thetas);
%% perform hough transform
for xi = 1:x
for yj = 1:y
if image(xi, yj) == 1
for theta_index = 1:num_thetas
th = theta(theta_index);
r = xi * cos(th) + yj * sin(th);
rho_index = round(r + num_rhos/2);
hough_space(rho_index, theta_index) = ...
hough_space(rho_index, theta_index) + 1;
end
end
end
end
%% show hough transform
subplot(1,2,1);
imagesc(theta, rho, hough_space);
title('Hough Transform');
xlabel('Theta (radians)');
ylabel('Rho (pixels)');
colormap('gray');
%% detect peaks in hough transform
r = [];
c = [];
[max_in_col, row_number] = max(hough_space);
[rows, cols] = size(image);
difference = 25;
thresh = max(max(hough_space)) - difference;
for i = 1:size(max_in_col, 2)
if max_in_col(i) > thresh
c(end + 1) = i;
r(end + 1) = row_number(i);
end
end
%% plot all the detected peaks on hough transform image
hold on;
plot(theta(c), rho(r),'rx');
hold off;
%% plot the detected line superimposed on the original image
subplot(1,2,2)
imagesc(image);
colormap(gray);
hold on;
for i = 1:size(c,2)
th = theta(c(i));
rh = rho(r(i));
m = -(cos(th)/sin(th));
b = rh/sin(th);
x = 1:cols;
plot(x, m*x+b);
hold on;
end
链接:
如何对霍夫变换图像进行去霍夫处理? br />
#1 楼
首先,Matlab具有内置的Hough变换:无需重新发明轮子。以及算法的有效性。您的三角形有白色和黑色的胖区域。理想情况下,三角形的厚度应为1px,标记三角形的边缘。使用Canny Edge Detection[H,T,R] = hough(BW,'RhoResolution',0.5,'Theta',-90:0.5:89.5);
结果是\ theta在$ -90 <\ theta <90 $度的范围内,而您的绘图是$ 0 <\ theta <180 $(或$ 0 <\ theta <\ pi $),因此减去$ 90 $度($ \ pi / 2 $)。在累加器矩阵中可能更大。尽管这里有很多算法,但我过去曾在其中使用过一种算法:
BW = edge(Image,'canny');
查看HoughLines以显示hough变换线,结果:
http://www.mathworks.com/help/toolbox/images/ref/houghlines.html
使用Canny Edge Detector的效果
>“边缘检测”可能会将三角形的每一边变成两条线。
Canny边缘检测的目标是通过使用非最大抑制来产生最大的窄/窄边缘
果壳中的Canny边缘检测(来源:Digital Image Processing,Gonazalez)
1) Define a region shape (typically its square)
2) Define an accumulator threshold
3) Select one pixel in the accumulator matrix
4) If it is a peak (i.e., larger than neighboring values above a threshold)
a) look at the points within the region shape.
b) If there is a larger value
this is not a peak
Else
this is a peak
5) Move to next pixel in accumulator matrix.
评论
$ \ begingroup $
感谢您的答复。我正在从头开始以更好地理解它。坎尼边缘检测仍然给出2个三角形。一个用于内边缘,一个用于外边缘。我从维基百科学到了理论,该理论指出theta为0:pi。我知道内置函数使用-pi / 2:pi / 2,但是应该没有真正的区别吗?
$ \ endgroup $
– Waspinator
2012年4月10日在18:13
$ \ begingroup $
马上行动,射程不会有所作为。 (您能分辨出已旋转180度的线之间的差异吗?)但是,如果您将霍夫变换用于图像校正算法,则确实会有所不同。 (这意味着右侧图像和上下图像之间的差异)
$ \ endgroup $
–CyberMen
2012年10月10日18:38
$ \ begingroup $
边缘检测不会在只想找到1条的地方产生2条线吗?找到粗线中心的方法会更好。
$ \ endgroup $
– Endolith
2012年10月10日19:31
$ \ begingroup $
@endolith在原始帖子中包含了一些关于边缘检测的讨论
$ \ endgroup $
–CyberMen
2012年4月11日,12:50
$ \ begingroup $
“不需要重新发明轮子”?告诉我的老师;-)
$ \ endgroup $
–内森·史威文(Nathan Schwermann)
2012年10月20日6:56
#2 楼
if image(xi, yj) == 1
需要更改为
if image(yj, xi) == 1
为了使线路在dehough中工作
#3 楼
使用3个循环的答案不是最优的,而是可以改善的,这里更多是一种直观的方法/观点:每对有效点都设置
y = ax + b
的唯一a和b。一条线将有许多对,且具有相同的a和b值,因此长线将作为一个峰出现。对于极坐标r&teta坐标也是如此。而不是分别处理每个点,而要使用成对的点。如果可以将所有(通常是稀疏的)点存储在单独的列表中会更好,但这不是必须的。
取每一对并计算其a和b。 (四舍五入为离散值)
转到数组中的特定位置并添加1。
长线->许多对具有相同a,b的对。
零星的点->在特定单元格中进行少量计数->更像是混乱。
从Radon /投影角度看它的另一种方法。
线条会强烈地投射到垂直的“收集线”,因此得分较高。
如果线与“收集线”之间的夹角不为90度,或者收集线未收集投影到该“收集线”中的所有线点,则得分会降低。
评论
您设法解决问题了吗?我正面临类似的问题。谢谢hough转换matlab倒检测器plusieurs椭圆