最小圓覆蓋學習筆記

2022-05-05 20:39:08 字數 1921 閱讀 1201

最小圓覆蓋是什麼,顧名思義:給出n個點,讓你畫乙個最小的包含所有點的圓,要求出圓的半徑,及圓心的座標。

三點定圓大家都知道吧,唯一要求是三點不共線。

求最小圓,就要列舉這些點,去確定圓。

對於可(du)敬(liu)的出題人,他可不想讓你這麼簡單的做完這個題。

這時,我們就要用到隨機增量法。

用這個東西:random_shuffle(a+1,a+n+1);把出題人善意給你的資料順序打亂。

(你要問為什麼?一會兒會解決吧)

下面我們可以開始求了。三點定圓,當然要三層迴圈,列舉三個點。

對於第乙個點,我們讓其為圓心。對於第二點我們和第乙個點連線,取其中點為圓心.連線為直徑,對於第三個點,我們進行三點定圓.

來了第四個點,我們判斷其是否在圓中,如果在圓中,我們繼續判斷,如果不在圓中,我們取一二個點,和第四個點進行三點定圓.

因為第四個點不在前三個點的圓中.所以第四個點定的新圓一定比前三個定的圓大.

顯然,第三個點的時間複雜度是o(n)的,表面上時間複雜的是o(n^3)

的,實際上在第一次執行完最內層迴圈.已經確定了乙個圓。再執行外邊的兩層迴圈,就會涉及到概率.

均攤時間複雜度o(n),具體我也不會證.

cq(i,2,n)}}

}}

}

前提是三點不共線。

我們設三個點為\((x_1,y_1)\),\((x_2,y_2)\),\((x_3,y_3)\)帶入到方程裡

\[\begin

(x_1−x_0)^2+(y_1−y_0)^2=r^2\\

(x_2−x_0)^2+(y_2−y_0)^2=r^2\\

(x_3−x_0)^2+(y_3−y_0)^2=r^2\\

\end

\]公式(1)(2)相減,(1)(3)相減之後經過化簡可以得到:

\((x_1−x_2)x_0+(y_1−y_2)y_0=\frac\)

\((x_1−x_3)x_0+(y_1−y_3)y_0=\frac\)

上面的式子太複雜,換乙個好看一點的。

設\(a=x_1−x_2\)

\(b=y_1−y_2\)

\(c=x_1−x_3\)

\(d=y_1−y_3\)

\(e=\frac\)

\(f=\frac\)

那麼 解得

de−bf

\(x_0=\frac\)

\(y_0=\frac\)

有了 x_0 和 y_0 的值後,帶入(1) 式就可以得到 r的值。至此,三點確定圓的問題就解決了。

沒了**如下

void tt(point p1,point p2,point p3)
完整**

#include#include#include#include#define cq(i,s,n) for(int i=s;i<=n;i++)

using namespace std;

const double eps=1e-12;

struct pointa[500005];

point o;

int n;

double ri;

double dis(point a,point b)

void tt(point p1,point p2,point p3)

int main()

random_shuffle(a+1,a+n+1);

o=a[1];ri=0;

cq(i,2,n)}}

}}

}printf("%.10lf\n%.10lf %.10lf",ri,o.x,o.y);

return 0;

}

\(}\)(話說可以算成雙倍經驗)

p2533 [ahoi2012]訊號塔

p1742 最小圓覆蓋

最小圓覆蓋

最小圓覆蓋。神奇的隨機演算法。當點以隨機的順序加入時期望複雜度是線性的。algorithm a 令ci表示為前i個點的最小覆蓋圓。當加入新點pi時如果pi不在ci 1裡那麼pi必定在ci的邊界上。b 再從新考慮這樣乙個問題,ci為前i個點最小覆蓋圓且p在ci的的邊界上!同理加入新點pi時如果p i不...

最小圓覆蓋

最小圓覆蓋問題 在乙個平面上,給出 n 個點,求包圍這些點的最小圓,輸出圓心及半徑。分析雖然可以用模擬退火或者三分套三分,這裡只講隨機增量法,隨機增量法是一種確定性演算法,隨機意義下均攤複雜度 o n 而且可以達到很高的精度 可達到 10 10 量級 有事實 如果點 p 不在集合 s 的最小圓覆蓋內...

最小圓覆蓋

本來不想學的 於是今天就碰到一道大裸題 例題 bzoj2823 求最小圓覆蓋n個點。偽 如下 把所有點隨機化,設為 x 1 y 1 x n y n 開始把圓心設為x 1 半徑設為0 for i 2ton 如果i號點在當前圓內則跳過 那麼i號點就在圓周上 把1號點和i號點作為直徑作乙個圓 for j ...