學習小記 半平面交 排序增量法

2022-08-04 18:03:21 字數 1457 閱讀 9766

之前的半平面交的演算法是基於分治和凸包合併的,分治兩邊,計算出半平面交,再合併凸包。

而這種排序增量法好寫簡潔常數小,適合在比賽中使用。

為了避免半平面交區域無界的情況,我們在無窮遠處四個方向加上四個半平面的限制。

可以看出,有限的半平面交是乙個凸包

方便起見,我們用點+向量的形式來表示乙個半平面,向量的左手向就是半平面的方向。

定義半平面的極角為向量的極角,我們將半平面按照極角排序,對於極角相同的,我們只保留最靠裡,也就是限制最緊的那一條。

我們維護乙個佇列,像做凸殼一樣的從隊尾加入半平面,如果當前隊尾半平面邊界和隊尾前乙個的邊界交點在新的半平面之外,說明隊尾就沒用了,將隊尾彈掉。

但是半平面交既然是乙個凸包,它會繞一圈回來,如果只在隊尾加肯定是不對的。

彈完隊尾之後,我們再判斷隊頭的半平面是否也沒用了,判定方法類似,如果能的話還要將隊頭的半平面給彈掉。

這樣做完以後,我們發現最後隊尾會剩下一些半平面,雖然這些半平面是凸的,但是它們有可能會被隊頭給彈掉,此時還要再判一下,將一些隊尾彈掉。

分析複雜度,每乙個半平面最多隻會進隊出隊各一次,時間複雜度僅在於排序,為\(o(n\log n)\)

ps:盡量避免在排序過載compare函式的時候用atan2去比較,每次比較都要計算atan2是很慢的,我們可以提前計算好再比,或者用叉積+象限來比。

醜到極致了...

namespace geometry

}; node operator +(node x,node y)

node operator -(node x,node y)

node operator *(double x,node y)

double crs(node x,node y)

double ang(node x)

struct line

; line(node _p,node _v)

}; node dot(line x,line y)

bool inside(line x,node y)

bool in(line x,node y) }

using namespace geometry;

int t,n,n1,n2;

node a[n],ab[n];

line d[4*n],db[4*n];

struct px

while(l+2double s=0;//計算面積

fo(i,l,r-2) s+=crs(dot(d[dq[i]],d[dq[i+1]]),dot(d[dq[i+1]],d[dq[i+2]]));

s+=crs(dot(d[dq[r-1]],d[dq[r]]),dot(d[dq[r]],d[dq[l]]));

s+=crs(dot(d[dq[r]],d[dq[l]]),dot(d[dq[l]],d[dq[l+1]]));

return s/2;

}

半平面交學習小記

其實只是記乙個板子 lll 核心是多邊形內的乙個點集,點集內任意一點與多邊形邊上任意一點的連線都在多邊形內。你可以把多邊形想成乙個房間,在核心內任意乙個點放上乙個全方位360度無死角的攝像機,這個攝像機能夠看到房間的任意角落。現在給出乙個n邊形的所有頂點,求是否存在核 poj喜聞樂見地掛了,例題不知...

半平面交 學習筆記

這次講半平面交。應該是平面幾何基礎演算法的最後一節了 凸包,旋轉卡殼,半平面交 說幾句題外話,這些演算法都比較耐 keng 用 die 比如凸包好像可以用於來優化dp 好像是利用斜率 很多模型都可以用旋轉卡殼往上套,而半平面交 可以處理許多與平面幾何沒有半毛錢關係的題目,尤其是對於一些不等式組的解集...

半平面交 學習筆記

前置知識 向量的凸包應用 2.半平面交的基本概念 二 半平面交的性質 半平面是立體幾何的基本概念之一。一條直線將平面分為兩部分,其中的每一部分均稱為半平面。例如,若a是平面 上的一條直線,則將 上不屬於a的點按以下性質分為兩個集合 鏈結同乙個集合的兩點的線段不與a相交,鏈結不同集合的兩點的線段必與a...