Problem Solving/BOJ

[백준 14891번] [구현] 톱니바퀴

  • -
728x90
반응형

실수를 상당히 많이 해서 시간이 오래 걸렸다..

 

제일 중요한 것은 index 실수를 하였다. 처음에 풀 때 돌아가는 톱니바퀴를 따로 저장해두고 한번에 돌리는 아이디어를 짠 것 까지는 좋은데, 들어가는 index와 매칭시키는 것을 실수하였다. 해당 문제점때문에 매칭이 잘못되어 틀리게 나왔었다.

 

또한 추가적으로 생각해보면, 각 상태를 따로 저장해두지 말고 이중배열로 data를 저장해두었으면 if문을 상당히 줄일 수 있었다.

first, second, third, fourth를 나누어서 vector에 정보를 저장해두었는데 생각해보니까 매우 비효율적인 것 같다. 

사실 그러한 방향성만 수정하였으면 코드 자체는 그리 길지 않게 해결할 수 있을 것 같다.

(다시 짤까 고민도 했었는데.. 귀찮아서 포기.. )

 

대략적으로 data_store 느낌으로 각 circle 이름과 data값들을 매칭시키고, pair나 구조체등을 이용하여 index를 저장해놓는다.

(나라면 구조체를 data_store[5]로 잡고, 해당 구조체 안에 component를 8개 숫자들 저장, right_index, left_index를 저장시켰을 것 같다.) 그렇게 되면 바로 data_store[circle_num].right_index 와 data_store[circle_num + 1].left_index를 비교하는 방식으로 돌아가는지 여부를 처리할 수 있게 된다.

 

일단 비효율적이긴 하지만 구현한 코드는 다음과 같다.

#include <iostream>
#include <vector>
#include <string>
#include <algorithm>

using namespace std;
vector<int> first_circle, second_circle, third_circle, fourth_circle;
int right_index_first = 2;
int left_index_first = 6;
int right_index_second = 2;
int left_index_second = 6;
int right_index_third = 2;
int left_index_third = 6;
int right_index_fourth = 2;
int left_index_fourth = 6;

int rotate_condition_check[5] = {0};

int change_index(int index_num, int direction){
    // 시계 방향
    if(direction == 1){
        if(index_num == 0) return 7;
        else return index_num - 1;
    }
    // 반시계 방향
    else{
        if(index_num == 7) return 0;
        else return index_num + 1;
    }
}

// Condition  우측 : 1, 좌측 : 0
void rotate_check(int rotate_circle, int condition){
    if (rotate_circle > 4 || rotate_circle < 1) return; // Early exit
    if(rotate_circle == 1){
        // 우측 체크
        if(condition == 1){
            if(first_circle[right_index_first] == second_circle[left_index_second]) return;
            else{
                rotate_condition_check[rotate_circle + 1] = 1;
                rotate_check(rotate_circle + 1, 1);
                return;
            }
        }
        else return; // 좌측으로는 갈 수 없음

    }
    else if(rotate_circle == 2){
        // 우측 체크
        if(condition == 1){
            if(second_circle[right_index_second] == third_circle[left_index_third]) return;
            else{
                rotate_condition_check[rotate_circle + 1] = 1;
                rotate_check(rotate_circle + 1, 1);
                return;
            }
        }
        // 왼쪽 체크
        else{
            if(second_circle[left_index_second] == first_circle[right_index_first]) return;
            else{
                rotate_condition_check[rotate_circle - 1] = 1;
                rotate_check(rotate_circle - 1, 0);
                return;
            }
        }

    }
    else if(rotate_circle == 3){
        // 우측 체크
        if(condition == 1){
            if(third_circle[right_index_third] == fourth_circle[left_index_fourth]) return;
            else{
                rotate_condition_check[rotate_circle + 1] = 1;
                rotate_check(rotate_circle + 1, 1);
                return;
            }
        }
        // 왼쪽 체크
        else{
            if(third_circle[left_index_third] == second_circle[right_index_second]) return;
            else{
                rotate_condition_check[rotate_circle - 1] = 1;
                rotate_check(rotate_circle - 1, 0);
                return;
            }
        }

    }
    else{
        // 왼쪽 체크
        if(condition == 0){
            if(fourth_circle[left_index_fourth] == third_circle[right_index_third]) return;
            else{
                rotate_condition_check[rotate_circle - 1] = 1;
                rotate_check(rotate_circle - 1, 0);
                return;
            }
        }
        else return; // 우측으로는 갈 수 없음
    }
    return;
}

void change_index_fuc(int rotate_circle, int direction, int condition){
    if(rotate_circle < 1 || rotate_circle > 4) return; // Early exit
    if(rotate_circle == 1){
        if(rotate_condition_check[rotate_circle] == 1){
            right_index_first = change_index(right_index_first, direction);
            left_index_first = change_index(left_index_first, direction);
        }
        else return; // 돌아가지 않는 상황
        if(direction == 1){
            if(condition == 1) change_index_fuc(rotate_circle + 1, - 1, 1);
            else change_index_fuc(rotate_circle - 1, - 1, 0);
        }
        else{
            if(condition == 1) change_index_fuc(rotate_circle + 1, 1, 1);
            else change_index_fuc(rotate_circle - 1, 1, 0);
        }
        return;
    }
    else if(rotate_circle == 2){
        if(rotate_condition_check[rotate_circle] == 1){
            right_index_second = change_index(right_index_second, direction);
            left_index_second = change_index(left_index_second, direction);
        }
        else return; // 돌아가지 않는 상황
        if(direction == 1){
            if(condition == 1) change_index_fuc(rotate_circle + 1, - 1, 1);
            else change_index_fuc(rotate_circle - 1, - 1, 0);
        }
        else{
            if(condition == 1) change_index_fuc(rotate_circle + 1, 1, 1);
            else change_index_fuc(rotate_circle - 1, 1, 0);
        }
        return;

    }
    else if(rotate_circle == 3){
        if(rotate_condition_check[rotate_circle] == 1){
            right_index_third = change_index(right_index_third, direction);
            left_index_third = change_index(left_index_third, direction);
        }
        else return; // 돌아가지 않는 상황
        if(direction == 1){
            if(condition == 1) change_index_fuc(rotate_circle + 1, - 1, 1);
            else change_index_fuc(rotate_circle - 1, - 1, 0);
        }
        else{
            if(condition == 1) change_index_fuc(rotate_circle + 1, 1, 1);
            else change_index_fuc(rotate_circle - 1, 1, 0);
        }
        return;

    }
    else if(rotate_circle == 4){
        if(rotate_condition_check[rotate_circle] == 1){
            right_index_fourth = change_index(right_index_fourth, direction);
            left_index_fourth = change_index(left_index_fourth, direction);
        }
        else return; // 돌아가지 않는 상황
        if(direction == 1){
            if(condition == 1) change_index_fuc(rotate_circle + 1, - 1, 1);
            else change_index_fuc(rotate_circle - 1, - 1, 0);
        }
        else{
            if(condition == 1) change_index_fuc(rotate_circle + 1, 1, 1);
            else change_index_fuc(rotate_circle - 1, 1, 0);
        }
        return;
    }
}

int main(void){
    // 데이터 저장

    for(int i = 0; i < 8; i++){
        int temp;
        scanf("%1d", &temp);
        first_circle.push_back(temp);
    }
    for(int i = 0; i < 8; i++){
        int temp;
        scanf("%1d", &temp);
        second_circle.push_back(temp);
    }
    for(int i = 0; i < 8; i++){
        int temp;
        scanf("%1d", &temp);
        third_circle.push_back(temp);
    }
    for(int i = 0; i < 8; i++){
        int temp;
        scanf("%1d", &temp);
        fourth_circle.push_back(temp);
    }

    int change_num;
    cin >> change_num;

    for(int i = 0; i < change_num; i++){
        int change_circle, direction;
        cin >> change_circle >> direction;
        fill(rotate_condition_check, rotate_condition_check + 5, 0);
        rotate_condition_check[change_circle] = 1;
        rotate_check(change_circle, 1);
        rotate_check(change_circle, 0);
        change_index_fuc(change_circle, direction, 1);
        if(direction == 1){
            change_index_fuc(change_circle - 1, -1, 0);
        }
        else{
            change_index_fuc(change_circle - 1, 1, 0);
        }
    }

    for(int i = 0; i < 2; i++){
        right_index_first = change_index(right_index_first, 1);
        right_index_second = change_index(right_index_second, 1);
        right_index_third = change_index(right_index_third, 1);
        right_index_fourth = change_index(right_index_fourth, 1);
    }

    int result = 0;

    if(first_circle[right_index_first] == 1) result += 1;
    if(second_circle[right_index_second] == 1) result += 2;
    if(third_circle[right_index_third] == 1) result += 4;
    if(fourth_circle[right_index_fourth] == 1) result += 8;

    cout << result << "\n";
    return 0;
}

 

딱 봐도 비슷한 코드가 돌고 있는 것을 확인할 수 있다. Index를 활용하여 object를 처리하는 방식으로 했으면 이렇게 if문을 4가지씩 나눠서 할 필요가 없다고 볼 수 있다. (대략 이렇게 되면 70줄 정도면 끝날 듯..)

 

 

반응형
Contents

포스팅 주소를 복사했습니다

이 글이 도움이 되었다면 공감 부탁드립니다.