BZOJ1069 [SCOI2007]最大土地面积

数据范围2000,我们如果枚举对角线然后走呢,是不是n^3呢,仔细一想不是。

因为面积是一个单增的过程,所以建完凸包以后枚举对角线复杂度就是n^2的。

因此这题我们就从一个四边形面积转化为两个三角形面积。

By:大奕哥

 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 typedef double db;
 4 const int inf=1e9;
 5 const int N=2005;
 6 struct node
 7 {
 8     db x,y;
 9     
10 }a[N],p0,s[N];
11 int n,top;
12 bool cmp(node a,node b){
13     db A=atan2(a.y-p0.y,a.x-p0.x);
14     db B=atan2(b.y-p0.y,b.x-p0.x);
15     if(A==B)return a.x<b.x;
16     return A<B;
17 };
18 db mul(node a,node b)
19 {
20     return a.x*b.y-b.x*a.y;
21 }
22 db calcs(node a,node b,node z)
23 {
24     node c;c.x=a.x-z.x;c.y=a.y-z.y;
25     node d;d.x=b.x-z.x;d.y=b.y-z.y;
26     return mul(c,d);
27 }
28 db solve()
29 {
30     s[top+1]=s[1];
31     db ans=0;
32     for(int i=1;i<=top;++i)
33     {
34         int p1=i%top+1,p2=(i+2)%top+1;
35         for(int j=i+2;j<=top;++j)
36         {
37             while(fabs(calcs(s[p1],s[i],s[j]))<fabs(calcs(s[p1+1],s[i],s[j])))
38             {
39                 p1=p1%top+1;
40             }
41             while(fabs(calcs(s[p2],s[i],s[j]))<fabs(calcs(s[p2+1],s[i],s[j])))
42             {
43                 p2=p2%top+1;
44             }
45             ans=max(ans,fabs(calcs(s[p2],s[i],s[j]))+fabs(calcs(s[p1],s[i],s[j])));
46         }
47     }
48     return ans;
49 }
50 int main()
51 {
52     scanf("%d",&n);
53     int pos=0;a[0].x=a[0].y=inf;
54     for(int i=1;i<=n;++i)
55     {
56         scanf("%lf%lf",&a[i].x,&a[i].y);
57         if(a[pos].y>a[i].y||(a[pos].y==a[i].y&&a[pos].x>a[i].x))pos=i;
58     }
59     swap(a[pos],a[1]);p0=a[1];
60     sort(a+2,a+1+n,cmp);
61     s[++top]=a[1];s[++top]=a[2];
62     for(int i=3;i<=n;++i)
63     {
64         while(top>1&&calcs(s[top],a[i],s[top-1])<=0)top--;
65         s[++top]=a[i];
66     }
67     printf("%.3lf",solve()/2);
68     return 0;
69 }

 

posted @ 2018-01-11 18:01  大奕哥&VANE  阅读(123)  评论(0编辑  收藏  举报