检测凸多边形的极值点

时间:2015-08-11 18:12:01

标签: c++ algorithm geometry

如何从确定的点获得凸多边形的极值点?我试图通过点角度来做这个,越来越小的角度是极点,但是当观察者更接近点时,这是无效的。

这是我的代码:

Vec2* bigger = &points[0]; // pointer to point with bigger angle
Vec2* smaller = &points[0]; // pointer to point with smaller angle

Vec2 observer = rayCenter;

// iterate through all points of polygon
for(unsigned u = 0 ; u < points.size() ; u++)
{
    Vec2 distance = observer - points[u];

    if(distance.angle() < (observer - *smaller).angle())
        smaller = &points[u];
    if(distance.angle() > (observer - *bigger).angle())
        bigger = &points[u];
}

结果:

enter image description here

蓝线是排除的点和黄色的理想点。 有没有最好的方法来解决这个问题?

抱歉我的英文。

3 个答案:

答案 0 :(得分:2)

对于观察者的给定位置,多边形顶点A,如果多边形的所有其他点位于的同一侧 > observer-to-A 行(或者,可能位于该行)。

如果已知多边形是凸的,则标准大大简化。无需分析多边形的所有其他点。通过分析两个直接邻居的位置,可以很容易地识别极值点。

如果A是我们的候选点,PN是多边形中的相邻点(上一个和下一个),那么A是一个极端点,如果两者都是PN位于观察者对A线的同一侧。

vec_of_A = A - observer; // observer-to-A vector
vec_of_P = P - observer;
vec_of_N = N - observer;

productP = vec_of_A.x * vec_of_P.y - vec_of_A.y * vec_of_P.x;
productN = vec_of_A.x * vec_of_N.y - vec_of_A.y * vec_of_N.x;

if (sign(productP) == sign(productN))
  // A is an extreme point
else
  // A is not an extreme point

如果P和/或N完全位于观察者对A线上,则需要做出一些额外的决策(取决于您在这种情况下认为极端的点)。

答案 1 :(得分:0)

使用现有凸包和观察点中的点计算新的凸包。在新的凸包中,与观察点相邻的点是你的&#34;极端&#34;分。

Here是一个matlab实现。下面是一个示例输出,其中蓝点是观察点,绿色多边形是红点的凸包。实现返回点(0,0)和(2,0)。

sample

答案 2 :(得分:0)

你不应该直接比较角度,因为有360°环绕。

通过计算由观察者和两个点形成的三角形的有符号区域,倾向于测试“此点更靠左”或“向右”。