문제
트리의 지름이란, 트리에서 임의의 두 점 사이의 거리 중 가장 긴 것을 말한다. 트리의 지름을 구하는 프로그램을 작성하시오.
입력
트리가 입력으로 주어진다. 먼저 첫 번째 줄에서는 트리의 정점의 개수 V가 주어지고 (2 ≤ V ≤ 100,000)둘째 줄부터 V개의 줄에 걸쳐 간선의 정보가 다음과 같이 주어진다. 정점 번호는 1부터 V까지 매겨져 있다.
먼저 정점 번호가 주어지고, 이어서 연결된 간선의 정보를 의미하는 정수가 두 개씩 주어지는데, 하나는 정점번호, 다른 하나는 그 정점까지의 거리이다. 예를 들어 네 번째 줄의 경우 정점 3은 정점 1과 거리가 2인 간선으로 연결되어 있고, 정점 4와는 거리가 3인 간선으로 연결되어 있는 것을 보여준다. 각 줄의 마지막에는 -1이 입력으로 주어진다. 주어지는 거리는 모두 10,000 이하의 자연수이다.
출력
첫째 줄에 트리의 지름을 출력한다.
👇 접근방식
일단 나와있는 테스트 케이스를 그려보았습니다.
그려보니깐, 인접해있는 노드들 가운데, 노드와 노드를 쭉 늘렸을 때, 길이가 가장 긴 첫 노드와 끝 노드의 사이의 간선 값을 다 더해준 값이 트리의 지름을 나타내는 말이였습니다.
구하는 방식이 어려워서 구글링을 통해서 문제를 익히는 방법으로 구현했습니다.
추가로 간략하게 증명을 다른 분 블로그를 참고하면서 정리한 게 있습니다.
https://devnuts.tistory.com/78 위 링크로 들어가서 한 번 보고 오시고,
이해가 안되면... 다른 분 것과 참고하셔도 좋을 거 같습니다.
DFS와 BFS 방식으로 다 풀 수 있는 문제지만,
DFS 문제로 문제를 풀어보겠습니다 !
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.StringTokenizer;
public class Boj_트리의지름 {
static int V; // 트리의 정점의 개수
static ArrayList<ArrayList<Node>> nodeList = new ArrayList<>();
static boolean[] visited;
static int max, farNode;
static class Node {
int data;
int edge;
public Node(int data, int edge) {
this.data = data;
this.edge = edge;
}
}
static void dfs(int data, int disSum) {
visited[data] = true;
// 가장 먼 노드 data 최신화
if (disSum > max) {
max = disSum;
farNode = data;
}
// recur
for (Node childData : nodeList.get(data)) {
if (!visited[childData.data]) {
visited[childData.data] = true;
dfs(childData.data, childData.edge + disSum);
}
}
}
public static void main(String[] args) throws IOException {
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
V = Integer.parseInt(br.readLine());
// list 초기화
for (int i = 0; i < V + 1; i++) {
nodeList.add(new ArrayList<>());
}
// 노드리스트 초기화
for (int i = 0; i < V; i++) {
StringTokenizer st = new StringTokenizer(br.readLine());
int node = Integer.parseInt(st.nextToken());
String tmp;
while (!(tmp = st.nextToken()).equals("-1")) {
int data = Integer.parseInt(tmp);
int edge = Integer.parseInt(st.nextToken());
nodeList.get(node).add(new Node(data, edge));
}
}
visited = new boolean[V + 1];
dfs(1, 0);
visited = new boolean[V + 1];
dfs(farNode, 0);
System.out.println(max);
}
}
'PS > 백준' 카테고리의 다른 글
[백준 *Java] - 이모티콘(14226) (0) | 2022.04.27 |
---|---|
[백준 *Java] - BFS 스페셜 저지 (16940) (0) | 2022.04.25 |
[백준 *Java] - 트리순회(1991) (0) | 2022.04.22 |
[백준 *Java] - 서울 지하철 2호선 (0) | 2022.04.19 |
[백준 *Java] - 부분수열의 합(1182) (0) | 2022.04.13 |