使用VC ++和Open CV。这是我正在尝试做的事情: 找到前三个近乎水平的霍夫线并绘制它们。 找到所有近乎垂直的线并绘制它们 如果任何垂直线高于水平线,则FLAG设置为0 如果上面没有垂直Hough线(全部在下面),则水平线然后FLAG = 1
int n, i,c=0;
int flag = 0;
cvCanny( src, dst, 50, 150, 3 );
lines = cvHoughLines2( dst, storage, CV_HOUGH_PROBABILISTIC, 1, CV_PI/180, 10, 5, 5 );
n = lines->total;
for( i = 0; i < n; i++ )
{
CvPoint* line = (CvPoint*)cvGetSeqElem(lines,i);
CvPoint pt1, pt2, hpt1, hpt2, vpt1, vpt2;
int hy = 0, vy = 0;
pt1 = line[0];
pt2 = line[1];
theta = atan( (double)(pt2.y - pt1.y)/(pt2.x - pt1.x) ); /*slope of line*/
degree = theta*180/CV_PI;
if( fabs(degree) < 8) //checking for near horizontal line
{
c++;
if( c > 0 && c <5) /*main horizontal lines come first*/
{
cvLine( out, pt1, pt2, CV_RGB(255, 255,255), 1, CV_AA, 0 );
hpt1 = line[0];
hpt2 = line[1];
if( hpt1.y > hpt2.y ) //finds out lower end-point
hy = hpt1.y;
else
hy = hpt2.y;
}
}
if( fabs(degree) > 70 ) /*near vertical lines*/
{
cvLine( out, pt1, pt2, CV_RGB(255, 255,255), 1, CV_AA, 0 );
vpt1 = line[0];
vpt2 = line[1];
if( vpt1.y > vpt2.y ) //finds upper end-pt of vertical line
vy = vpt1.y;
else
vy = vpt2.y;
if( vy >= hy ) //if vert line is lower than horizontal line
flag = 1;
else
flag = 0;
}
}
display( out, "hough lines" );
return flag;
}
然而,对于图像,即使在水平线上方检测到垂直线 - 仍然标志返回1.所以我是否错误地沿着轴计数?请帮帮我。
答案 0 :(得分:4)
if( fabs(degree) > 70 )
和if( fabs(degree) < 8 )
行看起来不对。大约180°的角度意味着几乎是水平的......你可能想要改变它,并牢记角度的周期性(所以360左右也几乎是水平的)。一个很好地处理的方法是使用if (fabs(cos(angle - desired_angle)) > 0.996)
,这意味着大致“如果angle和desired_angle在彼此的5度范围内,忽略方向”。 0.996
大致是5度的余弦,如果你需要它更精确地放更多的数字 - 0.9961946980917455
是一个更接近的匹配。
此外,您的循环顺序已关闭。你没有find the first three nearly-horizontal hough lines and draw them. find all the nearly-vertical lines and draw them if any vertical line is above the horizontal line
在这个序列中,你以任何顺序遍历所有行,并独立处理它们 - 垂直的那些可以在水平之前,所以你不知道要检查什么。 / p>
第三,
if( hpt1.y > hpt2.y ) //finds out lower end-point
hy = hpt1.y;
else
hy = hpt2.y;
VS
if( vpt1.y > vpt2.y ) //finds upper end-pt of vertical line
vy = vpt1.y;
else
vy = vpt2.y;
使用相同的代码查找较低的坐标以找到较高的坐标。你认为那可行吗?
四,
if( vy >= hy ) //if vert line is lower than horizontal line
flag = 1;
else
flag = 0;
flag的值取决于最后一遍这段代码。这与您说明中的any
不符。
答案 1 :(得分:1)
更简单的方法是不使用PPHL(渐进概率Hough线算法),而是使用SHL(标准HL)!这样你就可以获得角度和半径的极线形状!然后你可以检查角度,而不用自己计算。
如果输出角度大约为0°或180°,则为垂直线,如果大约为90°,则为水平线....