[Java | 알고리즘] 소수 판별법 (에라토스테네스의 체)

알린·2024년 6월 28일

코딩테스트

목록 보기
6/15

소수 판별법

  • N이 주어졌을 때 N을 2부터 N-1까지의 모든 수로 나누어봐 나누어떨어지는 수가 하나라도 존재하면 소수 아님
    => 시간복잡도가 O(N)이기에 비효율적
  • 알고리즘 개선: 제곱근까지만 확인하면 됨
    => 시간복잡도가 O(N의 2분의 1승)

코드

  • 제곱근까지만 확인
  • num이 어떤 수로 나누어 떨어질 때, 소수 아님(false 반환)
static boolean isPrime(int num) {
    if (num <= 1) return false;
    for (int i = 2; i <= Math.sqrt(num); i++) {
        if (num % i == 0) return false;
    }
    return true;
}

에라토스테네스의 체

  • 여러 개의 수가 소수인지 아닌지를 판별할 때 사용
    (N보다 작거나 같은 모든 소수를 찾을 때 사용)
    => 시간복잡도가 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. 위의 과정을 반복하면 구하는 구간의 모든 소수가 남는다.

코드

public static void isPrimeFun() {
    // 에라토스테네스의 체
    boolean[] isPrime = new boolean[n + 1];

    Arrays.fill(isPrime, true);
    
    // 소수인 i의 배수는 소수가 아니므로 false로 설정
    for (int i = 2; i <= Math.sqrt(n); i++) {
        for (int j = i * i; j <= n; j += i) {
            isPrime[j] = false;
        }
    }

    prime = new ArrayList<>();
    for (int i = 2; i <= n; i++) {
        if (isPrime[i]) {
            prime.add(i);
        }
    }
}
profile
짱이 되고싶은 개발 기록

0개의 댓글