bzoj4823: [Cqoi2017]老C的方块(最小割)

4823: [Cqoi2017]老C的方块

题目:传送门



题解:

   毒瘤题ORZ....

   太菜了看出来是最小割啥边都不会建...狂%大佬强强强

   

    黑白染色?不!是四个色一起染,四层图跑最小割。。。

   很惊奇的发现染完色之后只要是不喜欢的图形都一定可以由黄-->黑-->红-->绿 组成

   那就很nice啦...兴高采烈的去敲代码...结果10^5*10^5???搞毛线...太弱了ORZ,又看了一波大佬的操作,用map存!

   woc...不谈了不谈了...撸撸撸(分情况分到想屎...虽然不多)

   注意一下...黑到红连边的时候是不可以连inf的...然而我傻逼逼的打了...改成min(w[黑],w[红])...



代码:

  1 #include<cstdio>
  2 #include<cstring>
  3 #include<cstdlib>
  4 #include<cmath>
  5 #include<algorithm>
  6 #include<map>
  7 #define inf 999999999
  8 #define qread(x) x=read()
  9 using namespace std;
 10 typedef long long LL;
 11 inline LL read()
 12 {
 13     LL x=0,f=1;char ch;
 14     while(ch<‘0‘ || ch>‘9‘){if(ch==‘-‘)f=-1;ch=getchar();}
 15     while(ch>=‘0‘ && ch<=‘9‘){x=x*10+ch-‘0‘;ch=getchar();}
 16     return f*x;
 17 }
 18 struct node
 19 {
 20     int x,y,c,next,other;
 21 }a[1110000];int len,last[410000];
 22 int n,m,T,st,ed;
 23 void ins(int x,int y,int c)
 24 {
 25     int k1,k2;
 26     k1=++len;
 27     a[len].x=x;a[len].y=y;a[len].c=c;
 28     a[len].next=last[x];last[x]=len;
 29
 30     k2=++len;
 31     a[len].x=y;a[len].y=x;a[len].c=0;
 32     a[len].next=last[y];last[y]=len;
 33
 34     a[k1].other=k2;
 35     a[k2].other=k1;
 36 }
 37 int head,tail;
 38 int list[410000],h[410000];
 39 bool bt_h()
 40 {
 41     memset(h,0,sizeof(h));h[st]=1;
 42     list[1]=st;head=1;tail=2;
 43     while(head!=tail)
 44     {
 45         int x=list[head];
 46         for(int k=last[x];k;k=a[k].next)
 47         {
 48             int y=a[k].y;
 49             if(!h[y] && a[k].c)
 50             {
 51                 h[y]=h[x]+1;
 52                 list[tail++]=y;
 53             }
 54         }
 55         head++;
 56     }
 57     if(h[ed])return true;
 58     return false;
 59 }
 60 int find_flow(int x,int flow)
 61 {
 62     int s=0,t;
 63     if(x==ed)return flow;
 64     for(int k=last[x];k;k=a[k].next)
 65     {
 66         int y=a[k].y;
 67         if(h[y]==h[x]+1 && a[k].c && s<flow)
 68         {
 69             s+=t=find_flow(y,min(a[k].c,flow-s));
 70             a[k].c-=t;a[a[k].other].c+=t;
 71         }
 72     }
 73     if(!s)h[x]=0;
 74     return s;
 75 }
 76 int x[110000],y[110000],w[110000];//第x列,第y行,金币数
 77 map<pair<int,int>,int>id;
 78 int main()
 79 {
 80     len=0;memset(last,0,sizeof(last));
 81     memset(w,0,sizeof(w));
 82     qread(n);qread(m);qread(T);st=T+1;ed=st+1;
 83     for(int i=1;i<=T;i++){qread(x[i]);qread(y[i]);qread(w[i]);id[make_pair(x[i],y[i])]=i;}
 84     //黄-->黑-->红-->绿
 85     for(int i=1;i<=T;i++)
 86     {
 87         if(x[i]%4==0)//黑或黄
 88         {
 89             if(y[i]%2==1)ins(st,i,w[i]);//黄
 90             else//黑
 91             {
 92                 if(id[make_pair(x[i]+1,y[i])])ins(id[make_pair(x[i]+1,y[i])],i,inf);
 93                 if(id[make_pair(x[i],y[i]+1)])ins(id[make_pair(x[i],y[i]+1)],i,inf);
 94                 if(id[make_pair(x[i],y[i]-1)])ins(id[make_pair(x[i],y[i]-1)],i,inf);
 95             }
 96         }
 97         if(x[i]%4==1)//黑或黄
 98         {
 99             if(y[i]%2==0)ins(st,i,w[i]);//黄
100             else//黑
101             {
102                 //黑-->黄
103                 if(id[make_pair(x[i],y[i]-1)])ins(id[make_pair(x[i],y[i]-1)],i,inf);
104                 if(id[make_pair(x[i],y[i]+1)])ins(id[make_pair(x[i],y[i]+1)],i,inf);
105                 if(id[make_pair(x[i]-1,y[i])])ins(id[make_pair(x[i]-1,y[i])],i,inf);
106
107                 //黑-->红(计算w)
108                 if(id[make_pair(x[i]+1,y[i])])
109                     ins(i,id[make_pair(x[i]+1,y[i])],min(w[i],w[id[make_pair(x[i]+1,y[i])]]));
110             }
111         }
112         if(x[i]%4==2)//红或绿
113         {
114             if(y[i]%2==1)//红
115             {
116                 if(id[make_pair(x[i],y[i]-1)])ins(i,id[make_pair(x[i],y[i]-1)],inf);
117                 if(id[make_pair(x[i],y[i]+1)])ins(i,id[make_pair(x[i],y[i]+1)],inf);
118                 if(id[make_pair(x[i]+1,y[i])])ins(i,id[make_pair(x[i]+1,y[i])],inf);
119             }
120             else ins(i,ed,w[i]);//绿
121         }
122         if(x[i]%4==3)//红或绿
123         {
124             if(y[i]%2==0)//红
125             {
126                 //红-->绿
127                 if(id[make_pair(x[i],y[i]-1)])ins(i,id[make_pair(x[i],y[i]-1)],inf);
128                 if(id[make_pair(x[i],y[i]+1)])ins(i,id[make_pair(x[i],y[i]+1)],inf);
129                 if(id[make_pair(x[i]-1,y[i])])ins(i,id[make_pair(x[i]-1,y[i])],inf);
130
131                 //黑-->红
132                 if(id[make_pair(x[i]+1,y[i])])
133                     ins(id[make_pair(x[i]+1,y[i])],i,min(w[i],w[id[make_pair(x[i]+1,y[i])]]));
134             }
135             else ins(i,ed,w[i]);//绿
136         }
137     }
138     int ans=0;
139     while(bt_h())ans+=find_flow(st,inf);
140     printf("%d\n",ans);
141     return 0;
142 }

原文地址:https://www.cnblogs.com/CHerish_OI/p/8629703.html

时间: 2024-10-12 12:33:37

bzoj4823: [Cqoi2017]老C的方块(最小割)的相关文章

Bzoj4823 [Cqoi2017]老C的方块

没有题面,懒得手打 网络流 最小割 码农题(误) 一开始是冲着n<=5000的部分分写了网络流,结果神奇地发现似乎就是正解. 说好的dinic时间复杂度上界$O(V^2 E)$呢……网络流不愧是玄学算法. 放一张题目里的图 四种图案: 观察这四种图案和它们旋转/翻转以后的样子,可以发现一个共同点:每种图案都是由“中心一条蓝色边和它相邻的两个方块”,以及另外两个邻接的方块组成的 范围画出来就是这个样子: 可以发现“另外两个邻接的方块”肯定一个在蓝线左边一个在蓝线右边. 先说一种错误的想法: 将每个

[bzoj4823][洛谷P3756][Cqoi2017]老C的方块

Description 老 C 是个程序员. 作为一个懒惰的程序员,老 C 经常在电脑上玩方块游戏消磨时间.游戏被限定在一个由小方格排成的R行C列网格上 ,如果两个小方格有公共的边,就称它们是相邻的,而且有些相邻的小方格之间的公共边比较特殊.特殊的公共边排 列得有很强的规律.首先规定,第1行的前两个小方格之间的边是特殊边.然后,特殊边在水平方向上每4个小方格为 一个周期,在竖直方向上每2个小方格为一个周期.所有的奇数列与下一列之间都有特殊边,且所在行的编号从左到 右奇偶交替.下图所示是一个R =

BZOJ 4823: [Cqoi2017]老C的方块

分析: 我觉得我的网络流白学了...QAQ... 其实数据范围本是无法用网络流跑过去的,然而出题者想让他跑过去,也就跑过去了... 看到题目其实感觉很麻烦,不知道从哪里入手,那么仔细观察所给出的有用信息... 我们考虑网格图是一个含有挡板的图,这个挡板的分布很有规律,大概是每一行的相邻两个挡板都隔了四个格子,并且奇数行的排列相同,偶数行的排列相同... 然后考虑不合法的方块形状有什么共同点:仔细观察就会发现,所有的不合法图形中,挡板的左边至少有一个格子,右边至少有一个格子,并且左边的格子连着一个

【题解】CQOI2017老C的方块

网络流真的是一种神奇的算法.在一张图上面求感觉高度自动化的方案一般而言好像都是网络流的主阵地.讲真一开始看到这道题也有点懵,题面很长,感觉很难的样子.不过,仔细阅读了题意之后明白了:我们所要做的就是要用最小的代价,使得最后的图中不能出现给定的四种图案. 实际上之前做过一道非常毒瘤的网络流题目[无限之环].当时就思考了一下:为什么出题人规定不能旋转直线管子?原因就是因为这样的图建不出来,它与不具有其他的管子的特点.那么可以断定:给出的这四个图案必然也是非常特殊的图形,否则不会只有这四个/不会是这四

@loj - [email&#160;protected] 「CQOI2017」老 C 的方块

目录 @[email protected] @[email protected] @accepted [email protected] @[email protected] @[email protected] 老 C 是个程序员. 作为一个懒惰的程序员,老 C 经常在电脑上玩方块游戏消磨时间.游戏被限定在一个由小方格排成的 R 行 C 列网格上,如果两个小方格有公共的边,就称它们是相邻的,而且有些相邻的小方格之间的公共边比较特殊. 特殊的公共边排列得有很强的规律.首先规定,第 1 行的前两个

【CF331E】Biologist(网络流,最小割)

[CF331E]Biologist(网络流,最小割) 题面 洛谷 翻译: 有一个长度为\(n\)的\(01\)串,将第\(i\)个位置变为另外一个数字的代价是\(v_i\). 有\(m\)个要求 每个要求的形式是 首先确定若干位置都要是\(0\)或者\(1\) 然后给定这\(K\)个位置,如果些位置上都满足要求 那么就可以得到\(W_k\)元 某些要求如果失败了还要倒着给\(g\)元 问最终能够得到的最大利润 输入格式: 第一行是\(n,m,g\) 第二行是\(V_i\) 接下来\(m\)行 第

【BZOJ2039】【2009国家集训队】人员雇佣 [最小割]

人员雇佣 Time Limit: 20 Sec  Memory Limit: 259 MB[Submit][Status][Discuss] Description 作为一个富有经营头脑的富翁,小L决定从本国最优秀的经理中雇佣一些来经营自己的公司.这些经理相互之间合作有一个贡献指数,(我们用Ei,j表示i经理对j经理的了解程度),即当经理i和经理j同时被雇佣时,经理i会对经理j做出贡献,使得所赚得的利润增加Ei,j.当然,雇佣每一个经理都需要花费一定的金钱Ai,对于一些经理可能他做出的贡献不值得

hdoj 4289 Control 【拆点 求最小割】

Control Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 2295    Accepted Submission(s): 961 Problem Description You, the head of Department of Security, recently received a top-secret informati

There is a war (hdu 2435 最小割+枚举)

There is a war Time Limit: 5000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 970    Accepted Submission(s): 277 Problem Description There is a sea. There are N islands in the sea. There are some directional