判断点是否在区域内

njciapple 2010-04-15 03:17:04
从地图上取到点的经纬度和区域各顶点的经纬度,判断这个点是否在区域内。
例如:经度:118.891898,纬度:31.965411
区域各顶点的经纬度如下:118.89507293701172,31.965306481024427;118.89925718307495,31.964123212108052;118.89816284179687,31.96230276861502;118.89404296875,31.96361349156799

我用的算法如下:

using System.Drawing;

private int IsLeft(Point P0, Point P1, Point P2)
{
int abc = 0;
try
{
abc = ((P1.X - P0.X) * (P2.Y - P0.Y) - (P2.X - P0.X) * (P1.Y - P0.Y));
}
catch (Exception ex)
{
Console.WriteLine("判断点是否在区域某顶点左边时出现异常:{0}", ex.ToString());
}
return abc;
}

private bool PointInFences(Point pnt1, Point[] fencePnts)
{
int wn = 0, j = 0; //wn 计数器 j第二个点指针
try
{
for (int i = 0; i < fencePnts.Length; i++)
{//开始循环
if (i == fencePnts.Length - 1)
j = 0;//如果 循环到最后一点 第二个指针指向第一点
else
j = j + 1; //如果不是 ,则找下一点
if (fencePnts[i].Y <= pnt1.Y)
{ // 如果多边形的点 小于等于 选定点的 Y 坐标
if (fencePnts[j].Y > pnt1.Y)
{ // 如果多边形的下一点 大于于 选定点的 Y 坐标
if (IsLeft(fencePnts[i], fencePnts[j], pnt1) > 0)
{
wn++;
}
}
}
else
{
if (fencePnts[j].Y <= pnt1.Y)
{
if (IsLeft(fencePnts[i], fencePnts[j], pnt1) < 0)
{
wn--;
}
}
}
}
}
catch (Exception ex)
{
Console.WriteLine("判断点和区域时出现异常:{0}", ex.ToString());
}
if (wn == 0)
return false;
else
return true;
}



因为经纬度是小数,而Point要求是整数,我试过PointF,不行。
我将经纬度和区域各顶点的经纬都乘以10000,然后再四舍五入为整数,再判断,点还是不在区域内,实际上那个点是在区域内的,可能小数点后位数较多,乘以10000,不够精确。
如果是一个较大的区域,乘以10000,再四舍五入为整数,用上面的算法能判断出在区域内,如果区域较小,就不在区域内,也就是不准确,请高手指教!
...全文
675 4 打赏 收藏 转发到动态 举报
写回复
用AI写文章
4 条回复
切换为时间正序
请发表友善的回复…
发表回复
njciapple 2010-04-15
  • 打赏
  • 举报
回复
谢谢各位了,解决了,用System.Drawing包中的Point,只能接受int型的,我自己定义了一个Point类,接收double类型的数据

public class Point
{
public double X;
public double Y;

public Point(double x, double y)
{
this.X = x;
this.Y = y;
}
}

然后,直接传到上面算法里面去比较,就这么简单!
这就结贴去!多谢啦!
xiuxianshen 2010-04-15
  • 打赏
  • 举报
回复
point 的点是INT,32位的,反正经纬度只有180大小,如果精度不够,你完全乘以1000000或者10000000,只要不溢出就可以了
gamedragon 2010-04-15
  • 打赏
  • 举报
回复
判断的时候用double,要画的时候再转成PointF画出来就是了。
aoyihuashao 2010-04-15
  • 打赏
  • 举报
回复
如果你是用float做的,那显然是不行的,float只能有6位有效数字。按你这个需求,用dobule就可以了。

把要找的那个坐标的所有位数扩大成整数,在附带给它后面加个0.


double a = 118.8918980,b = 31.965411;

CString astr;
astr.Format("%lf",a);

CString bstr;
bstr.Format("%lf",b);

int lena = astr.GetLength()-astr.Find(".");
int lenb = bstr.GetLength()-bstr.Find(".");
int len = max(lena,lenb);

int N = pow(10,len);
CPoint p(int(a*N),int(b*N));


用这个N,对所有坐标操作一次,再判断,就是整数级别的判断了。

19,468

社区成员

发帖
与我相关
我的任务
社区描述
VC/MFC 图形处理/算法
社区管理员
  • 图形处理/算法社区
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧