您的位置:首页 > 其它

bzoj 4519: [Cqoi2016]不同的最小割

2016-04-13 10:06 239 查看
读错题了,注意最小割树是针对无向图而言的。然后就是裸题。

#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<algorithm>
#include<set>
#define ll long long
#define inf 1e9
#define eps 1e-8
#define md
#define N 900
using namespace std;
set<int> st;
struct yts { int x,t,f,ne;} e[20010],p[20010];
int v[N],q[N],dep[N],g[N];
bool vis[N];
int S,T,num,m,tot=0;
 
void put(int x,int y,int f)
{
num++; e[num].x=x; e[num].t=y; e[num].f=f;
e[num].ne=v[x]; v[x]=num;
}
 
void add(int x,int y,int f)
{
put(x,y,f); put(y,x,f);
}
 
bool bfs()
{
memset(dep,0,sizeof(dep));
int h=0,w=1; q[1]=S; dep[S]=1;
while (h!=w)
{
int x=q[++h];
for (int i=v[x];i;i=e[i].ne)
{
int y=e[i].t;
if (e[i].f&&!dep[y])
{
dep[y]=dep[x]+1;
q[++w]=y;
}
}
}
return dep[T]>0;
}
 
int dfs(int x,int flow)
{
if (x==T) return flow;
int used=0,now=0;
for (int i=v[x];i;i=e[i].ne)
{
int y=e[i].t;
if (e[i].f&&dep[y]==dep[x]+1)
{
now=dfs(y,min(flow-used,e[i].f));
e[i].f-=now; e[i^1].f+=now;
used+=now; if (flow==used) break;
}
}
if (!used) dep[x]=-1;
return used;
}
 
int dinic(int s,int t)
{
S=s; T=t;
int ans=0;
while (bfs()) ans+=dfs(S,inf);
return ans;
}
 
void get(int x)
{
vis[x]=1;
for (int i=v[x];i;i=e[i].ne)
{
int y=e[i].t;
if (e[i].f&&!vis[y]) get(y);
}
}
 
void solve(int l,int r)
{
if (l>=r) return;
memset(v,0,sizeof(v)); num=1;
for (int i=1;i<=m;i++) add(p[i].x,p[i].t,p[i].f);
int ans=dinic(g[l],g[r]);
if (st.find(ans)==st.end()) { tot++; st.insert(ans); }
memset(vis,0,sizeof(vis));
get(g[l]);
int w=l-1;
for (int i=l;i<=r;i++)
if (vis[g[i]]) swap(g[++w],g[i]);
solve(l,w); solve(w+1,r);
}
 
int main()
{
int n;
scanf("%d%d",&n,&m);
for (int i=1;i<=m;i++) scanf("%d%d%d",&p[i].x,&p[i].t,&p[i].f);
for (int i=1;i<=n;i++) g[i]=i;
tot=0;
solve(1,n);
printf("%d\n",tot);
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: