返回列表 上一主題 發帖

[發問] 落點問題....(我目前從未到過的領域)

[發問] 落點問題....(我目前從未到過的領域)

本帖最後由 ui123 於 2013-11-11 19:48 編輯

今天我跟同事2人在吃飯時,同事跟我討論了下面的問題:


---------------------------------------------------------------------------------------

我同事說:主管最近出了個超難題給她,題目如附件,然後就丟了很多data請她分類

                   大概1000筆左右(X,y軸點......"更恐怖的事" 是不一定是整數,還有小數點的)

她說,她很笨,只會一筆一筆對在哪一個區域,就這樣一直對下去......然後我也幫她對了很久

我只會正方形區域然後用if ....但這似乎行不通~今天加了一點班後終於完成了  ^^~開心

---------------------------------------------------------------------------------------


目前也只能這樣~

如果大家遇到跟我一樣的狀況會怎麼樣呢?

附件如下:
落點問題.rar (9.35 KB)

A、C區給的座標點為封閉線段,比較容易處理
B區感覺也是四邊形好像在A、C區下方,座標點不是封閉線段需要補點或額外處理
B區的描述可否另行補點(座標)處理

原則上四邊封閉區域可以用中心與檢查點連一直線,檢查與四邊線是否相交,全部沒有相交就是在裡面,與任一線相交表示在外面。

等我明天回來再詳細研究
{...} 表示需要用 CTRL+SHIFT+ENTER 三鍵輸入公式

TOP

回復 1# ui123
B區補完(6,6),(5,5)形成凹多邊形
判斷的演算法可以參考 http://www.csie.ntnu.edu.tw/~u91029/Polygon.html
裡面 判斷一個點是否在簡單多邊形內部裡面 這一段

TOP

回復 3# stillfish00
stillfish00 大  ~有看到你附的網站,謝謝!  好多奇奇怪怪的圖~(@[]@!!)
如果這個例子(附件中在M,N欄的座標)要用VBA寫成是不是會非常非常的複雜?
我看他的函數看起來不是VBA的函數寫成的?  非常陌生, VBA的函數有這些功能?!
落點問題_判斷例子.rar (10.27 KB)

TOP

回復 2# ML089
ML089大~
B區的描述可否另行補點(座標)處理?   可以的,這樣也比較合理,且ABC區無交集
也就是說,如果剛好在重疊的線上,取較小那一個(A<B<C),例如,剛好在A區及B區交接線上,算A區的
下面有另附例子,stillfish00 大說的好難,這種問題用"VBA函數"可以寫的出來嗎?!
網路上我找不到VBA寫的例子~
只是我也很好奇VBA是否能解決此類問題,這種問題感覺很簡單,但似乎超難判斷的!~
大家可以想一想,謝謝!

TOP

本帖最後由 stillfish00 於 2013-11-13 00:27 編輯

回復 4# ui123
他是C/C++寫的,改成VBA大約如下
  1. Function pointInPoly(ptx As Double, pty As Double, arPoly) As Boolean
  2.     Dim i As Long, j As Long
  3.     Dim pix As Double, piy As Double
  4.     Dim pjx As Double, pjy As Double
  5.    
  6.     For i = 1 To UBound(arPoly) - 1
  7.         j = i + 1
  8.         pix = arPoly(i, 1): piy = arPoly(i, 2)
  9.         pjx = arPoly(j, 1): pjy = arPoly(j, 2)
  10.         
  11.         '不包含點在多邊形線上
  12.         If Not (piy > pty) = (pjy > pty) Then
  13.             If ptx < (pjx - pix) * (pty - piy) / (pjy - piy) + pix Then pointInPoly = Not pointInPoly
  14.         End If
  15.     Next
  16. End Function
複製代碼
利用他寫一個自訂函數RegionABC
  1. Function RegionABC(x As Double, y As Double, RegionA As Range, RegionB As Range, RegionC As Range) As String
  2.     '不包含點在ABC邊緣
  3.     If pointInPoly(x, y, RegionA.Value) Then RegionABC = "A": Exit Function
  4.     If pointInPoly(x, y, RegionB.Value) Then RegionABC = "B": Exit Function
  5.     If pointInPoly(x, y, RegionC.Value) Then RegionABC = "C": Exit Function
  6.     RegionABC = "不在ABC"
  7. End Function
複製代碼
先補齊B區的點,
使用,例如在O4公式打上  "=RegionABC(M4,N4,$C$4:$D$8,$C$10:$D$16,$C$18:$D$22)"

TOP

回復 3# stillfish00


  stillfish00大提供的資料很完整,謝謝你提供那麼完整的網頁資訊。
{...} 表示需要用 CTRL+SHIFT+ENTER 三鍵輸入公式

TOP

回復 6# stillfish00


    鼓勵一下,C語言改為VBA,剛好可以參考,謝謝
{...} 表示需要用 CTRL+SHIFT+ENTER 三鍵輸入公式

TOP

回復 5# ui123

stillfish00 大的功力高強,使用自訂函數應該最好的方式

網頁中所述的方法比我講的考慮方法還要正確

判斷一個點是否在簡單多邊形內部
從給定點開始,往隨便一個方向(實作時習慣水平往右)射出一條無限長射線,看看穿過多少條邊。如果穿過偶數次,表示點在簡單多邊形外部;如果穿過奇數次,表示點在簡單多邊形內部。
要小心處理射線穿過頂點、射線與邊重疊的情況。也要小心處理點在多邊形邊界上的情況。
時間複雜度為 O(N) , N 為簡單多邊形的頂點數目。

我再來研究可否用公式決解,但會比VBA看起來更複雜。
{...} 表示需要用 CTRL+SHIFT+ENTER 三鍵輸入公式

TOP

回復 6# stillfish00

不好意思,借該版資料

stillfish00大:
可否請你再幫忙寫 A、B、C等區域面積的自訂函數,感恩。
{...} 表示需要用 CTRL+SHIFT+ENTER 三鍵輸入公式

TOP

        靜思自在 : 欣賞別人就是莊嚴自己。
返回列表 上一主題