1

我在下面编写了一些代码来检查两条线段是否相交以及它们是否相交来告诉我在哪里。作为输入,我有每条线两端的 (x,y) 坐标。它似乎工作正常,但现在在 A 线 (532.87,787.79)(486.34,769.85) 和 B 线 (490.89,764.018)(478.98,783.129) 的情况下,它说它们在 (770.136, 487.08) 处相交根本不相交。

有谁知道下面的代码中有什么不正确的?

double                      dy[2], dx[2], m[2], b[2];
double                      xint, yint, xi, yi;
WsqT_Location_Message       *location_msg_ptr = OPC_NIL;

FIN (intersect (<args>));

dy[0] = y2 - y1;
dx[0] = x2 - x1;
dy[1] = y4 - y3;
dx[1] = x4 - x3;

m[0] = dy[0] / dx[0];
m[1] = dy[1] / dx[1];
b[0] = y1 - m[0] * x1;
b[1] = y3 - m[1] * x3;

if (m[0] != m[1])
{
    //slopes not equal, compute intercept
    xint = (b[0] - b[1]) / (m[1] - m[0]);
    yint = m[1] * xint + b[1];

    //is intercept in both line segments?
    if ((xint <= max(x1, x2)) && (xint >= min(x1, x2)) &&
        (yint <= max(y1, y2)) && (yint >= min(y1, y2)) &&
        (xint <= max(x3, x4)) && (xint >= min(x3, x4)) &&
        (yint <= max(y3, y4)) && (yint >= min(y3, y4)))
    {
        if (xi && yi)
        {
            xi = xint;
            yi = yint;

            location_msg_ptr = (WsqT_Location_Message*)op_prg_mem_alloc(sizeof(WsqT_Location_Message));

            location_msg_ptr->current_latitude = xi;
            location_msg_ptr->current_longitude = yi;
        }

        FRET(location_msg_ptr);
    }
}

FRET(location_msg_ptr);
}
4

1 回答 1

0

关于线及其交叉点有一个绝对伟大而简单的理论,它基于为您的点和线添加额外的尺寸。在这个理论中,可以用一行代码从两个点创建一条线,并且可以用一行代码计算线的交点。此外,无穷远处的点和无穷远处的线可以用实数表示。

当点 [x, y] 表示为 [x, y, 1] 并且线 ax+by+c=0 表示为 [a, b, c] 时,您可能听说过齐次表示?对于点 [x, y, w] 的一般齐次表示,转换到笛卡尔坐标是 [x/w, y/w]。这个小技巧使所有的不同,包括无限远的线表示(例如[1,0,0])和使线表示看起来类似于点一。这为许多线/点操作的公式引入了一个很好的对称性,并且是绝对必须在编程中使用的。例如,

通过向量积很容易找到线的交点

p = l1xl2

可以从两点创建一条线是类似的方式:

l=p1xp2

在 OpenCV 的代码中,它只是:

line = p1.cross(p2);
p = line1.cross(line2);

请注意,这里没有需要关注的边缘情况(例如除以零或平行线)。我的观点是,我建议重写你的代码以利用这个关于线和点的优雅理论。

最后,如果你不使用 openCV,你可以使用一个 3D 点类并创建你自己的类似于这个的叉积函数:

template<typename _Tp> inline Point3_<_Tp> Point3_<_Tp>::cross(const Point3_<_Tp>& pt) const
{
    return Point3_<_Tp>(y*pt.z - z*pt.y, z*pt.x - x*pt.z, x*pt.y - y*pt.x);
}
于 2014-03-03T19:17:24.803 回答