백준

[백준/BOJ] 9020번 : 골드바흐의 추측 (JAVA / 자바)

코메인 2022. 3. 27. 23:52

안녕하세요~ 코딩하는 코알못 코메인입니다.

 

 

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

 

9020번: 골드바흐의 추측

1보다 큰 자연수 중에서  1과 자기 자신을 제외한 약수가 없는 자연수를 소수라고 한다. 예를 들어, 5는 1과 5를 제외한 약수가 없기 때문에 소수이다. 하지만, 6은 6 = 2 × 3 이기 때문에 소수가 아

www.acmicpc.net


- 문제 -

 

난이도 실버 1 문제이다.

자바에서 입력방식은 scanner와 bufferedreader가 있다.

자바를 초반에 접하면 처음에 배우는 입력은 scanner이다. scanner가 bufferedreader보다 편하지만 속도가 느리다.

bufferedreader는 무조건 문자열로 받아오기때문에 정수형이나 실수형 변수에 저장하기 위해서는 입력과 형변환을 해줘야한다.

더 자세한 내용은 아래 글 참고 하면 좋다.

https://comain.tistory.com/3

 

(JAVA / 자바) Scanner 와 Bufferedreader

안녕하세요~ 코딩하는 코알못 코메인입니다. 이번엔 백준 문제 풀면서 계속 언급될 scanner와 bufferedreader에 대한 간단한 정리를 해볼거다. 자바에서 입력은 scanner와 bufferedreader가 있다. 우선 각자

comain.tistory.com

 

풀이 방법

소수를 구하여 n이 어떠 소수의 합으로 이루어져있는지 구하는 문제이다.(여러 경우의 수가 있을 수 있는데 그럴 경우 두 소수의 차가 제일 낮은 값으로 출력)

 

우선 소수를 판별하기위해 에라토스테네스의 체를 사용할 것이다. 에라토스테네스에 대한 간략한 설명과 적응을 위해서는 

https://comain.tistory.com/253

 

[백준/BOJ] 1929번 : 소수 구하기 (JAVA / 자바)

안녕하세요~ 코딩하는 코알못 코메인입니다. https://www.acmicpc.net/problem/1929 1929번: 소수 구하기 첫째 줄에 자연수 M과 N이 빈 칸을 사이에 두고 주어진다. (1 ≤ M ≤ N ≤ 1,000,000) M이상 N이하의 소..

comain.tistory.com

소수구하기 문제를 먼저 보거나 풀어보자.

 

소수를 구했으면, 이제 2부터 n / 2까지 반복하는 반복문을 통해 두 소수를 합해서 n이 나오는 두 소수를 구할 것이다.

n/2까지만 하는 이유는 소수 i가 있을때 n이 나오는 다른 값은 n-i가 올 것이고, 두 값이 다 소수일 경우에 소수의 합인 결론이 나올 것이다. 이렇게 구하다보면 n까지 구하지 않아도 n / 2까지만 구해도 결과는 나올 것이다.

 

이부분은 코드를 보면 쉽게 이해될 것이다. 코드를 보자.


-풀이-

 

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;

public class Main {
	
	public static void main(String[] args) throws IOException {
		BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
		int T = Integer.parseInt(br.readLine());
		
		for(int i = 0; i < T; i++) {
			int n = Integer.parseInt(br.readLine());
			//소수 판별 배열
			boolean[] arr = new boolean[n + 1];
			//0과 1은 소수가 아니다
			//true는 소수가 아니다, false는 소수다.
			arr[0] = arr[1] = true;
			
			//소수판별을 위한 에라토스테네스 체 방식
			for(int j = 2; j * j <= n; j++) {
				if(!arr[j]) {
					for(int k = j * j; k <= n; k += j) {
						arr[k] = true;
					}
				}
			}
			
			//합해서 n이 되는 두 소수를 저장 할 변수
			int prime1 = 0;
			int prime2 = 0;
			
			for(int j = 2; j <= n / 2; j++) {
				//합해서 n이 나오는 두 값이 다 소수일때 변수에 저장.
				//반복문이 끌날때까지 저장하고, 마지막에 저장 된 값이 차가 제일 작은 값이 된다.
				if(!arr[j] && !arr[n - j]) {
					prime1 = j;
					prime2 = n - j;
				}
			}
			System.out.println(prime1 + " " + prime2);
		}
	}

}

-결과-

 


아직 코딩 공부가 부족한 필자라 설명과 풀이 방법이 많이 미흡할 수 있다. 코딩 고수분들은 보시고 문제점이 있다면 댓글로 말해주시면 감사한 마음으로 참고 수정 하겠습니다.