判斷點在多邊形內演算法

2021-09-25 12:34:53 字數 2338 閱讀 1631

點和多邊形關係的演算法實現

好了,現在我們已經了解了向量叉積的意義,以及判斷直線段是否有交點的演算法,現在回過頭看看文章開始部分的討論的問題:如何判斷乙個點是否在多邊形內部? 根據射線法的描述,其核心是求解從p點發出的射線與多邊形的邊是否有交點。注意,這裡說的是射線,而我們前面討論的都是線段,好像不適用吧?沒錯,確實是 不適用,但是我要介紹一種用計算機解決問題時常用的建模思想,應用了這種思想之後,我們前面討論的方法就適用了。什麼思想呢?就是根據問題域的規模和性質 抽象和簡化模型的思想,這可不是故弄玄虛,說說具體的思路吧。

計算機是不能表示無窮大和無窮小,計算機處理的每乙個數都有確定的值,而且必須有確定的值。我們面臨的問題域是整個實數空間的座標系,在每個維度上都是 從負無窮到正無窮,比如射線,就是從座標系中乙個明確的點到無窮遠處的連線。這就有點為難計算機了,為此我們需要簡化問題的規模。假設問題中多邊形的每個 點的座標都不會超過(-10000.0, +10000.0)區間(比如我們常見的圖形輸出裝置都有大小的限制),我們就可以將問題域簡化為(-10000.0, +10000.0)區間內的一小塊區域,對於這塊區域來說,>= 10000.0就意味著無窮遠。你肯定已經明白了,數學模型經過簡化後,演算法中提到的射線就可以理解為從模型邊界到內部點p之間的線段,前面討論的關於線 段的演算法就可以使用了。

射線法的基本原理是判斷由p點發出的射線與多邊形的交點個數,交點個數是奇數表示p點在多邊形內(在多邊形的邊上也視為在多邊形內部的特殊情 況),正常情況下經過點p的射線應該如圖6(a)所示那樣,但是也可能碰到多種非正常情況,比如剛好經過多邊形乙個定點的情況,如圖6 (b),這會被誤認為和兩條邊都有交點,還可能與某一條邊共線如圖6 (c)和(d),共線就有無窮多的交點,導致判斷規則失效。還要考慮凹多邊形的情況,如圖6(e)。

圖6 射線法可能遇到的各種交點情況

針對這些特殊情況,在對多邊形的每條邊進行判斷時,要考慮以下這些特殊情況,假設當前處理的邊是p1p2,則有以下原則:

1)如果點p在邊p1p2上,則直接判定點p在多邊形內;

2)如果從p發出的射線正好穿過p1或者p2,那麼這個交點會被算作2次(因為在處理以p1或p2為端點的其它邊時可能已經計算過這個點了),對這種情況的處理原則是:如果p的y座標與p1、p2中較小的y座標相同,則忽略這個交點;

3)如果從p發出的射線與p1p2平行,則忽略這條邊;

對於第三個原則,需要判斷兩條直線是否平行,通常的方法是計算兩條直線的斜率,但是本演算法因為只涉及到直線段(射線也被模型簡化為長線段了),就簡化了 很多,判斷直線是否水平,只要比較一下線段起始點的y座標是否相等就行了,而判斷直線是否垂直,也只要比較一下線段起始點的x座標是否相等就行了。

應用以上原則後,掃瞄線法判斷點是否在多邊形內的演算法流程就完整了,圖7就是演算法的流程圖:

最終掃瞄線法判斷點是否在多邊形內的演算法實現如下:

228 bool ispointinpolygon(const polygon& py, const point& pt)   

229

242

243 if(!pp.ishorizontal())

244

249 else if((issamefloatvalue(pp.pe.y, pt.y)) && (pp.pe.y > pp.ps.y))

250

253 else

254

259 }

260 }

261 }

262

263 return ((count % 2) == 1);

264 }

在圖形學領域實施的真正工程**,通常還會增加乙個多邊形的外包矩形快速判斷,對點根本就不在多邊形周圍的情況做快速排除, 提高演算法效率。這又涉及到求多邊形外包矩形的演算法,這個演算法也很簡單,就是遍歷多邊形的所有節點,找出各個座標方向上的最大最小值。以下就是求多邊形外包 矩形的演算法:

266 void getpolygonenveloprect(const polygon& py, rect& rc)   

267

285

286 rc = rect(minx, miny, maxx, maxy);

287 }

除了掃瞄線法,還可以通過多邊形邊的法向量方向、多邊形面積以及角度和等方法判斷點與多邊形的關係。但是這些演算法要麼只支援 凸多邊形,要麼需要複雜的三角函式運算(多邊形邊數小於44時,可採用近似公式計算夾角和,避免三角函式運算),使用的範圍有限,只有掃瞄線法被廣泛應 用。

判斷點在多邊形內演算法(射線法)

謝謝分享!點和多邊形關係的演算法實現 好了,現在我們已經了解了向量叉積的意義,以及判斷直線段是否有交點的演算法,現在回過頭看看文章開始部分的討論的問題 如何判斷乙個點是否在多邊形內部?根據射線法的描述,其核心是求解從p點發出的射線與多邊形的邊是否有交點。注意,這裡說的是射線,而我們前面討論的都是線段...

判斷點在多邊形內部

微博 文中所指的多邊形均為凸多邊形,一些描述可能有誤,歡迎指正。在開始之前,我們需要先構建好測試環境。我構建了乙個比較特殊的多邊形,如下。從最上面的頂點順時針座標 螢幕座標系 分別為 40,10 60,30 60,50 20,50 20,30 根據對多邊形的了解,我們可以得出如下結論 如果乙個點在多...

判斷點在多邊形內部

用的是射線法,我的 取的是向右的射線 這題沒有點在邊上的情況,但是還是要考慮很多 比如射線覆蓋邊,射線交短點的情況,為了區分各種狀況 我分成了6中相交情況 唉 有點多了 不過比較清晰 不知道別人是怎麼做的 include struct edge struct point 儲存邊 edge e 105...