본문 바로가기

알고리즘

BOJ 5052 전화번호 목록

www.acmicpc.net/problem/5052

 

5052번: 전화번호 목록

첫째 줄에 테스트 케이스의 개수 t가 주어진다. (1 ≤ t ≤ 50) 각 테스트 케이스의 첫째 줄에는 전화번호의 수 n이 주어진다. (1 ≤ n ≤ 10000) 다음 n개의 줄에는 목록에 포함되어 있는 전화번호가

www.acmicpc.net

처음에는 Naive하게 문자열을 입력받을 때 마다 지금까지 입력받았던 모든 문자열과 비교하여 일관성을 체크하는 방법을 생각했다.

해당 방법은 시간복잡도 O(t * n ^2) 이니 될리가 없었다.

 

이 문제에서 시간을 줄이기 위해서는 앞서 입력받은 문자열들과 비교하는 횟수를 줄일 필요가 있다.

문자열의 비슷한 구간이 모아져있다면, 비교횟수를 줄일 수 있을 것이라고 생각했고, 이와 비슷한 아이디어로 구현되어있는 trie가 떠올랐다.

그래서 Trie 를 사용하면 될 것 같아 trie를 사용하여 문제를 풀었다.

 

아래 코드는 제출 코드이다.

 

#include <cstdio>

class node{
public:
    node* arr[10];
    bool end;
    void clear(){
        for(int i=0;i<10;i++){
            this->arr[i] = NULL;
        }
        end = false; 
    }
    node(){ this->clear();}
};
node aa[100001];
class trie{
public:
    int idx = 0;
    bool insert(char* a, int n){
        node* now = &(aa[0]);
        node* next;
        for(int i=0;;i++){

            if(a[i]){
                next = now->arr[a[i]-'0'];  
                if(next == 0) {
                    //printf("%d\n", idx);
                    ++idx;
                    now->arr[a[i]-'0'] = &(aa[idx]);
                    now->arr[a[i]-'0']->clear();
                }
                
                now = now->arr[a[i]-'0'];
            }
            else{
                now->end = true;
                for(int i=0;i<10;i++){
                    if(now->arr[i]) return true;
                }
                return false;
            }          
            if(now->end) {
                return true;
            }
        }
    }
    void clear(){
        aa[0].clear();
        idx = 0;
    }
};
trie t;

int main(){
    int T; scanf("%d",&T);
    while(T--){
        int n; scanf("%d",&n);
        char str[11];
        bool flag = false;
        t.clear();

        for(int i=0;i<n;i++){
            scanf("%s",str);
            if(flag) continue;
            //else
            flag = t.insert(str, 0);
        }
        if(flag) printf("NO\n");
        else printf("YES\n");
    }

    return 0;
}

 

 

PS 1. 문제 풀때 clear 함수에 들어가는 내용을 initializer에 써서 많은 시간을 버린건 아쉬웠다.

PS 2. class 대신 배열로 선언하면 실행시간을 좀 더 줄일 수 있을 것이다.

 

'알고리즘' 카테고리의 다른 글

BOJ 2887 행성 터널  (0) 2021.03.28
BOJ 13334 철로  (0) 2021.02.16
BOJ 12100 2048 (Easy)  (0) 2021.01.29
BOJ 7423 합이 0인 네 정수  (0) 2021.01.27
BOJ 2252 줄 세우기  (0) 2021.01.26