您的位置:首页 > 理论基础 > 计算机网络

bzoj1822: [JSOI2010]Frozen Nova 冷冻波网络流

2017-05-17 16:08 405 查看
思路比较显然:二分答案,流流流

但是实现的时候感觉自己数学捉急。。

一开始算了个直线到点距离。。。。

应该是线段到点距离

1 #include <bits/stdc++.h>
2 #define sqr(x) ((x)*(x))
3 #define MAXN 50000
4 #define TO (n+m+2)
5 #define FROM (n+m+1)
6 #define PO (n+m+2)
7 #define INF 2000000000
8 #define mid (l+r>>1)
9 using namespace std;
10 int n,m,k,LI=2,ans;
11 int to[MAXN],w[MAXN],nex[MAXN],fir[MAXN];
12 int h[MAXN],qq[MAXN],flo[MAXN],id[MAXN];
13 int ti[MAXN],x[MAXN],y[MAXN],X[MAXN],Y[MAXN],r[MAXN],p[MAXN],q[MAXN],R[MAXN];
14 void add(int p,int q,int o)
15 {
16     to[LI]=q;w[LI]=o;nex[LI]=fir[p];fir[p]=LI;LI++;
17     to[LI]=p;w[LI]=0;nex[LI]=fir[q];fir[q]=LI;LI++;
18 }
19 bool bfs()//计算层次图
20 {
21     int head=-1,tail=0;
22     for(int i=0;i<=PO;i++) h[i]=-1;
23     qq[0]=FROM;h[FROM]=0;// h[i]:点i的层数
24     while(head!=tail)
25     {
26         int x=qq[++head];
27         for(int i=fir[x];i;i=nex[i])
28             if(flo[i]&&h[to[i]]==-1)
29             {
30                 h[to[i]]=h[x]+1;
31                 qq[++tail]=to[i];
32             }
33     }
34     return h[TO]!=-1;
35 }
36 int dfs(int x,int f)//增广路:到点x最大容量为 f
37 {
38     if(x==TO)return f;
39     int w,used=0;
40     for(int i=fir[x];i;i=nex[i])
41         if(h[to[i]]==h[x]+1)
42         {
43             w=dfs(to[i],min(flo[i],f-used));
44             flo[i]-=w; flo[i^1]+=w;
45             used+=w;if(used==f)return f;
46         }
47     if(!used)h[x]=-1;
48     return used;
49 }
50 int dinic() //%usqwedf
51 {
52     int ans=0;
53     while(bfs())
54         ans+=dfs(FROM,1e9);
55     return ans;
56 }
57 bool ok(int time)
58 {
59     for(int i=1;i<=n;i++)
60         w[id[i]]=time/ti[i]+1;
61     for(int i=0;i<LI;i++)
62         flo[i]=w[i];
63     return(dinic()==m);
64 }
65 int main()
66 {
67 //    freopen("1.in","r",stdin);
68     scanf("%d%d%d",&n,&m,&k);
69     for(int i=1;i<=n;i++)
70         scanf("%d%d%d%d",&x[i],&y[i],&r[i],&ti[i]);
71     for(int i=1;i<=m;i++)
72         scanf("%d%d",&X[i],&Y[i]);
73     for(int i=1;i<=k;i++)
74         scanf("%d%d%d",&p[i],&q[i],&R[i]);
75     for(int i=1;i<=n;i++)
76         for(int j=1;j<=m;j++)
77         {
78             bool flag=sqr(x[i]-X[j])+sqr(y[i]-Y[j])<=sqr(r[i]);
79             if(!flag) continue;
80             long long a=y[i]-Y[j],b=X[j]-x[i],c=x[i]*Y[j]-y[i]*X[j];
81             for(int o=1;o<=k;o++)
82                 if(sqr(a*p[o]+b*q[o]+c)<=sqr(R[o])*(sqr(a)+sqr(b)) && (sqr(x[i]-p[o])+sqr(y[i]-q[o])<=sqr(R[o]) || sqr(X[j]-p[o])+sqr(Y[j]-q[o])<=sqr(R[o])))
83                 {
84                     flag=0;
85                     break;
86                 }
87             if(flag)
88                 add(i,j+n,1);
89         }
90     for(int i=1;i<=m;i++)
91         add(i+n,TO,1);
92     for(int i=1;i<=n;i++)
93         id[i]=LI,add(FROM,i,0);
94     int l,r;
95     for(l=0,r=4000000;l<r;)
96     if(ok(mid)) r=mid;else l=mid+1;
97     if(ok(l))
98         printf("%d\n",l);
99     else
100         puts("-1");
101     return 0;
102 }
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: