문제 설명
지나다니는 길을 'O', 장애물을 'X'로 나타낸 직사각형 격자 모양의 공원에서 로봇 강아지가 산책을 하려합니다. 산책은 로봇 강아지에 미리 입력된 명령에 따라 진행하며, 명령은 다음과 같은 형식으로 주어집니다.
["방향 거리", "방향 거리" … ]
예를 들어 "E 5"는 로봇 강아지가 현재 위치에서 동쪽으로 5칸 이동했다는 의미입니다. 로봇 강아지는 명령을 수행하기 전에 다음 두 가지를 먼저 확인합니다.
주어진 방향으로 이동할 때 공원을 벗어나는지 확인합니다.
주어진 방향으로 이동 중 장애물을 만나는지 확인합니다.
위 두 가지중 어느 하나라도 해당된다면, 로봇 강아지는 해당 명령을 무시하고 다음 명령을 수행합니다.
공원의 가로 길이가 W, 세로 길이가 H라고 할 때, 공원의 좌측 상단의 좌표는 (0, 0), 우측 하단의 좌표는 (H - 1, W - 1) 입니다.
공원을 나타내는 문자열 배열 park, 로봇 강아지가 수행할 명령이 담긴 문자열 배열 routes가 매개변수로 주어질 때, 로봇 강아지가 모든 명령을 수행 후 놓인 위치를 [세로 방향 좌표, 가로 방향 좌표] 순으로 배열에 담아 return 하도록 solution 함수를 완성해주세요.
먼저 좌표를 이동하며 올바른 이동인지 확인하는 메소드들을 만들었다.
public class Test_78_walkInThePark {
public int[] solution(String[] park, String[] routes) {
int[] answer = new int[2];
// 출발지점 찾기
int yLocation = 0;
int xLocation = 0;
boolean found = false;
for (int i = 0; i < park.length && !found; i++) {
for (int j = 0; j < park[0].length(); j++) {
if (park[i].charAt(j) == 'S') {
yLocation = i;
xLocation = j;
found = true;
break;
}
}
}
// 명령 수행
for (String route : routes) {
char direction = route.charAt(0);
int numOfStep = Integer.parseInt(route.substring(2)); // 이동할 거리
switch (direction) {
case 'N' -> yLocation = goN(park, numOfStep, yLocation, xLocation);
case 'S' -> yLocation = goS(park, numOfStep, yLocation, xLocation);
case 'W' -> xLocation = goW(park, numOfStep, yLocation, xLocation);
case 'E' -> xLocation = goE(park, numOfStep, yLocation, xLocation);
}
}
answer[0] = yLocation;
answer[1] = xLocation;
return answer;
}
// 북쪽으로 이동
private int goN(String[] park, int numOfStep, int yLocation, int xLocation) {
for (int i = 1; i <= numOfStep; i++) {
if (yLocation - i >= 0 && (park[yLocation - i].charAt(xLocation) == 'O'
|| park[yLocation - i].charAt(xLocation) == 'S')) {
yLocation--;
} else {
break;
}
}
return yLocation;
}
// 남쪽으로 이동
private int goS(String[] park, int numOfStep, int yLocation, int xLocation) {
for (int i = 1; i <= numOfStep; i++) {
if (yLocation + i < park.length && (park[yLocation + i].charAt(xLocation) == 'O'
|| park[yLocation + i].charAt(xLocation) == 'S')) {
yLocation++;
} else {
break;
}
}
return yLocation;
}
// 서쪽으로 이동
private int goW(String[] park, int numOfStep, int yLocation, int xLocation) {
for (int i = 1; i <= numOfStep; i++) {
if (xLocation - i >= 0 && (park[yLocation].charAt(xLocation - i) == 'O'
|| park[yLocation].charAt(xLocation - i) == 'S')) {
xLocation--;
} else {
break;
}
}
return xLocation;
}
// 동쪽으로 이동
private int goE(String[] park, int numOfStep, int yLocation, int xLocation) {
for (int i = 1; i <= numOfStep; i++) {
if (xLocation + i < park[0].length() && (park[yLocation].charAt(xLocation + i) == 'O'
|| park[yLocation].charAt(xLocation + i) == 'S')) {
xLocation++;
} else {
break;
}
}
return xLocation;
}
public static void main(String[] args) {
Test_78_walkInThePark sol = new Test_78_walkInThePark();
// 예시 1
String[] park = {"SOO","OOO","OOO"};
String[] routes = {"E 2","S 2","W 1"}; // 결과값 : [2, 1]
// 예시 2
// String[] park = {"SOO","OXX","OOO"};
// String[] routes = {"E 2","S 2","W 1"}; // 결과값 : [0, 1]
// 예시 3
// String[] park = {"OSO", "OOO", "OXO", "OOO"};
// String[] routes = {"E 2", "S 3", "W 1"}; // 결과값 : [0, 0]
System.out.println(Arrays.toString(sol.solution(park, routes)));
}
}
이 코드의 결과값으로 [2, 1]가 나와야하지만
[1, 0]가 나왔다.
아주 어이없는 이유로
if (xLocation + i < park[0].length() && (park[yLocation].charAt(xLocation + i) == 'O'
|| park[yLocation].charAt(xLocation + i) == 'S')) {
xLocation++;
}
조건문 안에 이동이 가능하다면, x의 좌표를 증가시키게되는데
i가 증가하는 반복문에서 이미 증가된 x 좌표에 i를 더하게되어
위치가 일치하지 못하게되었다.
// 동쪽으로 이동
private int goE(String[] park, int numOfStep, int yLocation, int xLocation) {
int startPoint = xLocation;
for (int i = 1; i <= numOfStep; i++) {
if (startPoint + i < park[0].length() && (park[yLocation].charAt(startPoint + i) == 'O'
|| park[yLocation].charAt(startPoint + i) == 'S')) {
xLocation++;
} else {
break;
}
}
return xLocation;
}
해당 조건문의 비교대상을 startPoint라는 변수로 잡아서 해결하였는데...
예시 3번에서 [0, 0]이 나와야할게 [3, 1]이 나왔다.
// 동쪽으로 이동
private int goE(String[] park, int numOfStep, int yLocation, int xLocation) {
int startPoint = xLocation;
for (int i = 1; i <= numOfStep; i++) {
if (startPoint + i < park[0].length() && (park[yLocation].charAt(startPoint + i) == 'O'
|| park[yLocation].charAt(startPoint + i) == 'S')) {
xLocation++;
} else {
return startPoint;
}
}
return xLocation;
}
동쪽으로 2번 이동할 경우
1번은 이동이 가능하지만, 2번째에서 이동이 불가능할 때
이미 1번째 이동에서 xLocation이 증가하여 2번째에 이동이 불가능하여도 이미 1증가한 xLocation을 반환하여 오답이 나왔던 것이었다.
진짜 정말 별거 아닌 문제였는데
쓸데없는데에서 문제를 찾느라 생각보다 시간이 오래걸렸다.