[67256번] 키패드 누르기
✔️ 문제 설명
스마트폰 전화 키패드의 각 칸에 다음과 같이 숫자들이 적혀 있습니다.
이 전화 키패드에서 왼손과 오른손의 엄지손가락만을 이용해서 숫자만을 입력하려고 합니다.
맨 처음 왼손 엄지손가락은 * 키패드에 오른손 엄지손가락은 # 키패드 위치에서 시작하며, 엄지손가락을 사용하는 규칙은 다음과 같습니다.
- 엄지손가락은 상하좌우 4가지 방향으로만 이동할 수 있으며 키패드 이동 한 칸은 거리로 1에 해당합니다.
- 왼쪽 열의 3개의 숫자 1, 4, 7을 입력할 때는 왼손 엄지손가락을 사용합니다.
- 오른쪽 열의 3개의 숫자 3, 6, 9를 입력할 때는 오른손 엄지손가락을 사용합니다.
- 가운데 열의 4개의 숫자 2, 5, 8, 0을 입력할 때는 두 엄지손가락의 현재 키패드의 위치에서 더 가까운 엄지손가락을 사용합니다.
4-1. 만약 두 엄지손가락의 거리가 같다면, 오른손잡이는 오른손 엄지손가락, 왼손잡이는 왼손 엄지손가락을 사용합니다.
순서대로 누를 번호가 담긴 배열 numbers, 왼손잡이인지 오른손잡이인 지를 나타내는 문자열 hand가 매개변수로 주어질 때, 각 번호를 누른 엄지손가락이 왼손인 지 오른손인 지를 나타내는 연속된 문자열 형태로 return 하도록 solution 함수를 완성해주세요.
✔️ 입출력 예

입출력 예 #1
순서대로 눌러야 할 번호가 [1, 3, 4, 5, 8, 2, 1, 4, 5, 9, 5]이고, 오른손잡이입니다.

따라서 "LRLLLRLLRRL"를 return 합니다.
입출력 예 #2
왼손잡이가 [7, 0, 8, 2, 8, 3, 1, 5, 7, 6, 2]를 순서대로 누르면 사용한 손은 "LRLLRRLLLRR"이 됩니다.
입출력 예 #3
오른손잡이가 [1, 2, 3, 4, 5, 6, 7, 8, 9, 0]를 순서대로 누르면 사용한 손은 "LLRLLRLLRL"이 됩니다.
✔️ 제한 사항
- numbers 배열의 크기는 1 이상 1,000 이하입니다.
- numbers 배열 원소의 값은 0 이상 9 이하인 정수입니다.
- hand는 "left" 또는 "right" 입니다.
- "left"는 왼손잡이, "right"는 오른손잡이를 의미합니다.
- 왼손 엄지손가락을 사용한 경우는 L, 오른손 엄지손가락을 사용한 경우는 R을 순서대로 이어붙여 문자열 형태로 return 해주세요.
✔️ 코드 구상
키패드를 그대로 이차원 배열로 만들어야겠다는 생각이 먼저 떠올랐다.
그리고 손가락의 위치를 x, y 좌표로 하는 int[]을 만들어 숫자 하나를 누를 때마다 이동시키기로 했다.
주어지는 숫자는 한 번만 순회하면 되기 때문에 iterator를 사용하면 될 것이고 반환 또한 int기 때문에 answer에 +해주면 된다.
iter를 순회하는 동안 로직은 키패드를 왼쪽, 가운데, 오른쪽으로 나눠 배열로 담은 후 포함하는지를 if문으로 구분한다.
if문 {}내에서는 answer에 L or R을 덧붙이고 손가락 위치를 이동시킨다.
✔️ 1차 코드 (실패)
- 이상하다.. 분명 인텔리제이에서 출력된건 테스트 케이스를 통과했는데 프로그래머스에서는 다르게 출력된다고 한다..ㅜㅜ
import java.util.*;
public class Solution {
public String solution(int[] numbers, String hand) {
String answer = "";
int[][] map = { {1, 4, 7},
{2, 5, 8},
{3, 6, 9} };
int[] leftHeader = {0, 3};
int[] rightHeader = {2, 3};
Iterator iter = Arrays.stream(numbers).iterator();
while(iter.hasNext()) {
int num = (int) iter.next();
if(Arrays.stream(map[0]).anyMatch(i -> i == num) == true) {
answer += "L";
leftHeader = new int[] {0, Arrays.binarySearch(map[0], num)};
} else if(Arrays.stream(map[2]).anyMatch(i -> i == num) == true) {
answer += "R";
rightHeader = new int[] {2, Arrays.binarySearch(map[2], num)};
} else {
int[] middleHeader;
if(num == 0) {
middleHeader = new int[] {1, 3};
} else {
middleHeader = new int[] {1, Arrays.binarySearch(map[1], num)};
}
int distanceL = Math.abs(leftHeader[0] - middleHeader[0]) + Math.abs(leftHeader[1] - middleHeader[1]);
int distanceR = Math.abs(rightHeader[0] - middleHeader[0]) + Math.abs(rightHeader[1] - middleHeader[1]);
if(distanceL < distanceR) {
answer += "L";
leftHeader = middleHeader;
} else if(distanceL > distanceR) {
answer += "R";
rightHeader = middleHeader;
} else {
answer += hand.toUpperCase().charAt(0);
if(hand == "left") {
leftHeader = middleHeader;
} else {
rightHeader = middleHeader;
}
}
}
}
return answer;
}
}
✔️ 2차 코드 (성공)
- 디버깅하며 코드 한줄한줄 따라가며 확인해도 문제점을 찾지 못했고.. 엄청난 삽질 끝에 한가지 실수를 발견했다
- String엔 ==가 아닌 equals를 꼭 쓰자!!!!! 절대로 잊혀지지 않을 것 같다
import java.util.*;
public class Solution {
public String solution(int[] numbers, String hand) {
String answer = "";
int[][] map = { {1, 4, 7},
{2, 5, 8},
{3, 6, 9} };
int[] leftHeader = {0, 3};
int[] rightHeader = {2, 3};
Iterator iter = Arrays.stream(numbers).iterator();
while(iter.hasNext()) {
int num = (int) iter.next();
if(Arrays.stream(map[0]).anyMatch(i -> i == num) == true) {
answer += "L";
leftHeader = new int[] {0, Arrays.binarySearch(map[0], num)};
} else if(Arrays.stream(map[2]).anyMatch(i -> i == num) == true) {
answer += "R";
rightHeader = new int[] {2, Arrays.binarySearch(map[2], num)};
} else {
int[] middleHeader;
if(num == 0) {
middleHeader = new int[] {1, 3};
} else {
middleHeader = new int[] {1, Arrays.binarySearch(map[1], num)};
}
int distanceL = Math.abs(leftHeader[0] - middleHeader[0]) + Math.abs(leftHeader[1] - middleHeader[1]);
int distanceR = Math.abs(rightHeader[0] - middleHeader[0]) + Math.abs(rightHeader[1] - middleHeader[1]);
if(distanceL < distanceR) {
answer += "L";
leftHeader = middleHeader;
} else if(distanceL > distanceR) {
answer += "R";
rightHeader = middleHeader;
} else {
answer += hand.toUpperCase().charAt(0);
if(hand.equals("left")) { //String은 ==가 아닌 꼭 equals를 사용하자!!!!!
leftHeader = middleHeader;
} else {
rightHeader = middleHeader;
}
}
}
}
return answer;
}
}