问题 A: 第一题
时间限制: 1 Sec 内存限制: 32 MB
题目描述
该题的目的是要你统计图的连通分支数。
输入
每个输入文件包含若干行,每行两个整数i,j,表示节点i和j之间存在一条边。
输出
输出每个图的联通分支数。
样例输入
1 4
4 3
5 5
样例输出
2
因为没有给出一共有多少个点,所以需要在输入数据时自行记录。
代码
(1) DFS
#include<cstdio>
#include<vector>
using namespace std;
const int maxv = 1000010;
vector<int> Adj[maxv];//采用邻接表存储图
bool vis[maxv] = {false};
bool Hash[maxv] = {false}; //增加一个Hash来判断该图包含哪些点
void DFS(int u, int depth) {
vis[u] = true;
for(int i = 0; i < Adj[u].size(); i++){
int v = Adj[u][i];
if(vis[v] == false) {
DFS(v, depth + 1);
}
}
}
void DFSTrave(int n) {
int ltfz = 0;
for(int u = 0; u <= n; u++){
if(Hash[u] == true && vis[u] == false) {
DFS(u, 1);
ltfz++;
}
}
printf("%d\n", ltfz);
}
int main() {
int a, b, n = 0;
while(scanf("%d%d", &a, &b) != EOF){
if(a > n) n = a;
if(b > n) n = b;
Adj[a].push_back(b);
Adj[b].push_back(a);
Hash[a] = Hash[b] = true;
}
DFSTrave(n);
return 0;
}
/**************************************************************
Problem: 1798
User: 14041045
Language: C++
Result: 正确
Time:192 ms
Memory:31284 kb
****************************************************************/
(2) BFS
#include<cstdio>
#include<vector>
#include<queue>
using namespace std;
const int maxv = 1000010;
vector<int> Adj[maxv];
bool inq[maxv] = {false};
bool Hash[maxv] = {false};
void BFS(int u) {
queue<int> q;
q.push(u);
inq[u] = true;
while(!q.empty()) {
int u = q.front();
q.pop();
for(int i = 0; i < Adj[u].size(); i++) {
int v = Adj[u][i];
if(inq[v] == false) {
q.push(v);
inq[v] = true;
}
}
}
}
void BFSTrave(int n){
int ltfz = 0;
for(int u = 0; u <= n; u++){
if(Hash[u] == true && inq[u] == false){
BFS(u);
ltfz++;
}
}
printf("%d\n", ltfz);
}
int main() {
int a, b, n = 0;
while(scanf("%d%d", &a, &b) != EOF){
if(a > n) n = a;
if(b > n) n = b;
Adj[a].push_back(b);
Adj[b].push_back(a);
Hash[a] = Hash[b] = true;
}
BFSTrave(n);
return 0;
}
/**************************************************************
Problem: 1798
User: 14041045
Language: C++
Result: 正确
Time:216 ms
Memory:31292 kb
****************************************************************/