https://www.acmicpc.net/problem/2744

 

2744번: 대소문자 바꾸기

영어 소문자와 대문자로 이루어진 단어를 입력받은 뒤, 대문자는 소문자로, 소문자는 대문자로 바꾸어 출력하는 프로그램을 작성하시오.

www.acmicpc.net

 

문제를 풀기에 앞서 ASCII Code에 대해서 필요한 정보를 정리하고 넘어가자.

간단하게 char에 해당되는 정수 값이 존재한다고 생각하면 된다.

예를 들어, 문자 A의 ASCII Code 값은 65이다.

아래 테이블을 참고하자.

 

 

중요한건, 문제를 풀 때, 각 문자에 해당되는  ASCII Code 값을 알아야하는 게 아니라는 것이다.

어떻게 활용하면 되는가?

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
package String;
 
public class StringClass {
    
    public static void main(String[] args) {
        
        // ASCII Code값을 char 변수에 넣으면, 그 변수에 ASCII Code값에 해당하는 문자가 저장된다.
        char x = 65;
        System.out.println(x); // A
        
        // 문자끼리 연산이 가능 -> 문자 사이의 간격만큼 결과가 나타남
        int n = 'Z' - 'A';
        System.out.println(n); // 25 -- A는 1번째, Z는 26번째 문자니까
        
        // char와 int 사이에 연산이 가능
        System.out.println(x + 25); // 90
        
        // 문자끼리 대소비교가 가능(ASCII Code 값으로 대소비교)
        System.out.println('A' < 'Z'); // true
        
        // Casting
        // char를 int로 형변환 가능(ASCII Code 값 저장)
        System.out.println((int)x); // 65
        
        // int를 char로 형변환 가능(ASCII Code 값이 해당 int 값인 char이 반환)
        System.out.println((char)(x + 25)); // Z (ASCII Code값이 90)
    }
}
 
cs

 

이를 활용하여 간단하게 대소문자를 변환해보자.

중요한 생각은 A와 Z 사이의 간격은 a와 z 사이의 간격과 같다는 것!

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
package String;
 
public class StringClass {
    
    public static void main(String[] args) {
        
        String str = "AbCdEf";
        for (int i = 0; i < str.length(); i++) {
            // 대문자의 경우!
            if('A' <= str.charAt(i) && str.charAt(i) <= 'Z') {
//                int dist = str.charAt(i) - 'A';    // A와의 간격
                System.out.print((char)('a' + str.charAt(i) - 'A')); // a로부터 해당 간격만큼 떨어진 문자로!
            } 
            else {
                System.out.print((char)('A' + str.charAt(i) - 'a'));
            }
        }
    }
}
 
cs

 

AbCdEf가 aBcDeF로 변환됨을 알 수 있다.

 

이제 [BOJ] 2744. 대소문자 바꾸기 문제를 풀어보자.

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
import java.util.Scanner;
 
public class Main {
 
    public static void main(String[] args) {
 
        Scanner sc = new Scanner(System.in);
        String str = sc.next();
        String answer = "";
        for (int i = 0; i < str.length(); i++) {
            if ('A' <= str.charAt(i) && str.charAt(i) <= 'Z') { // 대문자라면,
                answer += (char)('a' + str.charAt(i) - 'A');
            } else { // 소문자라면,
                answer += (char)('A' + str.charAt(i) - 'a');
            }
        }
        System.out.println(answer);
    }
 
}
cs

 

 

또는,

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
import java.util.Scanner;
 
public class Main {
 
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);
        String str = sc.next();
        char[] arr = str.toCharArray();
        for (int i = 0; i < str.length(); i++) {
            char ch = str.charAt(i);
            if('A' <= ch && ch <= 'Z') {
                arr[i] = (char)('a' + ch - 'A');
            } else {
                arr[i] = (char)('A' + ch - 'a');
            }
            
        }
        
        System.out.println(arr);
    }
 
}
 
cs

 

끝.

 

'알고리즘 및 코테 > 자료구조 및 알고리즘' 카테고리의 다른 글

[String] 문자열(Java)  (0) 2023.03.22

String 클래스는 Java.lang 패키지로 제공되는 Java 문자열 클래스이다.

별도의 import 없이 사용이 가능한데, 아래와 같이 선언을 할 수 있다.

 

 

위 둘의 차이는 이후 알아보기로 하자.

String 클래스는 한 번 인스턴스가 생성되면 수정할 수 없다. (immutable object)

 

 

값의 변경은 불가능하지만, 새 String을 만들어 바꿀 수는 있다.

 

 

위 코드 중에서 char[]를 String으로 바꾸는 것에 주목해보자.

아래와 같이 2가지 방법으로 바꿀 수 있다.

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
package String;
 
public class StringClass {
 
    public static void main(String[] args) {
        String str = "ABCDFFG";
        char[] temp_arr = str.toCharArray();
        System.out.println(temp_arr); // ABCDFFG
        temp_arr[4= 'E';
//        str = new String(temp_arr);
        str = String.valueOf(temp_arr);
        System.out.println(str); // ABCDEFG
    }
 
}
 
cs

 

즉, new String(char[] array) 혹은 String.valuOf(char[] array)를 이용!

 

그리고, 두 문자열이 같은지 비교하는 메서드로 equlas 메서드가 있는데, 왜 == 로는 비교를 할 수 없는지 살펴보자.

처음 String을 선언할 때 두 가지 방법이 있다는 것과 연결되는 내용이다.

 

 

두 방법의 차이는 리터럴로 선언하느냐, 인스턴스 객체를 생성하여 선언하느냐의 차이.

그 차이는 다음과 같다.

 

 

리터럴로 선언한 경우에는 두 변수가 같은 "text" 값을 가리키고 있다.

하지만, 인스턴스로 선언한 경우에는 서로 다른 객체를 생성하고 그 안에 "test"를 참조하고 있다.

따라서 아래와 같은 결과가 나타난다.

 

 

그러므로! String을 비롯한 primitive type이 아닌 경우에는 equals 메서드로 비교를 하도록 주의하자. 결국 코딩테스트를 준비하는 과정에서는 너무 당연하지만 ==  대신 equals를 써야하는 것에 주의하는 것이 중요하니까.

 

String 클래스가 제공하는 메서드들은 다양하지만, 그중 일부를 정리하자면,

 

 

 이어서 BOJ에서 문자열 관련 문제를 풀며 추가 정리하도록 하자.

 

 

https://www.acmicpc.net/problem/1065

 

1065번: 한수

어떤 양의 정수 X의 각 자리가 등차수열을 이룬다면, 그 수를 한수라고 한다. 등차수열은 연속된 두 개의 수의 차이가 일정한 수열을 말한다. N이 주어졌을 때, 1보다 크거나 같고, N보다 작거나

www.acmicpc.net

 

이 문제를 풀면서 내가 예상하지 못한 무한루프에 빠지게 되었었다. 끝없는 고민 끝에 그 이유를 찾아냈고, 다시는 똑같은 잘못을 하지 않도록 그 이유를 기록하는 것에 목적을 두도록 한다.

 

먼저, 문제에서는 N이 1000보다 작거나 같긴 한데, 나는 좀 더 나아가서 N이 세자리수든 네자리수든 문제보다 더 큰 N이 왔을 때도 한수를 구할 수 있도록 코드를 작성해보고 싶었다.

 

먼저, 

내가 무한 루프에 빠지게 됐던 잘못된 코드를 저장해두도록 하겠다.

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
 
import java.util.Scanner;
 
public class Main {
 
    public static void main(String[] args) {
 
        Scanner sc = new Scanner(System.in);
        int N = sc.nextInt();
        int count = 0;
        for (int i = 1; i <= N; i++) {
            String iStr = i + "";
            if (iStr.length() > 2) {
                int[] arr = new int[iStr.length()];
                int m = 0;
                while (i != 0) {
                    arr[m] = i % 10;
                    i = i / 10;
                    m++;
                }
                int k = arr[1- arr[0];
                boolean b = true;
                for (int j = 1; j < arr.length; j++) {
                    if (arr[j] - arr[j - 1!= k) {
                        b = false;
                    }
                }
                if (b) {
                    count++;
                }
 
            } else {
                count++;
            }
 
        }
        System.out.println(count);
 
    }
}
cs

 

어디서 잘못됐을까?

 

while (i != 0) {
arr[m] = i % 10;
i = i / 10;
m++;
}

이 부분에서 i의 자릿수를 줄여가며 각각의 일의 자리 수를 받아 배열에 저장하는 과정에서 결과적으로 i는 늘 0이 된다는 것을 놓쳤다...

이후 다시 i++이 되어 다시 i는 1부터 for문을 돌기 시작한다. 그리고 1 ~ 99까지는 count가 되지만, 100이 됐을 때 i는 다시 0이 되어버리고, 다시 1부터 for문을 도는...무한루프..

 

그래서 i 값을 다른 변수(int n)에 저장해두어서 그 변수를 통해 while문을 돌리도록 하였다.

그 결과 코드를 작성해보면 다음과 같다.

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
 
import java.util.Scanner;
 
public class Main {
 
    public static void main(String[] args) {
 
        Scanner sc = new Scanner(System.in);
        int N = sc.nextInt();
        int count = 0;
        for (int i = 1; i <= N; i++) {
            String iStr = i + ""// 숫자가 몇자리 수인지를 파악하기 위해 문자열로 바꿔줬다.
            if (iStr.length() > 2) { // 세자리 수 이상의 경우!
                int[] arr = new int[iStr.length()]; // 자릿수 만큼의 배열의 크기를 갖는 배열 생성
                int m = 0// arr 배열의 인덱스의 역할을 하기 위한 변수 선언
                int n = i; // i값(파악하고자 하는 수)을 다른 변수에 저장해둔다.
                while (n != 0) {
                    arr[m] = n % 10// 일의 자리수를 배열에 하나씩 넣어준다.
                    n = n / 10;      // 자릿수를 줄여나가면서(예: 123 -> 12 -> 1 -> 0)
                    m++;              // 인덱스 증가시킴
                }
                int k = arr[1- arr[0]; // 등차수열을 이루는지 확인하기 위해 자릿수 사이의 차이를 하나 구해놓는다.
                boolean b = true;
                for (int j = 1; j < arr.length; j++) {
                    if (arr[j] - arr[j - 1!= k) {
                        b = false;    // 차이가 하나라도 다른게 있으면 false가 돼서 한수가 아닌 것으로 판단
                    }
                }
                if (b) { // 차이가 모두 일정하다는 것이므로 한수에 해당
                    count++;
                }
 
            } else { // 1 ~ 99 의 경우 그대로 한수가 된다.
                count++;
            }
 
        }
        System.out.println(count);
 
    }
}
cs

 

 

 

https://www.acmicpc.net/problem/4673

 

4673번: 셀프 넘버

셀프 넘버는 1949년 인도 수학자 D.R. Kaprekar가 이름 붙였다. 양의 정수 n에 대해서 d(n)을 n과 n의 각 자리수를 더하는 함수라고 정의하자. 예를 들어, d(75) = 75+7+5 = 87이다. 양의 정수 n이 주어졌을 때,

www.acmicpc.net

 

풀이부터 보면 다음과 같다.

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
public class Main {
 
    public static void main(String[] args) {
        int[] arr = new int[10000]; // { 0,0,0,0,0,0,0...}
 
        for (int i = 0; i < 10000; i++) {
            int num = d(i + 1); // 1부터 함수에 넣어본다.
 
            if (num <= 10000) { // 10000 이하의 수 중에서
                arr[num - 1= 1// 생성자를 가지고 있는 경우 그 (수-1)를 인덱스로 하여 1 입력
            }
 
        }
        for (int i = 0; i < 10000; i++) {
            if (arr[i] == 0) { // 생성자를 가지고 있지 않은 경우
                System.out.println(i + 1);
            }
        }
 
    }
 
    public static int d(int n) {
        int sum = n;
        while (n != 0) {
            sum += n % 10// 일의 자리 수를 더해준다.
            n = n / 10// 자릿수를 줄여준다.
        }
        return sum;
    }
 
}
cs

 

사용된 아이디어를 크게 2가지 경우로 나타낼 수 있다.

 

1. 어떤 수의 각각의 수를 읽는 방법

결론부터 말하자면, 어떤 수를 뒤에서부터 읽는 느낌으로 자릿수를 줄여나가며 각각의 일의자리 숫자들을 하나씩 읽는 것이다.

 위 코드에서 정의한 함수 int d(int n)에 n = 1234을 매개변수로 넣었을 때 어떻게 진행되는지 설명하면 이해가 된다.

 

n = 1234일때, 

sum의 값이 1234가 된다.

while 문에서,

sum은 1234 + 4가 된다.

이후, n은 123이 된다.( n = n / 10 부분. 1234 / 10 == 123 )

 

sum은 1234 + 4 + 3이 된다.

n은 12가 된다. ( 123 / 10 == 12 )

 

sum은 1234 + 4 + 3 + 2이 된다.

n은 1이 된다. ( 12 / 10 == 1 )

 

sum은 1234 + 4 + 3 + 2 + 1이 된다.

n은 0이 된다. ( 1 / 10 == 0 )

 

while문을 빠져나간다.

sum을 return한다.

 

 

2. 0부터든 1부터든 순차적으로 숫자들을 다루기 위해 어떤 배열의 인덱스 넘버를 활용하는 것

int[] arr = new int[10000]; 에서 배열 arr 에는 10000개의 칸이 존재하고 각 칸에는 0이 존재한다.

이때, 인덱스 넘버는 0부터 9999이다.

1부터 10000의 수들을 함수에 매개변수로 넣어주면서 판단하는 과정이므로

1을 넣었을 때 그 판단 결과는 인덱스 넘버 0에 넣어줘야 한다.

그 부분이 위 코드에서

if (num <= 10000) { // 10000 이하의 수 중에서
arr[num - 1] = 1; // 생성자를 가지고 있는 경우 그 (수-1)를 인덱스로 하여 1 입력
}

이다. ( num - 1에 주목하자. )

 

다시 수들을 출력할 때는 조건에 맞는 인덱스 넘버들을 출력!

 

 

 

!!!!!!!!!!!!!!인덱스의 중요성!!!!!!!!!!!!!!

 

 

 

 

 

'알고리즘 및 코테 > 백준' 카테고리의 다른 글

백준 1065번. 한수 (Java)  (0) 2023.02.17
백준 1110번: 더하기 사이클(Java)  (0) 2023.01.18

<문제>

사용자로부터 n개의 정수를 입력받는다. 정수가 하나씩 입력될 때마다 현재까지 입력된 정수들을 오름차순으로 정렬하여 출력하라.

 

<Solution 1>

새로 정수를 입력받을 때마다 배열 전체에 대해서 정렬을 하는 방법(버블 정렬)

비효율적인 부분이 존재하지만, 직관적이다.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
import java.util.Scanner;
 
public class Main {
 
    public static void main(String[] args) {
 
        Scanner sc = new Scanner(System.in);
        int n = sc.nextInt();
        int[] arr = new int[n];
        int tmp = 0;
        for (int i = 0; i < n; i++) {
            arr[i] = sc.nextInt();
            if (i == 0) {
                System.out.print(arr[0]);
            } 
            else {
                for (int j = 0; j < i; j++) {
                    for (int k = 0; k < i - j; k++) {
                        if (arr[k] > arr[k + 1]) {
                            tmp = arr[k + 1];
                            arr[k + 1= arr[k];
                            arr[k] = tmp;
                        }
                    }
                }
                for (int j = 0; j <= i; j++) {
                    System.out.print(arr[j] + " ");
                }
            }
        }
        sc.close();
    }
}
cs

 

<Solution 2>

첫번째 Solution의 비효율적인 부분은 무엇인가?

이미 이전 단계에서 오름차순으로 정렬이 되어 있음에도 불구하고 전체에 대해 다시 오름차순으로 정렬하는 것을 반복하고 있다. 추가로 입력된 값에 대해서만 고려해주는 방법을 생각해보자.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
import java.util.Scanner;
 
public class Main {
 
    public static void main(String[] args) {
 
        Scanner sc = new Scanner(System.in);
        int n = sc.nextInt();
        int[] arr = new int[n];
 
        for (int i = 0; i < n; i++) {
            int tmp = sc.nextInt();
            
            int j = i-1;
            while(j>=0 && arr[j]>tmp) {
                arr[j+1= arr[j];
                j--;
            }
            arr[j+1= tmp;
            
            /*
            <for문을 통한 풀이>
            if (i == 0) {
                arr[i] = tmp;
            } 
            else {
                for (int j = i - 1; j >= 0; j--) {
                    if (arr[j] > tmp) {
                        arr[j + 1] = arr[j];
                        arr[j] = tmp;
                    } else {
                        arr[j+1] = tmp;
                        break;
                    }
                }
            }
            
            */
            for (int k = 0; k <= i; k++) {
                System.out.print(arr[k] + " ");
            }
            System.out.println();
            
        }
 
    }
}
cs

<결과>

 

'알고리즘 및 코테' 카테고리의 다른 글

이진(이분) 탐색 - Binary Search - Java  (0) 2023.01.10
정렬 - Selection Sort  (0) 2023.01.10
정렬 - Bubble Sort  (0) 2023.01.09

<문제>

배열 {1,9,4,0,7,1,3,6,2,3}에서 인접한 원소들끼리 이어붙여 여러 정수들을 만들고,

그중 소수를 찾아 소수들 중 최대값을 구하라.

가령, 1, 19, 194, 1940 등등의 수가 만들어 질 수 있음

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
public class Main {
 
    public static void main(String[] args) {
        
        int[] arr = {1,9,4,0,7,1,3,6,2,3};
        // 1개 이상의 연속된 원소들을 이어붙여 1자리 이상의 수를 만들고
        // 그 중 소수를 찾아 그 소수들 중 최대값을 출력
        
        // 원소들을 이어붙여 정수를 만들고
        // 소수인지를 판별하고
        // 그 중 최대값을 찾는다.
        int maxVal = 0// 배열 내 원소들 모두 0모두 크거나 같음
        for (int i = 0; i < arr.length; i++) {
            for (int j = i; j < arr.length; j++) {
            
                //원소들을 이어붙여 정수 만듦
                int val=0;
                for (int k = i; k <= j; k++) {
                    val = val*10 + arr[k];
                }
                
                // 소수인지 판별
                // 그런데, val이 1이면 아래 for문 자체를 거치지 않는다.
                // p는 2부터인데, 조건식의 val이 1이므로 for문 자체를 거치지 않는다.
                boolean isPrime = true;
                for (int p = 2; p*<= val; p++) {
                    if(val % p == 0) {
                        isPrime = false;
                        break;
                    }
                }
                
                //최대값을 찾음
                if(isPrime && val > 1 && maxVal < val) {
                    maxVal = val;
                }
            }
        }
        if(maxVal > 0) {
            System.out.println("가장 큰 소수는 " + maxVal);
        }
        else {
            System.out.println("소수가 존재하지 않습니다.");
        }
        
        
        
        
    }
}
cs

결과는 1940713

<Solution>

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
import java.util.Scanner;
 
public class Main {
 
    public static void main(String[] args) {
 
        Scanner sc = new Scanner(System.in);
 
        int n = sc.nextInt();
        int[] data = new int[n];
        for (int i = 0; i < data.length; i++) {
            data[i] = sc.nextInt();
        }
        sc.close();
        //i가 증가함에 따라 maxSum은 값이 변하면 변한 채로 두고
        //sum만 i값이 증가함에 따라 초기화를 계속 시켜서 maxSum을 변화시킬 수 있도록 한다
        int maxSum = 0;
        for (int i = 0; i < data.length; i++) {
            int sum = 0;
            for (int j = i; j < data.length; j++) {
                sum += data[j];
                if (maxSum < sum) {
                    maxSum = sum;
                }
            }
        }
        System.out.println(maxSum);
 
    }
}
cs

최대값은 28!

Theme. 어떤 수가 소수가 인지 확인

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
import java.util.Scanner;
 
public class Main {
 
    public static void main(String[] args) {
 
        Scanner sc = new Scanner(System.in);
        // 어떤 수가 소수인지 확인
        int n = sc.nextInt();
        
        // 어떤 수를 2부터 n/2까지 나눠서 하나라도 나누어 떨어지면 소수가 아니다.
        // n/2 대신 n-1을 넣어도 된다.(어떤 수의 약수는 n/2를 넘을 수 없다)
        // 또한, n/2 대신 sqrt(n)을 넣어도 된다.
        boolean isPrime = true;
        for (int i = 2; i <= n/2; i++) {
            if(n % i == 0) {
                isPrime = false;
                break;
            }
        }
        if(isPrime) {
            System.out.println(n + "은 소수입니다.");
        } else {
            System.out.println(n + "은 소수가 아닙니다.");
        }
        
 
    }
}
cs

 

https://www.acmicpc.net/problem/1110

 

1110번: 더하기 사이클

0보다 크거나 같고, 99보다 작거나 같은 정수가 주어질 때 다음과 같은 연산을 할 수 있다. 먼저 주어진 수가 10보다 작다면 앞에 0을 붙여 두 자리 수로 만들고, 각 자리의 숫자를 더한다. 그 다음,

www.acmicpc.net

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
import java.util.Scanner;
 
public class Main {
    public static void main(String[] args) {
 
        Scanner sc = new Scanner(System.in);
 
        int N = sc.nextInt(); // 26
        int Ncopy = N;
        boolean b = true;
        int cycle = 0;
 
        while (b) {
            cycle++;
            int n1 = N / 10// 2 이때 N은 26
            int n2 = N % 10// 6
            int n3 = (n1 + n2) % 10// 8
            N = 10 * n2 + n3; // 새로운 수(68)를 만들고 N에 대입(루프 돌면서 갱신하도록)
            if (Ncopy != N) {
                b = true;
            } else {
                break;
            }
        }
        System.out.println(cycle);
 
    }
}
cs

문제를 처음 풀었을 때 무한루프가 돌게 되어 그 원인을 찾는 데 고민이 되었던 문제

무엇을 잘못했는가?

 

연산을 통해 새로운 수를 만들었을 때, 이를 새로운 변수에 저장하는 순간! 무한루프가 발생했다. 

즉, 위 코드 18번째 라인N = 10 * n2 + n3부분에서

우측 항은 새로운 수를 만든 것이고 이를 좌측 항의 변수 N에 대입하고 있지만,

 

이를 자칫 새로운 수를 만든 것이니까 int Num = 10 * n2 + n3라고 놓고 Num과 N이 같은지를 비교해서 루프를 돌릴 생각을 하면 안된다. 

그렇게 되면 N은 영원히 처음 입력한 수 그대로 변함이 없고 아무리 루프를 돌려도 변화가 없기 때문이다. 

그래서 초기 N의 값을 저장할 변수 Ncopy를 만들어 이에 저장해놓고, 새로운 수를 만들어 낼 때마다 비교하면서 문제를 풀어나가면 될 것이다.

 

간단한 문제이지만, while문에 익숙하지 못한 스스로를 발견할 수 있었던 문제였다. 성장하자.

 

'알고리즘 및 코테 > 백준' 카테고리의 다른 글

백준 1065번. 한수 (Java)  (0) 2023.02.17
백준 4673번. 셀프 넘버 - Java(자바)  (0) 2023.02.15

https://swexpertacademy.com/main/solvingProblem/solvingProblem.do

 

SW Expert Academy

SW 프로그래밍 역량 강화에 도움이 되는 다양한 학습 컨텐츠를 확인하세요!

swexpertacademy.com

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
import java.util.Scanner;
 
public class Solution {
    // 왼쪽 대각선 아래, 아래, 오른쪽 대각선 아래, 오른쪽 방향
    static int[][] drc = { { 1-1 }, { 10 }, { 11 }, { 01 } };
 
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);
 
        int tc = sc.nextInt();
        for (int t = 1; t <= tc; t++) {
            // 배열 입력 받기
            int N = sc.nextInt();
            char[][] arr = new char[N][N];
            for (int i = 0; i < N; i++) {
                char[] tempArr = sc.next().toCharArray();
                for (int j = 0; j < N; j++) {
                    arr[i][j] = tempArr[j];
                }
            }
            // 현재 위치에 돌이 있다면, 방향별 앞의 4칸에 돌이 있는지 확인한다.
            // boolean 변수를 이용해서 출력한다.
            boolean flag = false;
            outer: for (int r = 0; r < N; r++) {
                for (int c = 0; c < N; c++) {
                    if (arr[r][c] == 'o') {
                        flag = check(arr, r, c, N);
                        if (flag) {
                            break outer;
                        }
                    }
                }
            }
            if (flag) {
                System.out.println("#" + t + " " + "YES");
            } else {
                System.out.println("#" + t + " " + "NO");
            }
        }
    }
    static boolean check(char[][] arr, int r, int c, int size) {
        // 4방향을 델타 탐색(s로 인덱스 번호를 줘서 방향을 달리한다)
        for (int s = 0; s < 4; s++) {
            // 방향별 앞의 4개의 돌을 1개씩 체크한다.
            for (int k = 1; k <= 4; k++) {
                int nr = r + drc[s][0* k;
                int nc = c + drc[s][1* k;
                if (nr >= 0 && nr < size && nc >= 0 && nc < size && arr[nr][nc] == 'o') {
                    if (k == 4) {
                        return true;
                    }
                } else {
                    break;
                }
            } // end for: 방향별 앞의 4개의 돌 체크
 
        } // end for: 4개의 방향 체크
        return false// 4개의 방향 체크 다 했지만 조건 만족하는 경우 없다.
    }
 
}
 
cs

+ Recent posts