Prime Number 소수란?

정의: 1과 자기 자신으로밖에 나누어 떨어지지 않고 자기 자신의 곱셈의 역수가 없는 수

예시: 2, 3, 5, 7, 11, 13, 17, 19, 23, 29, 31, 37, 41, 43, 47, 53, 59, 61, 67, 71, 73, 79, 83, 89, 97 ....

 

Java로 코드 구현한 Prime Number 소수 판별법 (시간 복잡도 O(루트 N))

public boolean isPrime(int n){
	// 2는 소수이다.
	if(n==2) return true;
	// 2보다 작고 2를 제외한 짝수는 소수가 아니다.
    // 홀수 숫자는 첫번째 비트가 1이다. 
    if(n<2||(n&1)!=1) return false;
    
    // sqrt(n) 대신 i*i<=n 으로 실수 연산을 피하기
    // 2를 제외했으니 3이상의 모든 홀수를 대상으로 검사
    for(int i=3; i*i<=n; i+=2){
    	if(n%i==0)
        	return false;
    }
    return true;
}

 

에라토스테네스의 체 

정의: 고대 수학자 에라토네스가 발견한 수학에서 소수를 반별 할 수 있는 방법

우리는 해당 방법을 통해 우리는 O(NloglogN)만에 N 이하의 모든 소수를 얻을 수 있다.

 

알고리즘, 이미지 (출처 위키백과) 

  1. 2부터 소수를 구하고자 하는 구간의 모든 수를 나열한다. 그림에서 회색 사각형으로 두른 수들이 여기에 해당한다.
  2. 2는 소수이므로 오른쪽에 2를 쓴다. (빨간색)
  3. 자기 자신을 제외한 2의 배수를 모두 지운다.
  4. 남아있는 수 가운데 3은 소수이므로 오른쪽에 3을 쓴다. (초록색)
  5. 자기 자신을 제외한 3의 배수를 모두 지운다.
  6. 남아있는 수 가운데 5는 소수이므로 오른쪽에 5를 쓴다. (파란색)
  7. 자기 자신을 제외한 5의 배수를 모두 지운다.
  8. 남아있는 수 가운데 7은 소수이므로 오른쪽에 7을 쓴다. (노란색)
  9. 자기 자신을 제외한 7의 배수를 모두 지운다.
  10. 위의 과정을 반복하면 구하는 구간의 모든 소수가 남는다. (보라색)

 

Java로 코드 구현한 에라토스테네스의 체 (시간 복잡도 O(MAX log log MAX))

    public static int MAX = 1000000;
    public static boolean[] isPrime = new boolean[MAX+1];
    public static void era(boolean[] isPrime){
    	// 초기 소수값 판별 배열 초기화
    	Arrays.fill(isPrime,true);
        isPrime[0] = false; isPrime[1] = false;
        
        // 2부터 체크해서 본인의 배수 값을 false 처리
        for(int i=2;i<=MAX;i++){
            if(!isPrime[i]) continue;
            for(int j= i+i; j<=MAX; j+=i)
                isPrime[j] = false;
        }
    }

왜 시간 복잡도가 O(N log log N) 인가? GPT 부탁해!

관련 백준 문제:(소수 구하기) https://www.acmicpc.net/problem/1929

'PS > Algorithm' 카테고리의 다른 글

스위핑 알고리즘  (0) 2023.07.19

스위핑 알고리즘

스위핑 알고리즘은 1차원이나 2차원 공간에서 여러 개의 객체가 주어졌을 , 특정 축을 기준으로 방향으로 진행(스위핑)하며 문제를 해결하는 알고리즘으로 주로 기하학적 문제의 풀이에서 많이 사용된다.

아래의 예시와 같이 전체 선분의 범위 만큼의 배열을 잡은 후 선분의 시작 점에 +1, 나갈 때 -1 하는 방식으로 어느 x좌표에서 중복되는 선분의 갯수를 파악하기 편리하다.

 

해당 문제를 단순 구현할 경우 통상적으로 O(n*m)의 시간이 걸리지만 

        for (int i = start; i <= end; i++) {
            int tmp=0;
            for (Pos height : heights) {
                int max = Math.max(height.start,height.end);
                int min = Math.min(height.start,height.end);
                if(min<=i&&i<max)
                    tmp++;
            }
            count = Math.max(count,tmp);
        }

스위핑 알고리즘을 적용할 경우 O(n+m)의 시간 복잡도로 문제 해결이 가능하다.

	for (Pos height : heights) {
                int max = Math.max(height.start,height.end);
                int min = Math.min(height.start,height.end);
                CountX[max]--;
        		CountX[min]++;
        }
	for (int i = 1; i < CountX.length; i++) {
            CountX[i]+=CountX[i-1];
            CountY[i]+=CountY[i-1];
        }

해당 알고리즘을 사용한 문제 풀이

https://suhanlim.tistory.com/249

 

'PS > Algorithm' 카테고리의 다른 글

(Prime Number)소수 판별법, 에라토스테네스의 체 (Java)  (0) 2023.08.14

+ Recent posts