[프로그래머스] 대충 만든 자판

Hyun·2023년 5월 22일
0

프로그래머스

목록 보기
6/32

문제 설명

휴대폰 자판은 키 하나에 문자 여러개 할당된다.
=> 해당 키를 연속해서 누르면 연속해서 누른 횟수의 누적값에 따라 문자가 바뀐다.
ex) 1번키에 "A","B","C" 가 할당되어 있으면
1번 누름 ->"A"
2번 누름-> "B"
3번 누름 -> "C"

제한 사항
키 갯수 1~100개
특정 키에 할당된 문자는 무작위
같은 문자가 자판 전체(여러 키)에 여러번 할당된 경우 존재
아예 할당x인 문자도 존재 => 몇몇 문자열은 작성 못할 수도 있음

입출력 예
keymap targets result
["ABACD", "BCEFD"]["ABCD","AABB"] [9, 4]["AA"] ["B"][-1]
["AGZ", "BSSS"]["ASA","BGZ"] [4, 6]

특정문자열을 구현하기 위해 키를 최소 몇 번 눌러야하는지를 구하라.

문제 풀이

방법 => 딕셔너리 이용

  1. 중복을 제외한 "문자": keymap 의 원소값(문자열) 해당 문자가 속한 가장 앞부분의 index 형식으로 딕셔너리를 만듦
  2. 중복이면 딕셔너리에 해당 문자(key)의 value에 속한 값이 더 크면 현재 조사하고 있는 문자열의 위치(index) + 1로 교체함
  3. 중복이 아니면 "문자": 현재 조사하고 있는 문자열의 위치(index) + 1 로 교체함
  4. targets 배열을 돌면서 해당 문자열을 구현할 최소 키 누르는 횟수를 정리해놨던 딕셔너리를 이용해 구함, 딕셔너리에 해당 문자열 없으면 결과 배열에 -1추가하고 다음 문자열로 넘어감

기타 풀이 특징

  • +1 을 해주는 이유는 해당 문자의 인덱스 + 1번 연속해서 눌러야 해당 문자가 나오기 때문이다.
    ex) index 가 0인 문자는 (0 + 1)번 키를 연속해서 눌러야 한다.
def solution(keymap, targets):
    answer = []
    char_arr = {}
    #문자열을 돌면서 각 문자의 최소 index를 찾음
    for arr in keymap:
        for index_char, char in enumerate(arr):
            #딕셔너리에 해당 문자가 key값으로 있으면 => value 대소 비교해서 value 변경시킴
            if(char in char_arr):
                if(index_char < char_arr[char]):
                    char_arr[char] = index_char + 1
            #딕셔너리에 해당 문자 key값으로 없으면 => 딕셔너리에 그대로 추가
            else:
                char_arr[char] = index_char + 1

    print(char_arr)
    #타켓의 문자열을 돌면서 몇번 눌러야 하는지 계산
    for string in targets:
        count, notExist = 0, False
        for char in string:
            #딕셔너리에 없는 문자 => -1 삽입 & 다음 문자열로 넘어감
            if(not char in char_arr): 
                answer.append(-1)
                notExist = True
                break
            count = count + char_arr[char]
        if(not notExist): answer.append(count)

리팩토링

개선 내용

  • char_dict -> hs
  • notExist -> flag
  • 내장 함수 이용해 간소화

코드 개선
개선 전

 if(char in char_arr):
                if(index_char < char_arr[char]):
                    char_arr[char] = index_char + 1

개선 후(min 함수 사용)

if(char in hs):
                hs[char] = min(hs[char], index + 1)

전체 개선 코드

def solution(keymap, targets):
    answer = []
    hs = {}
    for arr in keymap:
        for index, char in enumerate(arr):
            if(char in hs):
                hs[char] = min(hs[char], index + 1)
            else:
                hs[char] = index + 1

    for string in targets:
        count, flag = 0, False
        for char in string:
            if(not char in hs): 
                answer.append(-1)
                flag = True
                break
            count = count + hs[char]
        if(not flag): answer.append(count)
            
    
    return answer

후기)
리팩토링하니 훨씬 깔끔해졌다. 가독성을 해치지 않는 선에서 리팩토링을 생활화하자.

profile
better than yesterday

0개의 댓글