【CQOI2016】【BZOJ4519】不同的最小割
2016-04-29 16:13
260 查看
Description
学过图论的同学都知道最小割的概念:对于一个图,某个对图中结点的划分将图中所有结点分成
两个部分,如果结点s,t不在同一个部分中,则称这个划分是关于s,t的割。对于带权图来说,将
所有顶点处在不同部分的边的权值相加所得到的值定义为这个割的容量,而s,t的最小割指的是在
关于s,t的割中容量最小的割。
而对冲刺NOI竞赛的选手而言,求带权图中两点的最小割已经不是什么难事了。我们可以把
视野放宽,考虑有N个点的无向连通图中所有点对的最小割的容量,共能得到N(N−1)
2个数值。
这些数值中互不相同的有多少个呢?这似乎是个有趣的问题。
Input
输入文件第一行包含两个数N,M,表示点数和边数。接下来M行,每行三个数u,v,w,
表示点u和点v(从1开始标号)之间有条边权值是w。
1<=N<=850 1<=M<=8500 1<=W<=100000
Output
输出文件第一行为一个整数,表示个数。
Sample Input
4 4
1 2 3
1 3 6
2 4 5
3 4 4
Sample Output
3
HINT
Source
模板默写大会
学过图论的同学都知道最小割的概念:对于一个图,某个对图中结点的划分将图中所有结点分成
两个部分,如果结点s,t不在同一个部分中,则称这个划分是关于s,t的割。对于带权图来说,将
所有顶点处在不同部分的边的权值相加所得到的值定义为这个割的容量,而s,t的最小割指的是在
关于s,t的割中容量最小的割。
而对冲刺NOI竞赛的选手而言,求带权图中两点的最小割已经不是什么难事了。我们可以把
视野放宽,考虑有N个点的无向连通图中所有点对的最小割的容量,共能得到N(N−1)
2个数值。
这些数值中互不相同的有多少个呢?这似乎是个有趣的问题。
Input
输入文件第一行包含两个数N,M,表示点数和边数。接下来M行,每行三个数u,v,w,
表示点u和点v(从1开始标号)之间有条边权值是w。
1<=N<=850 1<=M<=8500 1<=W<=100000
Output
输出文件第一行为一个整数,表示个数。
Sample Input
4 4
1 2 3
1 3 6
2 4 5
3 4 4
Sample Output
3
HINT
Source
模板默写大会
#include<iostream> #include<cstdio> #include<cstring> #include<cmath> #include<algorithm> #include<tr1/unordered_map> #define MAXN 1000 #define LL long long #define GET (ch>='0'&&ch<='9') #define MAXLL 1ll<<60 using namespace std; using namespace std::tr1; template <class classname> inline void in(classname &x) { char ch=getchar();x=0; while (!GET) ch=getchar(); while (GET) x=x*10+ch-'0',ch=getchar(); } unordered_map<int,int> Hash; int n,m,S,T,top,ans; bool vis[MAXN]; int dis[MAXN],cnt[MAXN],tmp[MAXN]; int C[MAXN][MAXN],num[MAXN],mncut[MAXN][MAXN]; struct edge { int st,to,c; edge *next,*rev; }e[MAXN*10<<1],*prev[MAXN]; inline void insert(int u,int v,int c) { e[++top].to=v;e[top].st=u;e[top].c=c;e[top].next=prev[u];prev[u]=&e[top]; } inline void add(int u,int v,int c) { insert(u,v,c);insert(v,u,c);prev[u]->rev=prev[v];prev[v]->rev=prev[u]; } int ISAP() { edge *E[MAXN],*rep[MAXN];int ret=0;int now=S; for (int i=1;i<=n;++i) E[i]=prev[i]; memset(dis,0,sizeof(dis));memset(cnt,0,sizeof(cnt));cnt[0]=n; while (dis[S]<=n) { edge *i;bool flag=0; for (i=E[now];i;i=i->next) if (i->c>0&&dis[i->to]+1==dis[now]) { flag=1;E[now]=i;break; } if (flag) { rep[now=i->to]=i; if (now==T) { int minn=0x3f3f3f3f; for (int i=T;i!=S;i=rep[i]->st) minn=min(minn,rep[i]->c); for (int i=T;i!=S;i=rep[i]->st) rep[i]->c-=minn,rep[i]->rev->c+=minn; ret+=minn;now=S; } continue; } if (!(--cnt[dis[now]])) break; int mind=n+1;E[now]=prev[now]; for (edge *i=prev[now];i;i=i->next) if (i->c>0) mind=min(mind,dis[i->to]); dis[now]=mind+1;++cnt[dis[now]]; if (now!=S) now=rep[now]->st; } return ret; } void dfs(int x) { vis[x]=1; for (edge *i=prev[x];i;i=i->next) if (i->c>0&&!vis[i->to]) dfs(i->to); } void solve(int l,int r) { if (l==r) return; for (int i=1;i<=top;i+=2) e[i].c=e[i].rev->c=((e[i].c+e[i].rev->c)>>1); S=num[l];T=num[r];int t=ISAP();memset(vis,0,sizeof(vis));dfs(S); for (int i=1;i<=n;i++) if (vis[i]) for (int j=1;j<=n;j++) if (!vis[j]) mncut[i][j]=min(mncut[i][j],t),mncut[j][i]=min(mncut[j][i],t); int tp=0,len,L=l-1; for (int i=l;i<=r;i++) if (vis[num[i]]) tmp[++tp]=num[i];len=tp; for (int i=l;i<=r;i++) if (!vis[num[i]]) tmp[++tp]=num[i]; for (int i=1;i<=tp;i++) num[++L]=tmp[i]; solve(l,l+len-1);solve(l+len,r); } int main() { in(n);in(m);int u,v,w;memset(mncut,0x3f,sizeof(mncut)); for (int i=1;i<=n;i++) num[i]=i; for (int i=1;i<=m;i++) in(u),in(v),in(w),C[u][v]+=w,C[v][u]+=w; for (int i=1;i<=n;i++) for (int j=i+1;j<=n;j++) if (C[i][j]) add(i,j,C[i][j]); solve(1,n); for (int i=1;i<=n;i++) for (int j=i+1;j<=n;j++) if (Hash.find(mncut[i][j])==Hash.end()) { Hash[mncut[i][j]]=1;ans++; } printf("%d\n",ans); }
相关文章推荐
- Gomory-Hu tree (最小割树) 介绍及实现
- 【ZJOI2011】【BZOJ2229】最小割
- 【CERC2015】【BZOJ4435】Juice Junctions
- TopCoder SRM687 div1 500
- CQOI2016 不同的最小割 分治最小割(最小割树)
- Handler.post 问题
- LeetCode206:Reverse Linked List
- VTK交互
- mybatis中的#和$的区别
- ios微信点击超链接,去掉半透明黑色框效果
- 23种设计模式
- 读文件错误
- RecyclerView重写线性布局管理器
- 【BZOJ4548】小奇的糖果
- APUE读书笔记-第十章 信号
- @RequestParam @RequestBody @PathVariable
- PAT-B 1027. 打印沙漏
- maven一直无法依赖问题(总结)
- nyoj_75 日期计算
- javascript中继承(二)-----借用构造函数继承的个人理解