垃圾blog太多,实在难以卒读,于是掏出书系统学习了下,发现边双联通分量无非就是把桥删了,讲了一大堆,毛用没有。
上次抄了个假板子搞的怀疑人生,遂口胡一遍算法,自己手撸了一个,希望从此BCC变成SB题。
#include <bits/stdc++.h>
using namespace std;
struct edge{
int to,next;
}e[40003];
int head[10003];
int cnt,tmpdfn,ans,S;
int dfn[10003];
int low[10003];
int a[10003];
int sum[10003];
bool vis[10003];
bool used[40003];
int n,m;
void add(int u,int v){
e[cnt].to=v;
e[cnt].next=head[u];
head[u]=cnt++;
}
void init(){
cnt=0,tmpdfn=0,S=0;
memset(head,-1,sizeof(head));
memset(vis,false,sizeof(vis));
memset(used,false,sizeof(used));
}
void dfs(int u){
vis[u]=true;
dfn[u]=++tmpdfn;
low[u]=dfn[u];
sum[u]=a[u];
for(int i=head[u];~i;i=e[i].next){
if(used[i])continue;
used[i]=used[i^1]=true;
int v=e[i].to;
if(vis[v]){
low[u]=min(low[u],dfn[v]);
}
else {
dfs(v);
low[u]=min(low[u],low[v]);
sum[u]+=sum[v];
if(low[v]>dfn[u]){
ans=min(ans,abs(S-sum[v]-sum[v]));
}
}
}
}
int main(){
while(~scanf("%d%d",&n,&m)){
init();
for(int i=0;i<n;i++){scanf("%d",&a[i]);S+=a[i];}
ans=S+1;
for(int j=1;j<=m;j++){
int u,v;
scanf("%d%d",&u,&v);
add(u,v);
add(v,u);
}
dfs(0);
for(int i=0;i<n;i++)if(!vis[i])ans=S+1;
if(ans>S)printf("impossible\n");
else printf("%d\n",ans);
}
}
本文介绍了一种简化版的BCC(边双联通分量)算法实现过程,通过删除桥接边来寻找图中的双连通分量,并提供了一个具体的C++代码实现示例。该算法有助于解决特定类型的图论问题。
1119

被折叠的 条评论
为什么被折叠?



