射线法判断点是否在多边形里面

射线法

射线法是用被测点向任意方向(通常为了好算,使其射向右侧)做一条射线,判断射线与多边形的交点。如果交点的数量为奇数,则被测点在多边形内;如果交点的数量为偶数,则被测点在多边形以外。

使用实例

下面看下集中情况:
a点在多边形内
射线法判断点是否在多边形里面_第1张图片
射线法判断点是否在多边形里面_第2张图片
射线法判断点是否在多边形里面_第3张图片
a点在多边形外
射线法判断点是否在多边形里面_第4张图片
射线法判断点是否在多边形里面_第5张图片

代码说明

1.点与多边形顶点重合

// 点与多边形的顶点重合
		if (((start.x == ref.x) && (start.y == ref.y)) || ((end.x == ref.x) && (end.y == ref.y)))
		{
			return true;
		}

2.判断线段两端点是否在射线两侧
射线法判断点是否在多边形里面_第6张图片

if (((ref.y >= start.y)&&(ref.y < end.y)) || ((ref.y >= end.y)&&(ref.y < start.y)))

3.判断点是在线段的右边还是左边
射线法判断点是否在多边形里面_第7张图片
现根据两点式直线方程求出a点的x值
两点式方程公式:(y-y1)/(y2-y1)=(x-x1)/(x2-x1)。

// 线段上与射线 Y 坐标相同的点的 X 坐标
x = start.x + (ref.y - start.y) * (end.x - start.x) / (end.y - start.y);

x值为a点出的x值,判断点ref是在线段的左边还是右边

// 射线穿过多边形的边界
if (x > ref.x)
{
	++count;
}

完成代码

// 射线法判断点在多边形的内部或外部
bool PtInPolygon(CPoint ref, TVA_Polygon poly)
{
	int i, j, n;
	n = poly.numPoints;
	long int x;
	int count = 0;
	CPoint start, end;

	if (0 == n)
	{
		return false;
	}


	for (i = 0, j = n-1; i < n; j = i++)
	{
		start.x = poly.points[i].x;
		start.y = poly.points[i].y;
		end.x = poly.points[j].x;
		end.y = poly.points[j].y;
		
		// 点与多边形的顶点重合
		if (((start.x == ref.x) && (start.y == ref.y)) || ((end.x == ref.x) && (end.y == ref.y)))
		{
			return true;
		}

		// 判断线段两端点是否在射线两侧
		if (((ref.y >= start.y)&&(ref.y < end.y)) || ((ref.y >= end.y)&&(ref.y < start.y)))
		{
			// 线段上与射线 Y 坐标相同的点的 X 坐标
			x = start.x + (ref.y - start.y) * (end.x - start.x) / (end.y - start.y);

			// 点在多边形的边上
			if (ref.x == x)
			{
				return true;	// onside
			}

			// 射线穿过多边形的边界
			if (x > ref.x)
			{
				++count;
			}
		}
	}

	// 射线穿过多边形边界的次数为奇数时点在多边形内
	return (count%2) ? true/*inside*/ : false/*outside*/;
}

你可能感兴趣的:(数据结构与算法,算法)