bzoj2055 80人環遊世界(可行流)

2022-02-28 03:01:51 字數 1277 閱讀 7441

傳送門

表示完全看不懂最小費用可行流……

據某大佬說

我們考慮拆點,然後進行如下連邊

$s$向$a_i$連邊,權值$0$,容量$[0,m]$

$a_i$向$a_i'$連邊,權值$0$容量$[v_i,v_i]$

如果存在邊$(i,j)$,則連邊$a_i'->a_i$,權值為$w_$,容量$[0,m]$

$a_i'$向$t$連邊,權值$0$,容量$[0,m]$

$t$向$t'$連邊,權值$0$容量$[0,m]$

然後跑個最小費用可行流

1

//minamoto

2 #include3 #include4 #include5 #include6

#define inf 0x3f3f3f3f

7using

namespace

std;

8#define getc() (p1==p2&&(p2=(p1=buf)+fread(buf,1,1<<21,stdin),p1==p2)?eof:*p1++)

9char buf[1

<<21],*p1=buf,*p2=buf;

10 inline int

read()

20const

int n=505,m=500005;21

int head[n],next[m],ver[m],edge[m],flow[m],tot=1

;22 inline void add(int u,int v,int e,int

f)26

intdis[n],vis[n],cur[n],s,t,ans,s,t,kt,n,m;

27 queueq;

28bool

spfa()42}

43}44return ~dis[s];45}

46int dfs(int u,int

limit)57}

58 vis[u]=0;59

return

fl;60}61

void

zkw()

64int

main()

72 add(t,kt,0,m),add(kt,s,0

,inf);

73for(int i=1;i<=n;++i)

74for(int j=i+1;j<=n;++j)

78zkw();

79 printf("

%d\n

",ans);

80return0;

81 }

BZOJ2055 80人環遊世界

題解 總算a掉了,各種蛋疼。int main for1 i,n for2 j,i 1,n for1 i,n insert i n,t,0,inf,0 insert t,s,0,inf,0 mcf printf d n mincost return0 s是附加源,sss是真正的源,t是真正的匯。這樣構...

bzoj 2055 80人環遊世界

有源匯上下界最小費用可行流。將每個國家拆點。源點向乙個新建節點連一條上界為總人數下界為0費用為0的邊。新建節點向每個國家的入點連一條上界為正無窮下界為0費用為0的邊。每個國家的入點向出點連一條上下界均為該國家訪問人數費用為0的邊。每個國家的出點向匯點連一條上界為正無窮下界為0費用為0的邊。對於國家i...

BZOJ2055 80人環遊世界

上下界最小費用流 限制點訪問量 拆點 i,i 建圖 1.s s m,m 0 2.s i 0,inf 0 i t 0,inf 0 3.i j 0,inf x 4.i i vi,vi 0 然後就是上下界流的常見套路啦 根據 調整 原則 先是每個點點權為di ini outi 然後 0的連源點 0的連匯點...