【发布时间】:2016-08-08 03:01:38
【问题描述】:
我正在按照“算法简介”一书来实现线段相交,但我对算法得到的结果感到困惑。我一定在算法中遗漏了一些东西,我需要一些帮助才能找到它。检查以下sn-p代码:
glm::i16vec2 contourLineStart(1057,1762);
glm::i16vec2 contourLineEnd(1057,0);
glm::i16vec2 hilbertLineStart(-1762,-2466);
glm::i16vec2 hilbertLineEnd(-1734,-2466);
正如你所看到的,两条线是用上面定义的坐标形成的,你也可以想象 contourLine 是由 contourLineStart 和 contourLineEnd 制定的,而 hilbertLine 可以由 hilbertLineStart 和 hilbertLineEnd 制定。而且这两条线不可能相交。不幸的是,算法告诉我有一个交叉点,让我很困惑。剩下的代码如下:
glm::i32 direction(const glm::i16vec2& pi,
const glm::i16vec2& pj,
const glm::i16vec2& pk)
{
return ((pk.x - pi.x)*(pj.y - pi.y)) - ((pj.x - pi.x)*(pk.y - pi.y));
}
int main()
{
glm::i16vec2 contourLineStart(1057,1762);
glm::i16vec2 contourLineEnd(1057,0);
glm::i16vec2 hilbertLineStart(-1762,-2466);
glm::i16vec2 hilbertLineEnd(-1734,-2466);
glm::i16 d1 = direction(contourLineStart,contourLineEnd,hilbertLineStart);
glm::i16 d2 = direction(contourLineStart,contourLineEnd,hilbertLineEnd);
glm::i16 d3 = direction(hilbertLineStart,hilbertLineEnd,contourLineStart);
glm::i16 d4 = direction(hilbertLineStart,hilbertLineEnd,contourLineEnd);
if((d1 > 0 && d2 < 0) || (d1 < 0 && d2 > 0) &&
(d3 > 0 && d4 < 0) || (d3 < 0 && d4 > 0))
{
std::cout << "There is a intersection" << std::endl;
}
else
{
std::cout << "There is no intersection" << std::endl;
}
return 0;
}
在这个过程中我有什么遗漏吗?
谢谢
【问题讨论】:
-
编码问题在这里是题外话,所以我将其移至 Stack Overflow。您应该从尝试调试代码开始:手动执行代码,查看每一行发生的情况,并检查它是否有意义。我很怀疑在这里使用 16 位整数;似乎它只是要求整数溢出。
-
我不是 C++ 专家,但预计因为您似乎在对 16 位整数类型进行算术运算(猜测这就是
i16的意思),所以中间结果会溢出。尝试将每个乘法的操作数转换为 32 位 int。 -
感谢您的提示,简单的 int 工作正常。我相信您对 16 位整数的看法是正确的。我将它们重新声明为简单的 int,现在交集测试似乎工作正常。
标签: c++ algorithm geometry glm-math