CF190 DIV1 B Ciel and Duel 最大費用流

來源:互聯網
上載者:User

這場CF竟然掛0了好開心!

這題的費用流解法真是……

分兩種情況討論,一種是Ciel選擇中間結束,另一種是全部打完

【我一開始總想把兩種情況一起解決QAQ】

第一種情況的話,左邊是Ciel,右邊是Jiro,源點連左邊流量1費用0,右邊連匯點流量1費用0,對於Jiro的每一張ATK,如果Ciel的卡>=Jiro的卡則連邊,流量1費用C-J,跑最大費用流直到某一次的增廣路的費用為負數時結束。

對於第二種情況,首先Ciel的卡數要大於Jiro的卡數,左邊是Ciel,右邊是Jiro,源點連左邊流量1費用0,右邊連匯點流量1費用0,對於Jiro的每一張ATK,如果Ciel的卡>=Jiro的卡則連邊,流量1費用C-J,對於Jiro的每一張DEF,如果Ciel的卡>Jiro的卡則連邊,流量1費用0,然後多拉出一個點EX,左邊的點連EX流量1費用為這張卡的strength,EX連匯點流量為Ciel的卡數 - Jiro的卡數,費用為0,跑最大費用流,必須滿流這種情況才成立。

輸出兩種方法的最大值。

#include<cstdio>#include<cstdlib>#include<cstring>#include<cmath>#include<iostream>#include<algorithm>#include<string>#include<map>#include<set>#include<queue>#include<stack>#include<ctime>#include<vector>#include<utility>using namespace std;#define N 1010#define M 1000010#define INF (1<<30)int n,m,s,t,ans;int head[N],d[N],pre[N],cnt;bool vis[N];struct edge{int v,w,c,next;}e[M];void addedge(int u,int v,int w,int c){e[cnt]=(edge){v,w,c,head[u]}; head[u]=cnt++;e[cnt]=(edge){u,0,-c,head[v]}; head[v]=cnt++;}int spfa(){queue<int> q;memset(pre,-1,sizeof(pre));for(int i=0;i<N;++i) d[i]=-INF;d[s]=0;q.push(s);while (! q.empty()){int u=q.front();q.pop();vis[u]=0;for(int i=head[u];i!=-1;i=e[i].next)if(e[i].w)if(d[e[i].v]<d[u]+e[i].c){d[e[i].v]=d[u]+e[i].c;pre[e[i].v]=i;if(! vis[e[i].v]) q.push(e[i].v),vis[e[i].v]=1;}}return d[t]!=-INF;}int flow;void mcmf1(){ans=flow=0;while (spfa()){int u,mn=INF;for(u=t;u!=s;u=e[pre[u]^1].v)mn=min(mn,e[pre[u]].w);if(d[t]<0) break;flow+=mn;ans+=mn*d[t];for(u=t;u!=s;u=e[pre[u]^1].v)e[pre[u]].w-=mn,e[pre[u]^1].w+=mn;}}void mcmf2(){ans=flow=0;while (spfa()){int u,mn=INF;for(u=t;u!=s;u=e[pre[u]^1].v)mn=min(mn,e[pre[u]].w);flow+=mn;ans+=mn*d[t];for(u=t;u!=s;u=e[pre[u]^1].v)e[pre[u]].w-=mn,e[pre[u]^1].w+=mn;}}int n1,n2,ans1;char ss[N][6];int J[N],C[N];int main (){freopen("1.in","r",stdin);scanf("%d%d",&n1,&n2);for(int i=1;i<=n1;++i) scanf("%s %d",ss[i],&J[i]);for(int i=1;i<=n2;++i) scanf("%d",&C[i]);n=n1+n2;s=n+1;t=s+1;cnt=0;memset(head,-1,sizeof(head));for(int i=1;i<=n1;++i)addedge(n2+i,t,1,0);for(int i=1;i<=n2;++i){addedge(s,i,1,0);for(int j=1;j<=n1;++j)if(strcmp(ss[j],"ATK")==0 && C[i]>=J[j]) addedge(i,j+n2,1,C[i]-J[j]);}mcmf1();ans1=ans;if(n2<=n1){printf("%d\n",ans1);return 0;}cnt=0;memset(head,-1,sizeof(head));int ex=t+1;addedge(ex,t,n2-n1,0);for(int i=1;i<=n1;++i)addedge(n2+i,t,1,0);for(int i=1;i<=n2;++i){addedge(s,i,1,0);addedge(i,ex,1,C[i]);for(int j=1;j<=n1;++j){if(strcmp(ss[j],"ATK")==0){if(C[i]>=J[j]) addedge(i,j+n2,1,C[i]-J[j]);}else{if(C[i]>J[j]) addedge(i,j+n2,1,0);}}}mcmf2();if(flow==n2) printf("%d\n",max(ans,ans1));else printf("%d\n",ans1);return 0;}

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.