生活随笔
收集整理的這篇文章主要介紹了
1069: [SCOI2007]最大土地面积|旋转卡壳
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
旋轉卡殼就是先求出凸包。然后在凸包上枚舉四邊形的對角線兩側分別找面積最大的三角形
因為在兩側找面積最大的三角形的頂點是單調的所以復雜度就是n2
單調的這個性質能夠自行繪圖感受一下,似乎比較顯然
#include<algorithm>
#include<iostream>
#include<cstdlib>
#include<cstring>
#include<cstdio>
#include<vector>
#include<cmath>
#include<queue>
#include<set>
#include<map>
#define ll long long
#define N 2002
using namespace
std
struct W{double
x,
y
int n,top
W operator-(W a,W b)
{return (W){a
.x-b
.x,a
.y-b
.y}
}
double dis(W a,W b)
{return (a
.x-b
.x)*(a
.x-b
.x)+(a
.y-b
.y)*(a
.y-b
.y)
}
double operator*(W a,W b)
{return a
.x*b
.y-a
.y*b
.x
}
bool operator<(W c,W d)
{double t=(c-a[
1])*(d-a[
1])if(t==
0)return dis(c,a[
1])<dis(d,a[
1])return t<
0
}
void Graham()
{int k=
1for(int i=
2if(a[k]
.y>a[i]
.y||(a[k]
.y==a[k]
.y&&a[k]
.x>a[i]
.x))k=i
swap(a[k],a[
1])
st[++top]=a[
1],
st[++top]=a[
2]for(int i=
3{while(top>
1&&(a[i]-
st[top-
1])*(
st[top]-
st[top-
1])<=
0)top--
st[++top]=a[i]}
}
double Rotating_caliper()
{double mx=
0int a,bfor(int
x=
1{a=
x%top+
1,b=(
x+
2)%top+
1for(int
y=
x+
2{while(a%top+
1!=
y&&(
st[
y]-
st[
x])*(
st[a+
1]-
st[
x])>(
st[
y]-
st[
x])*(
st[a]-
st[
x]))a=a%top+
1while(b%top+
1!=
x&&(
st[b+
1]-
st[
x])*(
st[
y]-
st[
x])>(
st[b]-
st[
x])*(
st[
y]-
st[
x]))b=b%top+
1mx=max(mx,(
st[
y]-
st[
x])*(
st[a]-
st[
x])+(
st[b]-
st[
x])*(
st[
y]-
st[
x]))}}return mx
}
int main()
{scanf(
"%d",&n)for(int i=
1scanf(
"%lf%lf",&a[i]
.x,&a[i]
.y)Graham()printf(
"%.3lf",Rotating_caliper()/
2)return
0
}
總結
以上是生活随笔為你收集整理的1069: [SCOI2007]最大土地面积|旋转卡壳的全部內容,希望文章能夠幫你解決所遇到的問題。
如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。