bzoj4950(二分图最大匹配)
生活随笔
收集整理的這篇文章主要介紹了
bzoj4950(二分图最大匹配)
小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.
[Wf2017]Mission Improbable
Time Limit:?1 Sec??Memory Limit:?1024 MBSubmit:?105??Solved:?49
[Submit][Status][Discuss]
Description
那是春日里一個天氣晴朗的好日子,你準備去見見你的老朋友Patrick,也是你之前的犯罪同伙。Patrick在編程競賽 上豪賭輸?shù)袅艘淮蠊P錢,所以他需要再干一票。為此他需要你的幫助,雖然你已經(jīng)金盆洗手了。你剛開始很不情愿, 因為你一點也不想再回到那條老路上了,但是你覺得聽一下他的計劃也無傷大雅。在附近的一個倉庫里有一批貨物, 包含一些貴重的消費性部件,Patrick企圖從中盡可能多地偷些東西出來。這意味著要找一條進去的路,弄暈安保人 員,穿過各種各樣的激光射線,你懂的,都是常見的搶劫技術(shù)。然而,倉庫的核心裝備了一套Patrick搞不定的安保系 統(tǒng)。這也是他需要你幫助他的地方。這批貨物被放置在一些巨大的立方體箱里,每個箱子的尺寸都是相同的。這些 箱子堆放成許多整齊的堆,每個箱子可以表示成一個三維的網(wǎng)格。安保系統(tǒng)每個小時會用三臺相機對這堆貨物進行 一次拍照,相機分別為:前置相機(front camera),側(cè)置相機(side camera)和頂置相機(top camera)。前置相機的照 片顯示了每一行最高的那堆箱子的高度,側(cè)置相機顯示了每一列最高的那堆箱子的高度,頂置相機顯示了每個位置是 否存在一堆箱子。如果安保系統(tǒng)發(fā)現(xiàn)任何一張照片出現(xiàn)了變化,它會立即拉響警報。一旦 Patrick 進去了,他會確 定每堆箱子的高度并且發(fā)給你。圖1顯示了一種網(wǎng)格可能的放置,以及每臺相機會得到的視圖。 圖 1. 網(wǎng)格的高度值與對應(yīng)的相機視圖。 圖 2. 洗劫后網(wǎng)格可能的高度值。 Patrick想盡可能多偷走一些箱子。由于他不能弄壞安保系統(tǒng),他準備重新安排剩余每堆箱子的放置,使得下一次相 機取像時會得到相同的照片,從而騙過安保系統(tǒng)。在上面的例子中,他可以偷走九個箱子。圖2顯示了一種可能的剩 余箱子的安置方案能使得安保系統(tǒng)認為與原安置情況相同。Patrick想請你幫他確定在保證能騙過安保系統(tǒng)的情況 下他最多能偷走多少個箱子。你會幫他干完這最后一票么?Input
第一行包含兩個整數(shù)r(1≤r≤100)和c(1≤n≤100),分別表示網(wǎng)格的行數(shù)與列數(shù)。 接下來r行,每行包含c個整數(shù),表示對應(yīng)行上每堆立方體箱的高度(箱子的數(shù)量)。 所有的高度在0到10^9之間 (含邊界) 。Output
輸出在不被發(fā)現(xiàn)的情況下最多能偷走多少箱子。Sample Input
樣例15 5
1 4 0 5 2
2 1 2 0 1
0 2 3 4 4
0 3 0 3 1
1 2 2 1 1
樣例2
2 3
50 20 3
20 10 3
Sample Output
樣例19
樣例2
30 題解: 這道題應(yīng)該如何去想,側(cè)面的,前面的相機,就是行和列的最大值,而上面的相機,只會是判斷該點有無, 行的最大值有可能是列的最大值,那么就可以偷更多的箱子,所以如果該點是行列的最大值,就連一條邊, 然后就ok了。 1 #include<iostream> 2 #include<cstdio> 3 #include<cstring> 4 #include<cmath> 5 #include<algorithm> 6 #define MAXN 100000+10 7 using namespace std; 8 typedef long long LL; 9 struct ed{LL v,next;}edge[MAXN]; 10 LL match[220],head[220],vis[220],n,m; 11 LL map[220][220],sum=0,mh[220],ml[220]; 12 void add(LL u,LL v){ 13 static LL tot=0; 14 edge[++tot].v=v; 15 edge[tot].next=head[u]; 16 head[u]=tot; 17 } 18 bool dfs(LL u){ 19 for(LL i=head[u];i;i=edge[i].next){ 20 LL v=edge[i].v; 21 if(vis[v])continue; 22 vis[v]=1; 23 if(!match[v]||dfs(match[v])){ 24 match[v]=u; 25 return true; 26 } 27 } 28 return false; 29 } 30 int main(){ 31 scanf("%lld%lld",&n,&m); 32 for(LL i=1;i<=n;i++) 33 for(LL j=1;j<=m;j++){ 34 scanf("%lld",&map[i][j]); 35 mh[i]=max(mh[i],map[i][j]); 36 ml[j]=max(ml[j],map[i][j]); 37 if(map[i][j])sum+=map[i][j]-1; 38 } 39 for(LL i=1;i<=n;i++) 40 for(LL j=1;j<=m;j++) 41 if(mh[i]&&map[i][j]&&mh[i]==ml[j])add(i,n+j); 42 for(LL i=1;i<=n;i++)if(mh[i])sum-=mh[i]-1; 43 for(LL i=1;i<=m;i++)if(ml[i])sum-=ml[i]-1; 44 for(LL i=1;i<=n;i++){ 45 memset(vis,0,sizeof(vis)); 46 if(mh[i]&&dfs(i))sum+=mh[i]-1; 47 } 48 printf("%lld",sum); 49 return 0; 50 }
?
轉(zhuǎn)載于:https://www.cnblogs.com/fengzhiyuan/p/7717503.html
總結(jié)
以上是生活随笔為你收集整理的bzoj4950(二分图最大匹配)的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Fragment滑动切换简单案例
- 下一篇: 【CodeVS】1083 Cantor表