pat甲级打卡-1013 Battle Over Cities

一题双解:

1.临界矩阵+dfs 查询二维矩阵邻接分量

// 题目要求:output 指定城市沦陷后需要修复的路的条数 
// 图的存储,因为要多次查询两节点是否连接,所以用邻接矩阵,相比邻接表的时间更低
#include<bits/stdc++.h>
using namespace std;
const int N=1010;
int v[N][N];
bool visited[N];
int n,m,k;
void dfs(int node){
    visited[node]=true;
    for(int i=1;i<=n;i++){
        if(!visited[i] && v[node][i]==1)
            dfs(i);
    }
}

int main(){
    int a,b;
    cin>>n>>m>>k;
    while(m--){
        cin>>a>>b;
        v[a][b]=v[b][a]=1;
    }
    while(k--){
        memset(visited,0,sizeof visited);
        int id,cnt=0;
        cin>>id;
        visited[id]=true;
        for(int j=1;j<=n;j++){
            if(!visited[j]){
                dfs(j);
                cnt++;
            }
        }
        cout<<cnt-1<<endl;
    }
    return 0;
}

2.并查集

// 题目要求:output 指定城市沦陷后需要修复的路的条数 

//并查集处理连通分量问题

#include<bits/stdc++.h>
using namespace std;
const int N=1010;
int v[N][N];//邻接矩阵
int p[N];
int n,m,k;

int find(int x){
    if(p[x]!=x) p[x]=find(p[x]);
    return p[x];
}

void init(){
    for(int i=1;i<=n;i++)   p[i]=i;
    return;
}

void merge(int a,int b){
    a=find(a);
    b=find(b);
    if(a!=b){
        p[a]=b;
    }
    return ;
}

int oper(int x){
    int sum=0;
    for(int i=0;i<N;i++){//断开与x相连的所有边
        for(int j=0;j<N;j++){
            if(i!=x && j!=x && v[i][j]==1){
                merge(i,j);
            }
        }
    }
    for(int i=1;i<=n;i++){
        if(p[i]==i) sum++;
    }
    return sum-2; //除去被占领的节点本身以及n个节点需要n-1条路
    
}

int main(){
    cin>>n>>m>>k;
    for(int i=1;i<=n;i++){
        p[i]=i;
    }
    while(m--){
        int a,b;
        cin>>a>>b;
        v[a][b]=v[b][a]=1;
    }
    while(k--){
        int id;
        cin>>id;
        init();
        int ans=oper(id);
        cout<<ans<<endl;
    }
    return 0;
    
}



posted @ 2022-05-02 16:35  秋月桐  阅读(30)  评论(0编辑  收藏  举报