문제 링크 : https://www.acmicpc.net/problem/17276
이 문제는 배열 돌리기 1을 먼저 푼 후 접근하였다.
[BOJ] 배열 돌리기 1 16926.JAVA
문제 링크 : https://www.acmicpc.net/problem/16926 처음 시도에는 배열의 외각을 돌리는 거 말고는 해결하지 못하였다. 그래서 배열 돌리기의 기초가 되는 백준 달팽이 문제를 풀면서 기초를 다지고 다시
nkt-docs.tistory.com
두 문제의 차이점은 기본 로직은 동일 하나 어떤 값을 돌릴 것인지의 차이가 있다.
문제의 핵심
1. 2차원 정수 배열의 크기는 홀수 X 홀수이기 때문에 항상 가운데 지점이 존재한다.
- 2차원 정수 배열의 크기는 홀수 X 홀수이기 때문에 항상 가운데 지점이 존재한다.
- 배열의 첫 번째 트랙부터 가운데 지점까지(N/2) 반목문을 실행한다.
- 가운데 지점에서 몇 번째 트랙인지를 체크하여 배열의 어떤 값을 돌릴지 구현한다.
- N이 5일 때, 첫 번째 트랙(가장 외곽)은 N/2 - x(행)을 계산하여 돌릴 값을 선택한다.
- 각도의 값이 0보다 작으면 +8을 하여 항상 오른쪽 방향으로만 돌아가도록 구현한다.
- -45도일 경우, -45/45 == -1이므로 +8을 하여 7번 만큼 오른쪽으로 돌렸을 때 왼쪽으로 1번(-1) 돌린 위치가 된다.
- 항상 오른쪽으로 배열을 돌리지만 실제로는 왼쪽(0,0 기준 하, 좌, 상, 우)으로 돌면서 값을 이동 시킨다.
아래와 같이 소스를 공유한다.
public class 배열돌리기 {
public static int N;
public static int[][] map;
public static void main(String[] args) throws IOException {
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(System.out));
int t = Integer.parseInt(br.readLine());
for(int z = 0; z < t; z++) {
String[] str = br.readLine().split(" ");
N = Integer.parseInt(str[0]);
int c = Integer.parseInt(str[1]);
map = new int[N][N];
for (int i = 0; i < N; i++) {
StringTokenizer st = new StringTokenizer(br.readLine(), " ");
for (int j = 0; j < N; j++) {
map[i][j] = Integer.parseInt(st.nextToken());
}
}
if(c%360 != 0 ) {
move(c/45);
}
StringBuilder sb = new StringBuilder();
for(int i = 0; i < N; i++) {
for(int j = 0; j < N; j++) {
// 움직인 배열을 보기 좋게 출력
// sb.append(map[i][j] <= 9 ? "0"+map[i][j]:map[i][j]).append(" ");
sb.append(map[i][j]).append(" ");
}
sb.append("\n");
}
bw.write(sb.toString());
}
bw.flush();
bw.close();
}
public static void move(int c) {
int[] dx = {1, 0, -1, 0};
int[] dy = {0, 1, 0, -1};
// 가운데 지점
int p = N/2;
if(c < 0) c += 8;
for(int i = 0; i < c; i ++) {
for(int j = 0; j < N/2; j++) {
int x = j;
int y = j;
int idx = 0;
int temp = map[x][y];
while(idx < 4) {
int mx = dx[idx]*(p-j);
int my = dy[idx]*(p-j);
int xx = x + mx, yy = y + my;
if(xx < j || yy < j || xx > N-j-1 || yy > N-j-1) {
idx++;
}else {
map[x][y] = map[xx][yy];
x = xx;
y = yy;
}
}
// 마지막 위치에 첫번째 값을 할당
map[x][y+(p-j)] = temp;
}
}
}
}
'알고리즘 > 문제풀이 - 백준온라인저지' 카테고리의 다른 글
[BOJ 분할정복] 종이의 개수 1780.JAVA (0) | 2021.05.13 |
---|---|
[BOJ 분할정복] 색종이 만들기 2630.JAVA (0) | 2021.05.13 |
[BOJ] 빗물 14719.JAVA (0) | 2021.04.14 |
[BOJ] 배열 돌리기 1 16926.JAVA (0) | 2021.04.12 |
[BOJ] 달팽이 1913.JAVA (0) | 2021.04.11 |