您的位置:首页 > 其它

风险度量 (判断联通性)

2018-03-24 22:53 183 查看
X星系的的防卫体系包含 n 个空间站。这 n 个空间站间有 m 条通信链路,构成通信网。
两个空间站间可能直接通信,也可能通过其它空间站中转。

对于两个站点x和y (x != y), 如果能找到一个站点z,使得:
当z被破坏后,x和y无法通信,则称z为关于x,y的关键站点。

显然,对于给定的两个站点,关于它们的关键点的个数越多,通信风险越大。

你的任务是:已知网络结构,求两站点之间的通信风险度,即:它们之间的关键点的个数。

输入数据第一行包含2个整数n(2 <= n <= 1000), m(0 <= m <= 2000),分别代表站点数,链路数。
空间站的编号从1到n。通信链路用其两端的站点编号表示。
接下来m行,每行两个整数 u,v (1 <= u, v <= n; u != v)代表一条链路。
最后1行,两个数u,v,代表被询问通信风险度的两个站点。

输出:一个整数,如果询问的两点不连通则输出-1.

例如:
用户输入:
7 6
1 3 2 3
3 4 3 5
4 5 5 6
1 6
则程序应该输出:
2
并查集#include<cstdio>
#include<cstring>
#include<algorithm>
#include<cmath>
typedef long long ll;
using namespace std;

const int maxn=2010;
int pre[maxn],u[maxn],v[maxn];
/*
利用并查集,总感觉有点慢
这道题就是n*m的一个复杂度
感觉效率不是特别高,还是比较好的
*/
int find_rt(int x){
return pre[x]==x?x:pre[x]=find_rt(pre[x]);
}

int main()
{
int n,m;
scanf("%d %d",&n,&m);
for(int i=1;i<=n;i++) pre[i]=i;
for(int i=1;i<=m;i++){
scanf("%d %d",&u[i],&v[i]);
int ru=find_rt(u[i]),rv=find_rt(v[i]);
if(ru!=rv)
pre[ru]=rv;
}
int a,b;
scanf("%d %d",&a,&b);
int ra=find_rt(a),rb=find_rt(b);
if(ra!=rb){
printf("-1\n");
return 0;
}
int ans=0;
for(int i=1;i<=n;i++){
if(i==a||i==b) continue;
for(int j=1;j<=n;j++) pre[j]=j;
for(int j=1;j<=m;j++){
if(u[j]==i||v[j]==i) continue;
int ru=find_rt(u[j]),rv=find_rt(v[j]);
if(ru!=rv)
pre[ru]=rv;
}
int ra=find_rt(a),rb=find_rt(b);
if(ra!=rb) ans++;
}
printf("%d\n",ans);
return 0;
}
bfs判断联通#include<cstdio>
#include<cstring>
#include<algorithm>
#include<cmath>
#include<queue>
#include<vector>
typedef long long ll;
using namespace std;

const int maxn=2010;
vector<int> vec[maxn];
int vis[maxn];

int bfs(int st,int ed){
queue<int> q;//千万注意这个循环调用的问题,就是有可能会有残留,导致一直出错
q.push(st);
vis[st]=1;
while(!q.empty()){
int now=q.front();
if(now==ed) return 1;
q.pop();
for(int i=0;i<vec[now].size();i++){
int v=vec[now][i];
if(!vis[v]){
vis[v]=1;
q.push(v);
}
}
}
return 0;
}

int main()
{
int n,m;
scanf("%d %d",&n,&m);
for(int i=1;i<=m;i++){
int u,v;
scanf("%d %d",&u,&v);
vec[u].push_back(v);
vec[v].push_back(u);
}
int a,b;
scanf("%d %d",&a,&b);
if(!bfs(a,b)){
printf("-1\n");
return 0;
}
int ans=0;
for(int i=1;i<=n;i++){
if(i==a||i==b) continue;
memset(vis,0,sizeof(vis));
vis[i]=1;
if(!bfs(a,b)) ans++;
}
printf("%d\n",ans);
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: