https://swexpertacademy.com/main/code/problem/problemDetail.do?contestProbId=AV5PobmqAPoDFAUq
문제 접근
머리론 되게 쉬워보이는데 일일이 구현하는 건 생각보다 시간이 걸렸다.
움직이는 방향을 boolean 타입으로 지정해서 어디로 움직일지 방향을 잡아준다.
달팽이는 2차원 배열 공간을 움직이며 움직이는 공간에 1씩 증가된 값을 저장시켜준다.
달팽이가 다음 경로로 갈 수 없는 경우는 크기를 벗어나게 될 때와 값이 저장되어 있는 경우다. → int형 배열은 초기값을 지정해주지 않으면 default로 0이 들어가있다.
4방향으로 움직이면서 다음 경로로 갈 수 없는 경우의 수를 다 만들어주었다.
해당 방향으로 움직일 때(true)만 갈 수 없는 경우를 탐색하도록 하였음 → 해당 방향 아닌데도 조건을 만족한 다른 방향이 돌아가는 경우가 있었기 때문
++ 이제보니 값 저장할 변수로 number를 안쓰고 반복문에서 k를 활용해도 되겠더라
import java.util.*;
import java.io.*;
public class Solution {
public static void main(String[] args) throws IOException {
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
int T = Integer.parseInt(br.readLine());
for(int t=0; t<T; t++) {
int N = Integer.parseInt(br.readLine());
int[][] snail = new int[N][N];
int number = 1;
int X = 0;
int Y = 0;
snail[Y][X] = number; // 시작
boolean XPlusMove = true;
boolean XMinusMove = false;
boolean YPlusMove = false;
boolean YMinusMove = false;
for(int k=1; k<N*N; k++) {
if(XPlusMove) X++;
else if(XMinusMove) X--;
else if(YPlusMove) Y++;
else if(YMinusMove) Y--;
// 이동 방향이 true일 때만 장애물 탐색 작동시키기
if(XPlusMove == true) {
if(X >= snail[0].length || (X < snail[0].length && snail[Y][X] != 0)) { // 오른쪽 이동 중 크기를 벗어나거나 경로에 값이 있다면
X--; // 범위를 벗어나니 다시 감소
Y++; // 방향 전환
XPlusMove = false;
YPlusMove = true;
}
}
if(YPlusMove == true) {
if(Y >= snail.length || (Y < snail.length && snail[Y][X] != 0)) { // 아래로 이동 중 크기를 벗어나거나 경로에 값이 없다면
Y--; // 범위를 벗어나니 다시 감소
X--; // 방향 전환
YPlusMove = false;
XMinusMove = true;
}
}
if(XMinusMove == true) {
if(X < 0 || (X >= 0 && snail[Y][X] !=0)) { // 왼쪽으로 이동 중 크기를 벗어나거나 경로에 값이 없다면
X++; // 범위를 벗어나니 다시 감소
Y--; // 방향 전환
XMinusMove = false;
YMinusMove = true;
}
}
if(YMinusMove == true) {
if(YMinusMove && Y < 0 || (Y >=0 && snail[Y][X] !=0)) {// 위쪽으로 이동 중 크기를 벗어나거나 경로에 값이 없다면
Y++; // 범위를 벗어나니 다시 감소
X++; // 방향 전환
YMinusMove = false;
XPlusMove = true;
}
}
snail[Y][X] = ++number;
}
System.out.println("#"+(t+1));
for(int i=0; i<snail.length; i++) {
for(int j=0; j<snail[0].length; j++) {
System.out.print(snail[i][j] + " ");
}
System.out.println();
}
}
}
}
다른 사람 풀이
Arrays.fill() 은 해당 배열을 전부 값으로 저장하는 메서드
1차원 배열 → Arrays.fill(배열명, 저장할 값) / 2차원 배열 → Arrays.fill(배열명[인덱스], 저장할 값)
예전에도 이런 문제 풀이를 볼 때
int dx[] = {0,1,0,-1};
int dy[] = {1,0,-1,0};
이런 형태를 본 적이 있는데 이게 이런 유형의 문제를 푸는 정형화된 방법인가?
이 분은 지나갔던 경로를 boolean 타입으로, 방향 전환을 한 줄로 처리하였다.
public static void main(String[] args) throws NumberFormatException, IOException {
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
int Tc = Integer.parseInt(br.readLine());
//오,하,좌,상 순서로 방향배열 만들기
int dx[] = {0,1,0,-1};
int dy[] = {1,0,-1,0};
for (int tc = 1; tc <= Tc; tc++) {
int N = Integer.parseInt(br.readLine());
//N*N 크기의 2차원배열 생성
int arr[][] = new int[N][N];
boolean visit[][] = new boolean[N][N];
for (int i = 0; i < N; i++) {
Arrays.fill(visit[i], false);
}
//빈 칸을 다 채울때까지
int dir = 0;
int x = 0;
int y = 0;
for (int i = 1 ; i <= N*N; i++) {
//System.out.println(x + "," + y + " : "+ i);
//정수 입력 , 방향표시
arr[x][y] = i; // 값 넣기
visit[x][y] = true; // 지나간 경로 표시
//다음칸 갈수있는지 확인하기
int nextx = x + dx[dir];
int nexty = y + dy[dir];
//방향바꾸기 조건 : 1.범위를 넘어갈때 , 2. 다음칸이 채워져있을때
if(nextx >=N || nexty >=N || nextx < 0 || nexty < 0 || visit[nextx][nexty] == true ) {
dir = (dir+1)%4; //방향전환
}
//다음칸 지정
x = x + dx[dir];
y = y + dy[dir];
}
//출력하기
System.out.println("#" + tc );
for (int i = 0; i < N; i++) {
for (int j = 0; j < N; j++) {
System.out.print(arr[i][j] + " ");
}
System.out.println();
}
}//Tc
}
'알고리즘 > SWEA' 카테고리의 다른 글
[SWEA / 초심자의 회문 검사 / JAVA] (0) | 2023.04.25 |
---|---|
[SWEA / 스도쿠 검증 / JAVA] (0) | 2023.04.07 |
[SWEA / 간단한 압축 풀기 / JAVA] (0) | 2023.04.04 |
[SWEA / 조교의 성적 매기기 / JAVA] (0) | 2023.03.30 |
[SWEA / 중간 평균값 구하기 / JAVA] (0) | 2023.02.20 |
댓글