250x250
Notice
Recent Posts
Recent Comments
Link
일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | 3 | 4 | |||
5 | 6 | 7 | 8 | 9 | 10 | 11 |
12 | 13 | 14 | 15 | 16 | 17 | 18 |
19 | 20 | 21 | 22 | 23 | 24 | 25 |
26 | 27 | 28 | 29 | 30 | 31 |
Tags
- 백준#boj#12755
- 백준#BOJ#14501#퇴사#브루트포스
- 백준#boj#16932#모양만들기
- 백준#BOJ#2615#오목
- 백준#BOJ#8012#한동이는영업사원
- 백준#BOJ#1939#중량제한
- 백준#BOJ#12865#평범한배낭
Archives
- Today
- Total
순간을 성실히, 화려함보단 꾸준함을
[boj : 4803] 트리 본문
문제 : 트리의 개수를 구해라. (이때, x==y 인 조건은 배제해도 된다. 적어도 이 문제에는 x==y인 데이터는 존재하지 않음)
해설 : 뭐 각자 선호하는 방식으로 풀면 된다. disjoint-set 개념을 이용해도 되고 dfs를 이용해서 구해도 되고.
저는 dfs로 구했습니다. 이때 트리라는 것을 체크하는 방법이 여러가지 존재한다고 하네요.
전 끝까지 갔을때 싸이클이 존재하면 false를 존재하지 않는다면 true를 return 시켜 & 연산으로 판별해주었습니다.
다른 방법은 트리는 n개의 정점이 주어지고 항상 간선의 개수는 n-1개라는 것 입니다.
그럼 어느 정점으로 들어가게 되고 그 정점에 붙어있는 간선의 개수를 더해줍니다. 그리고 (정점의 개수)*2 = (간선의 개수) 라면 트리, 아니면 트리가 아니다라고 판별해주면 됩니다.
#include<bits/stdc++.h>
using namespace std;
int n, m;
int memo[510];
vector<int> v[510];
bool dfs(int x,int prev);
int main()
{
int cnt, t = 1;
while (true) {
cnt = 0;
int x, y;
cin >> n >> m;
if (n == 0 && m == 0)break;
for (int i = 0; i < m; i++) {
cin >> x >> y;
v[x].push_back(y);
v[y].push_back(x);
}
for (int i = 1; i <= n; i++)
if (!memo[i]) {
if (dfs(i, -1)) cnt++;
}
if (cnt == 1)
printf("Case %d: There is one tree.", t);
else if(cnt>1)
printf("Case %d: A forest of %d trees.", t,cnt);
else
printf("Case %d: No trees.", t);
cout << "\n";
memset(memo, 0, sizeof(memo));
for (int i = 1; i <= n; i++)
v[i].clear();
t++;
}
return 0;
}
bool dfs(int x,int prev)
{
bool ret = true;
if (memo[x] == 1)
return false;
memo[x] = 1;
for (int i = 0; i < v[x].size(); i++)
if(prev!=v[x][i])
ret &= dfs(v[x][i],x);
return ret;
}
'알고리즘,SQL > 백준,BOJ' 카테고리의 다른 글
[boj : 12904] A와 B (0) | 2020.12.23 |
---|---|
[boj : 13273] 로마숫자 (0) | 2020.12.23 |
[boj : 1833] 고속철도 설계하기 (0) | 2020.12.22 |
[boj : 12739] 돌림판(small) (0) | 2020.12.22 |
[boj : 7682] 틱택토 (0) | 2020.12.20 |