判斷某一點是否在幾何圖形內部

 

  公司項目,要實現用戶在矩形的紅外圖像上圈一塊區域,計算該區域內部的平均溫度、最大、最小溫度,圈的區域有多是矩形、橢圓、或者任意由多條線段構成的多邊形,實現這個需求能夠轉換爲求一個點是否在該幾何圖形內部,下面總結一下各類幾何圖形的判斷方法。git

1.矩形github

判斷點是否在矩形內,只要肯定點的座標在矩形四個頂點限定範圍內便可算法

如上圖,知足x<=x2&&x>x1&&y>y1&&y<y便可測試

2.橢圓spa

判斷點是否在橢圓內,能夠根據橢圓表達式求得code

如上圖,若是a>b,即焦點在x軸上,則知足(x*x/a/a+y*y/b/b < 1)的點在橢圓內,若是a<b,即焦點在y軸上,則知足(y*y/a/a+x*x/b/b<1)的點在橢圓內blog

3.由多個點構成的不規則圖形get

對於不規則圖形,能夠經過射線法判斷,即計算射線與多邊形各邊的交點,若是是偶數,則點在多邊形外,不然在多邊形內it

算法代碼以下:io

public bool Contains(Point test)
        {
            int i;
            int j;
            bool result = false;
            for (i = 0, j = _pointList.Count - 1; i < _pointList.Count; j = i++)
            {
                if ((_pointList[i].Y > test.Y) != (_pointList[j].Y > test.Y) &&
                    (test.X < (_pointList[j].X - _pointList[i].X) * (test.Y - _pointList[i].Y) / (_pointList[j].Y - _pointList[i].Y) + _pointList[i].X))
                {
                    result = !result;
                }
            }
            return result;
        }

要計算射線與線段的交叉,能夠觀察下圖:

 

  • t點與線段(v1-v2)要發生相交,t.y必須在線段的兩個頂點的y值之間,即  t.y<v2.y&&t.y>v1.y
  • 知足上面這個條件之後,只須要判斷該點在線段的左側仍是右側,若是在線段左側,則該射線與線段相交,要判斷t在左側仍是右側,須要先求得水平線與線段的交點c的x座標:c.x=(t.y-v1.y)*(v2.x-v1.x)/(v2.y-v1.y)+v1.x

由上兩條,能夠推得,t點與線段相交的條件爲: t.y<v2.y  &&  t.y>v1.y  &&  c.x<((t.y-v1.y)*(v2.x-v1.x)/(v2.y-v1.y)+v1.x)

接下來考慮一些特殊狀況:

  • v1.y==v2.y,即射線與線段重合,該狀況不知足第一個條件,於是對結果沒有影響
  • 射線在頂點上相交,有以下幾種狀況:

A頂點爲交叉計數提供奇數(1),B、C爲交叉計數提供偶數(分別是0、2),正好符合算法條件,A是多邊形真正的交叉,B、C不是

算法測試結果以下:

測試程序地址:https://github.com/xienb/SpatialRelationTest

相關文章
相關標籤/搜索