본문 바로가기
Algorithm/BOJ

백준 5446번 : 용량 부족 - 트라이, Java

by catchJava 2023. 1. 2.

https://www.acmicpc.net/problem/5446

 

5446번: 용량 부족

팀포2 덕후 연수는 팀포2를 다운받던 도중 하드 용량이 부족하다는 것을 알았다. 이때는 침착하게 팀포2를 하지 말거나 하드를 새로 사면 되지만 불가능했고, 결국 하드에서 쓸모없는 파일을 지

www.acmicpc.net

1.문제설명

주어지는 문자열을 바탕으로

트라이를 만들고 각 분기점에 대해 파일들을 한번에 지울 수 있는지 없는지 판별하여

모든 파일을 지우는 최소 횟수를 구해야 하는 문제이다.

 

우선 주어지는 N1개의 단어를 바탕으로 트라이를 구현한 후

지울 수 없는 단어 N2개에 대해서

이미 구현된 트라이에 해당 단어는 지울 수 없음을 마킹한다.

 

마킹이 완료되면 전체 트라이를 순회하면서

해당 분기를 지울 수 있으면 1을 리턴하고,

지울 수 없다면 다음 노드로 이동한다.

 

다음 노드에서도 해당 분기를 지울 수 있으면 1을 리턴하고, 지울 수 없다면

다음 노드로 이동하는 과정을 재귀적 구현한다.

이때 지울 수 없지만 단어의 마지막 지점인 경우에는 1을 더해주어야 한다.

 

2.문제풀이코드 Java

 

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
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
//package org.example;
 
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.util.*;
 
public class Main {
    final int MX = 63;
    final long mod = 1000000007;
 
    public int charToNum(char a) {
        if (a == '.'return 62;
        if (Character.isDigit(a)) { // 0~9
            return a - '0';
        }
        int num = a - 'A';
        if (num >= 26return a - 'a' + 10;
        return num + 36;
    }
 
    class Trie {
        Trie[] child;
        boolean end;
        boolean canDelete;
 
        public Trie() {
            child = new Trie[MX];
            end = false;
            canDelete = true;
        }
 
        public void insert(String str) {
            Trie tmp = this;
            for (int i = 0; i < str.length(); i++) {
                int cur = charToNum(str.charAt(i));
                if (tmp.child[cur] == null) {
                    tmp.child[cur] = new Trie();
                }
                tmp = tmp.child[cur];
            }
            tmp.end = true;
        }
 
        public void markNotDelete(String str) {
            Trie tmp = this;
 
            for (int i = 0; i < str.length(); i++) {
                int cur = charToNum(str.charAt(i));
                if (tmp.child[cur] == null) {
                    return;
                }
                tmp.child[cur].canDelete = false;
                tmp = tmp.child[cur];
            }
        }
 
        public int getAns() {
            Trie tmp = this;
 
            int ret = 0;
 
            for (int i = 0; i < MX; i++) {
                if (tmp.child[i] != null) {
                    if (tmp.child[i].end && !tmp.child[i].canDelete) {
                        ret++;
                    }
                    if (tmp.child[i].canDelete) {
                        ret++;
                    } else {
                        ret += tmp.child[i].getAns();
                    }
                }
            }
            return ret;
        }
 
    }
 
 
    public void solution() throws Exception {
        BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
        int t = Integer.parseInt(br.readLine());
 
        for (int T = 0; T < t; T++) {
            int N1 = Integer.parseInt(br.readLine());
 
            Trie root = new Trie();
 
            for (int i = 0; i < N1; i++) {
                String trieInput = br.readLine();
                root.insert(trieInput);
            }
 
            int N2 = Integer.parseInt(br.readLine());
 
            for (int i = 0; i < N2; i++) {
                String notDeleteName = br.readLine();
                root.markNotDelete(notDeleteName);
            }
 
            // root check
            boolean canRmAll = true;
            for (int i = 0; i < MX; i++) {
                if (root.child[i] != null && !root.child[i].canDelete) {
                    canRmAll = false;
                    break;
                }
            }
            if (canRmAll) {
                System.out.println(1);
                continue;
            }
 
            System.out.println(root.getAns());
        }
    }
 
    public static void main(String[] args) throws Exception {
        new Main().solution();
    }
}
cs