반응형
문제 출처 : www.acmicpc.net/problem/1260
문제
그래프를 DFS로 탐색한 결과와 BFS로 탐색한 결과를 출력하는 프로그램을 작성하시오. 단, 방문할 수 있는 정점이 여러 개인 경우에는 정점 번호가 작은 것을 먼저 방문하고, 더 이상 방문할 수 있는 점이 없는 경우 종료한다. 정점 번호는 1번부터 N번까지이다.
입력
첫째 줄에 정점의 개수 N(1 ≤ N ≤ 1,000), 간선의 개수 M(1 ≤ M ≤ 10,000), 탐색을 시작할 정점의 번호 V가 주어진다. 다음 M개의 줄에는 간선이 연결하는 두 정점의 번호가 주어진다. 어떤 두 정점 사이에 여러 개의 간선이 있을 수 있다. 입력으로 주어지는 간선은 양방향이다.
출력
첫째 줄에 DFS를 수행한 결과를, 그 다음 줄에는 BFS를 수행한 결과를 출력한다. V부터 방문된 점을 순서대로 출력하면 된다.
알고리즘 분류
풀이
dfs : 깊이 우선 탐색
bfs : 너비 우선 탐색
dfs는 재귀 또는 스택을 이용하여 구현할 수 있다.
스택을 이용한 dfs는 현재 노드와 인접한 노드를 스택에 저장하고,
스택의 top을 방문, 현 노드의 인접 노드 스택 저장의 과정을 반복한다.
이때, 방문한 적이 있는 스택의 top은 무시한다.
bfs는 큐를 이용하여 구현할 수 있다.
현재 노드와 인접한 노드를 큐에 저장하고,
큐의 top을 방문, 현 노드의 인접 노드 큐 저장의 과정을 반복한다.
stack을 이용한 dfs 구현은 stack은 FILO, queue는 FIFO라는 점에서
각각 사용한 자료구조가 다르다.
코드1(재귀DFS)
#include<iostream>
#include<queue>
using namespace std;
int line[1001][1001];
int visited[1001];
int n, m, v;
queue<int> q;
void dfs(int idx) {
cout << idx << ' ';
for (int i = 1; i <= n; i++) {
if (line[idx][i] && !visited[i])
{
visited[i] = 1;
dfs(i);
}
}
}
void bfs(int idx) {
q.push(idx);
while (!q.empty()) {
idx = q.front();
q.pop();
cout << idx << ' ';
for (int i = 1; i <= n; i++) {
if (line[idx][i] && !visited[i]) {
q.push(i);
visited[i] = 1;
}
}
}
}
int main() {
ios::sync_with_stdio(false);
cin.tie(NULL);
cout.tie(NULL);
cin >> n >> m >> v;
for (int i = 0; i < m; i++) {
int from, to;
cin >> from >> to;
line[from][to] = 1;
line[to][from] = 1;
}
visited[v] = 1;
dfs(v);
cout << '\n';
fill_n(visited, 1001, 0);
visited[v] = 1;
bfs(v);
return 0;
}
코드2(스택DFS)
#include<iostream>
#include<queue>
#include<stack>
using namespace std;
int line[1001][1001];
int visited[1001];
int n, m, v;
queue<int> q;
stack<int> stk;
void dfs(int idx) {
stk.push(idx);
while (!stk.empty()) {
idx = stk.top();
stk.pop();
if(!visited[idx])
cout << idx << ' ';
visited[idx] = 1;
for (int i = n; i > 0; i--) {
if (line[idx][i] && !visited[i]) {
stk.push(i);
}
}
}
}
void bfs(int idx) {
q.push(idx);
while (!q.empty()) {
idx = q.front();
q.pop();
cout << idx << ' ';
for (int i = 1; i <= n; i++) {
if (line[idx][i] && !visited[i]) {
q.push(i);
visited[i] = 1;
}
}
}
}
int main() {
ios::sync_with_stdio(false);
cin.tie(NULL);
cout.tie(NULL);
cin >> n >> m >> v;
for (int i = 0; i < m; i++) {
int from, to;
cin >> from >> to;
line[from][to] = 1;
line[to][from] = 1;
}
dfs(v);
cout << '\n';
fill_n(visited, 1001, 0);
visited[v] = 1;
bfs(v);
return 0;
}
반응형
'알고리즘 문제 풀이 > 백준' 카테고리의 다른 글
백준 1697 숨바꼭질 c++ (0) | 2021.03.31 |
---|---|
백준 2178 미로 탐색 c++ (0) | 2021.03.31 |
백준 11000 강의실 배정 c++ (0) | 2021.03.29 |
백준 11003 최솟값 찾기 c++ (0) | 2021.03.26 |
백준 2075 N번째 큰 수 c++ (0) | 2021.03.25 |
댓글