본문 바로가기

알고리즘 문제 풀이

프로그래머스(2018 카카오 블라인드 코딩 테스트 1차) - 비밀지도

https://programmers.co.kr/learn/courses/30/lessons/17681

 

코딩테스트 연습 - [1차] 비밀지도

비밀지도 네오는 평소 프로도가 비상금을 숨겨놓는 장소를 알려줄 비밀지도를 손에 넣었다. 그런데 이 비밀지도는 숫자로 암호화되어 있어 위치를 확인하기 위해서는 암호를 해독해야 한다. 다

programmers.co.kr

 

 

 

 

  

 

                                          풀이  코드  

 

function solution(n, arr1, arr2) {
    const answer = [];
    const result = [];
    
    let sum = 0;
    let str = '';
    
    for (let i = 0; i < arr1.length; i++) {
        sum = arr1[i] | arr2[i];
        sum = sum.toString(2);
        answer.push(sum);
    }
    
    for (let i = 0; i < answer.length; i++) {
        for (let j = 0; j < answer[i].length; j++) {
            if (answer[i][j] === '1') str += '#';
            else if(answer[i][j] === '0') str += ' ';
        }
        if (answer[i].length !== n) {
           for (let k = 0; k < n - answer[i].length; k++) {
                str = ' ' + str
            }
        }
        result.push(str);
        str = '';
    }
   return result;
}

해설을  하자면   먼저  접근 방법부터 이야기 해보겠다  

 

 

 

 

그림을  보면   문제는  결국  전체  지도 모습을 구하는게  정답이다  

전체  지도를 각 줄마다  표현하면   

 

                                                                   11111

                                                                   10101

                                                                   11101

                                                                   10011

                                                                   11111

                

어떻게  이런 결과값이  나올까?    천천히  살펴보자  

 

 

첫번째  지도의  첫번째 줄 지도의 모습과  암호화된 배열이다 

 

두번째 지도의  첫번째 줄 지도의 모습과 암호화된 배열이다 

 

전체 지도의  첫번째 줄이다    그리고 암호화된 배열은 1111이다   이걸 보면  떠오르는 게 하나있다

01001과 11110 그리고 결과 값이 11111   바로 비트연산이다   

 

https://ko.wikipedia.org/wiki/%EB%B9%84%ED%8A%B8_%EC%97%B0%EC%82%B0

 

비트 연산 - 위키백과, 우리 모두의 백과사전

 

ko.wikipedia.org

필자는  비트연산을 이용해서  문제를 해결했다  이걸 떠올렸다면  그 뒤부턴  일사천리다  

 

for (let i = 0; i < arr1.length; i++) {
        sum = arr1[i] | arr2[i];
        sum = sum.toString(2);
        answer.push(sum);
    }

for문을 이용해서  두 배열의  값을  비트연산을 진행해서  새로운 배열에  삽입해줬다 

 

다음으로  문제의  지시대로  1은 '#'로  0은  공백처리를 한다   그다음  마지막 관문이  하나가 더남는다  

 

문제를 살펴보면  지도의 한변의 길이가  주어진다  이 길이는  즉  지도의 각 칸의  개수와도 연결이 된다  

결국  결과값의  자릿수들을  주어지는 변의 길이에 따라  맞춰주어야 한다는 것이다  

 

if (answer[i].length !== n) {
       for (let k = 0; k < n - answer[i].length; k++) {
           str = ' ' + str;
        }
 }

따라서  이렇게 조건문을  넣어준다   사실  이 조건문은  굳이 필요하지 않다   

 

https://developer.mozilla.org/ko/docs/Web/JavaScript/Reference/Global_Objects/String/padStart

 

String.prototype.padStart() - JavaScript | MDN

padStart() 메서드는 현재 문자열의 시작을 다른 문자열로 채워, 주어진 길이를 만족하는 새로운 문자열을 반환합니다. 채워넣기는 대상 문자열의 시작(좌측)부터 적용됩니다.

developer.mozilla.org

 

padStart()메서드를 이용하면  빼줄수 있다  ㅎㅎㅎ

 

def solution(n, arr1, arr2):
    result = []
    arr = list(map(lambda x : bin(x[0] | x[1])[2:], zip(arr1, arr2)))
    arr = list(map(lambda x : '0' * (n - len(x)) + x, arr))
    
    for a in arr :
        a =   a.replace('1', '#')
        a =   a.replace('0', ' ')
        result.append(a)
    return result

파이썬 풀이다  정말 신세계다  lambda  map 함수  그리고  zip()을 이용해서  저렇게  간단하게 처리가 가능하다