만족은 하되 안주하지는 말자

기록해야 기억한다

카테고리 없음

[JAVA] 행렬 테두리 회전하기

D36choi 2022. 2. 23. 14:36
728x90

문제

https://programmers.co.kr/learn/courses/30/lessons/77485?language=java 

 

코딩테스트 연습 - 행렬 테두리 회전하기

6 6 [[2,2,5,4],[3,3,6,6],[5,1,6,3]] [8, 10, 25] 3 3 [[1,1,2,2],[1,2,2,3],[2,1,3,2],[2,2,3,3]] [1, 1, 5, 3]

programmers.co.kr

내 풀이

import java.util.List;
import java.util.LinkedList;
import java.util.ArrayList;
import java.util.Queue;
class Solution {
    public int[] solution(int rows, int columns, int[][] queries) {
        List<Integer> answer = new ArrayList<Integer>();
        int[][] board = new int[rows + 1][columns + 1];
        
        for (int i=1; i<=rows; i++) {
            for (int j=1; j<=columns; j++) {
                board[i][j] = ((i-1) * columns + j);
            }
        }

        for(int[] query : queries) {
            answer.add(rotate(board, query));
        }
        
        return answer.stream().mapToInt(i->i).toArray();
    }
    
    private static int rotate(int[][] board, int[] query) {
        int min = 100000;
        Queue<Integer> originals = new LinkedList<>();
        int x1 = query[0];
        int y1 = query[1];
        int x2 = query[2];
        int y2 = query[3];
        
        for(int c=y1; c<=y2; c++) {
            originals.add(board[x1][c]);
        }
        for(int r=x1+1; r<=x2; r++) {
            originals.add(board[r][y2]);
        }
        for(int c=y2-1; c>=y1; --c) {
            originals.add(board[x2][c]);
        }
        for(int r=x2-1; r>=x1+1; --r) {
            originals.add(board[r][y1]);
        }

        int newValue = 0;
        for(int c=y1+1; c<=y2; c++) {
            newValue = originals.poll();
            min = Math.min(newValue,min);
            board[x1][c] = newValue;
        }
        for(int r=x1+1; r<=x2; r++) {
            newValue = originals.poll();
            min = Math.min(newValue,min);
            board[r][y2] = newValue;
        }
        for(int c=y2-1; c>=y1; --c) {
            newValue = originals.poll();
            min = Math.min(newValue,min);
            board[x2][c] = newValue;
        }
        for(int r=x2-1; r>=x1; --r) {
            newValue = originals.poll();
            min = Math.min(newValue,min);
            board[r][y1] = newValue;
        }
        
        return min;
    }
}

알게 된 것

2차원 배열의 초기화

회전 알고리즘

피드백

나는 4개의 반복문을 이용해 회전 알고리즘을 구현했지만,

다른 사람의 답변을 보니 아래와 같이 direction과 dx,dy 배열을 이용한 회전으로 하면 더 덜 지저분하게도 가능한 듯 하다.

        int[]dx={0,-1,0,1};
        int[]dy={1,0,-1,0};
        int dir=3;
        
        if(x==x2&&y==y1)dir=0;
        if(x==x2&&y==y2)dir=1;
        if(x==x1&&y==y2)dir=2;
        // ...

Dir = 3 이면, dx[dir], dy[dir] 을 더하면 x1축 -> 방향으로 진행가능하다.

 

예전에 비슷한 배열회전문제에서 위처럼 했었는데, 그새 까먹은 듯 싶다. 기억해두자.