Algorithm/백준 알고리즘
백준_2630 색종이 만들기(자바) / 재귀
미스터로즈
2021. 8. 4. 21:35
시간&메모리 제한
문제
입력&출력
문제풀이
package com.Back;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.StringTokenizer;
public class Back_2630 {
static int[][] arr;
static int ans1;
static int ans2;
public static void main(String[] args) throws NumberFormatException, IOException {
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
int N = Integer.parseInt(br.readLine());
arr = new int[N][N];
StringTokenizer st;
for (int i = 0; i < N; i++) {
st = new StringTokenizer(br.readLine());
for (int j = 0; j < N; j++) {
arr[i][j] = Integer.parseInt(st.nextToken());
}
}
int tmp = arr[0][0];
boolean flag=false;
for (int i = 0; i < N; i++) {
for (int j = 0; j < N; j++) {
if(arr[i][j]!=tmp) {
flag=true;
break;
}
}
if(flag==true)break;
}
if(flag==false&&tmp==1){
System.out.println(0);
System.out.println(1);
System.exit(0);
}else if(flag==false&&tmp==0) {
System.out.println(1);
System.out.println(0);
System.exit(0);
}
search(0, 0, N, N);
System.out.println(ans1);
System.out.println(ans2);
}
private static void search(int x, int y, int xx, int yy) {
int tmp = 0;
boolean flag = false;
tmp = arr[x][y];
for (int i = x; i < (xx+x) / 2; i++) {
for (int j = y; j < (yy+y)/2; j++) {
if(arr[i][j]!=tmp) {
search(x,y,(xx+x)/2,(yy+y)/2);
flag=true;
break;
}
}
if(flag==true)break;
}
if(flag==false&&tmp==0) {
ans1++;
}else if(flag==false&&tmp==1) {
ans2++;
}
flag=false;
tmp = arr[(xx+x)/2][y];
for (int i = (xx+x)/2; i < xx ; i++) {
for (int j = y; j < (yy+y) / 2; j++) {
if(arr[i][j]!=tmp) {
search((xx+x)/2,y,xx,(y+yy)/2);
flag=true;
break;
}
}
if(flag==true)break;
}
if(flag==false&&tmp==0) {
ans1++;
}else if(flag==false&&tmp==1) {
ans2++;
}
flag=false;
tmp = arr[x][(y+yy)/2];
for (int i = x; i < (xx+x)/2; i++) {
for (int j = (y+yy)/2; j < yy ; j++) {
if(arr[i][j]!=tmp) {
search(x,(y+yy)/2,(xx+x)/2,yy);
flag=true;
break;
}
}
if(flag==true)break;
}
if(flag==false&&tmp==0) {
ans1++;
}else if(flag==false&&tmp==1) {
ans2++;
}
flag=false;
tmp = arr[(xx+x)/2][(y+yy)/2];
for (int i = (x+xx)/2; i < xx ; i++) {
for (int j = (y+yy)/2; j < yy ; j++) {
if(arr[i][j]!=tmp) {
search((xx+x)/2,(y+yy)/2,xx,yy);
flag=true;
break;
}
}
if(flag==true)break;
}
if(flag==false&&tmp==0) {
ans1++;
}else if(flag==false&&tmp==1) {
ans2++;
}
}
}
- 재귀를 이용해서 범위가 모두 동일한지를 체크해주는 문제입니다.
- 동일하지 않은 경우 4개의 정사각형으로 잘라준 후에 다시 확인하는 로직을 짜면 됩니다.
- 아직 코드가 다듬어지지 않은 부분들이 많습니다.
- 재귀를 이용해서 위치에 대한 값을 보낼 때, 중앙 값을 안보내고 계속 절반씩 잘라서 보내는 실수로 좀 오래 걸렸던 문제입니다.