본문 바로가기
코딩테스트 연습/프로그래머스

[python] 프로그래머스 (소수 찾기) feat. 에라토스테네스의 체

by Lagooni 2021. 8. 27.

문제 설명

1부터 입력받은 숫자 n 사이에 있는 소수의 개수를 반환하는 함수, solution을 만들어 보세요.

소수는 1과 자기 자신으로만 나누어지는 수를 의미합니다.
(1은 소수가 아닙니다.)

제한 조건

  • n은 2 이상 1000000 이하의 자연수입니다.

입출력 예

nresult

10 4
5 3

입출력 예 설명

입출력 예 #1
1부터 10 사이의 소수는 [2,3,5,7] 4개가 존재하므로 4를 반환

입출력 예 #2
1부터 5 사이의 소수는 [2,3,5] 3개가 존재하므로 3을 반환


잘못된?? 풀이 방법

별다른 제한사항이 없어 소수를 판별하는 함수를 만들어 숫자별로 하나씩 소수라면 answer의 수를 1씩 증가시키는 방식으로 접근하였다.

n = 10

def solution(n):
    answer = 0
    for i in range(2, n+1):
        if(isPrime(i)):
            answer += 1
    return answer

def isPrime(num):
    for i in range(2, num):
        if(num % i == 0):
            return False
    return True

print(solution(n))

그 결과 시간초과... 56.3점... 시간복잡도를 신경써야하는 문제이다.


에라토스테네스의 체

고대 그리스 수학자 에라토스테네스가 발견하여 소수를 체에 걸러내듯 하여 붙여진 이름이다.

 

에라토스테네스의 체 알고리즘의 동작과정

  1. 2부터 N까지 모든 자연수를 나열한다.
  2. 남은 수 중에 아직 처리하지 않은 가장 작은 수 i를 찾는다.
  3. 남은 수 중에서 i를 제외한 모든 i의 배수를 제거한다.
  4. 2, 3번 과정을 반복시킨다.

에라토스테네스의 체 성능

시간 복잡도 O(NloglogN)

다수의 소수를 찾는 문제에서 아주 효과적이다.

하지만 각 자연수에 대한 소수 여부를 저장하기 때문에 숫자를 담을 메모리가 많이 필요함.

만약 숫자 10억 하나가 소수인지 아닌지 판별해야 한다면 에라토스테네스의 체는 비효율적일 수 있음.

 

https://www.youtube.com/watch?v=9rLFFKmKzno


def solution(n):
    answer = 0
    # 에라토스테네스의 체 초기화: n개 요소에 True 설정(소수로 간주)
    sieve = [True] * (n+1)
    # n의 최대 약수가 sqrt(n) 이하이므로 i=sqrt(n)까지 검사
    m = int(n ** 0.5)
    for i in range(2, m + 1):
        if sieve[i] == True:           # i가 소수인 경우
            for j in range(i+i, n+1, i): # i이후 i의 배수들을 False 판정
                sieve[j] = False

    for i in range(2, n+1):
        if(sieve[i] == True):
            answer += 1
    # 소수 개수
    return answer

 

댓글