오.. 풀어서 한 번에 맞춰버렸다..! 인덱스를 한 번 더 디버깅하고 점검하고 제출하니 바로 통과해서 아주 뿌듯했다.
initParams()
: 인자들을 초기화한다.
board
는 String 배열에서 char 2차원 배열로 변환했다. 블록들을 움직일 때 훨씬 편리하기 때문이다.isPop
은 삭제할 블록을 체크하는 데에 사용되는 배열이다.countPopBlocks()
: pop을 할 수 있는 동안 while문을 반복하면서 삭제한 블록 개수인 count
를 증가시킨다.
a. isPopAvailable()
: board
를 인덱스 순서대로 돌면서 isSquareSameBlock()
인지 검사한다.
isPop
배열에 삭제할 인덱스를 체크하고 true를 리턴한다.isSquareSameBlock()
: NULL
이 아닌 서로 같은 블록이 2x2로 모여있는지 체크한다.b. popAvailableBlocks()
: board
에 해당 블록 인덱스를 NULL
처리하고 count
를 증가시킨다.
realignBoard()
: 터뜨린 블록 자리에 위에 있는 블록을 아래로 떨어뜨린다.findNextNotNullIndex()
: i
번째 row보다 위에 아래로 떨어뜨릴 수 있는 블록이 있는지 확인하고 인덱스를 알아낸다.moveBlocksToBottom()
: notNullIndex
의 블록을 i
번째 row로 떨어뜨린다.class Solution {
private static final char NULL = '-';
private static final int[] dy = {0, 0, 1, 1};
private static final int[] dx = {0, 1, 0, 1};
private int y;
private int x;
private char[][] board;
private boolean[][] isPop;
public int solution(int m, int n, String[] b) {
initParams(m, n, b);
return countPopBlocks();
}
private void initParams(int m, int n, String[] b){
y = m;
x = n;
parseBoard(b);
isPop = new boolean[y][x];
}
private void parseBoard(String[] b) {
board = new char[y][x];
for (int i = 0; i < y; i++)
for (int j = 0; j < x; j++)
board[i][j] = b[y - i - 1].charAt(j);
}
private int countPopBlocks() {
int count = 0;
while (isPopAvailable()) {
count += popAvailableBlocks();
isPop = new boolean[y][x];
}
return count;
}
private boolean isPopAvailable() {
boolean flag = false;
for (int i = 0; i < y - 1; i++)
for (int j = 0; j < x - 1; j++)
if (isSquareSameBlock(i, j)) {
checkBlocksToPop(i, j);
flag = true;
}
return flag;
}
private boolean isSquareSameBlock(int i, int j) {
char now, before = NULL;
for (int k = 0; k < 4; k++) {
now = board[i + dy[k]][j + dx[k]];
if (before != NULL && now != before) return false;
before = now;
}
return before != NULL;
}
private void checkBlocksToPop(int i, int j) {
for (int k = 0; k < 4; k++)
isPop[i + dy[k]][j + dx[k]] = true;
}
private int popAvailableBlocks() {
int count = 0;
for (int i = 0; i < y; i++)
for (int j = 0; j < x; j++)
if (isPop[i][j]) {
board[i][j] = NULL;
count++;
}
realignBoard();
return count;
}
private void realignBoard() {
for (int i = 0; i < y; i++) {
for (int j = 0; j < x; j++) {
if (board[i][j] == NULL) {
int notNullIndex = findNextNotNullIndex(i, j);
if (notNullIndex != i) moveBlocksToBottom(i, notNullIndex, j);
}
}
}
}
private void moveBlocksToBottom(int i, int notNullIndex, int j) {
board[i][j] = board[notNullIndex][j];
board[notNullIndex][j] = NULL;
}
private int findNextNotNullIndex(int i, int j) {
int notNullIndex = i;
while (notNullIndex >= 0 && notNullIndex + 1 < y && board[notNullIndex][j] == NULL)
notNullIndex++;
return notNullIndex;
}
}