#!wiki style="display: inline; display: none;"
, }}}
정수론 Number Theory |
|||
{{{#!wiki style="margin:0 -10px -5px;min-height:2em" {{{#!folding [ 펼치기 · 접기 ] {{{#!wiki style="margin:-6px -1px -11px" |
공리 | ||
페아노 공리계 · 정렬 원리 · 수학적 귀납법 · 아르키메데스 성질 | |||
산술 | |||
나눗셈 | 약수· 배수 | 배수 · 약수( 소인수) · 소인수분해( 목록) · 공배수 · 공약수 · 최소공배수 · 최대공약수 | |
약수들의 합에 따른 수의 분류 | 완전수 · 부족수 · 과잉수 · 친화수 · 사교수 · 혼약수 · 반완전수 · 불가촉 수 · 괴짜수 | ||
정리 | 베주 항등식 · 산술의 기본정리 · 나눗셈 정리 | ||
기타 | 유클리드 호제법 · 서로소 | ||
디오판토스 방정식 | 페르마의 마지막 정리 · 피타고라스 세 쌍 · 버츠와 스위너톤-다이어 추측(미해결) | ||
모듈러 연산 | |||
잉여역수 · 2차 잉여 · 기약잉여계 · 완전잉여계 · 중국인의 나머지 정리 · 합동식 · 페르마의 소정리 · 오일러 정리 · 윌슨의 정리 | |||
소수론 | |||
수의 분류 | 소수 · 합성수 · 메르센 소수 · 쌍둥이 소수( 사촌 소수 · 섹시 소수) · 페르마 소수 · 레퓨닛 수 | ||
분야 | 대수적 정수론 · 해석적 정수론 | ||
산술함수 | 뫼비우스 함수 · 소수 계량 함수 · 소인수 계량 함수 · 약수 함수 · 오일러 파이 함수 · 폰 망골트 함수 · 체비쇼프 함수 · 소수생성다항식 | ||
정리 | 그린 타오 정리 · 페르마의 두 제곱수 정리 · 디리클레 정리 · 소피 제르맹의 정리 · 리만 가설(미해결) · 골드바흐 추측(미해결)( 천의 정리) · 폴리냑 추측(미해결) · 소수 정리 | ||
기타 | 에라토스테네스의 체 · 윌런스의 공식 |
1. 개요
素 因 數 分 解 · prime factorization합성수를 소수들의 곱으로 나타내는 것을 말한다.[1] 소수를 처음 배우는 중학교부터 자주는 아니더라도 계속 쓰이는 기본적인 수학 도구. 모든 합성수가 소인수분해된 형태를 가지고 있다는 것은 산술의 기본정리로 증명된다.
소인수 분해를 직관적으로 설명한 영상
'소인수분해'라는 명칭은 중학교에 가서야 언급되지만, 초등학교 5학년 때 약수와 배수를 구하기 위해 잠시 사용된다.
1.1. 온라인 사이트
factordb - 이름 그대로 소인수분해 방법이 알려진 수들의 데이터베이스를 제공한다. 모르는 수의 소인수분해 방법이 궁금할 때 참조하면 좋은 자료.Calculator Soup®라는 홈페이지에서도 소인수분해가 가능하다.
울프람알파에서도 prime factorization 과 함께 숫자를 넣어주면 소인수분해 결과를 보여준다. 간단히 'factor N'(N은 양의 정수)로도 된다.
11111111111111111의 소인수분해
2. 소인수분해를 하는 방법
이 문단에서는 1보다 큰 어떤 정수 [math(N)]이 주어졌을 때, 10진법 표기에서 약수를 찾는 여러 가지 기술에 대해 소개한다. 먼저 가장 쉬운 방법은 아래의 배수 판정법을 이용하는 것이다.정수 [math(N)]에 대해서,
1. 2의 배수[2]: 일의 자리 숫자가 짝수.[3]
1. 3의 배수: 각 자릿수의 합이 3의 배수.
1. 4의 배수: 맨 뒤 두 자리가 00이거나 4의 배수.
1. 5의 배수: 일의 자리가 0이거나 5인 경우.
1. 6의 배수: [math(N)]이 2의 배수이면서 3의 배수.
1. 8의 배수: 맨 뒤 세 자리가 000 또는 8의 배수.
1. 9의 배수: 각 자릿수의 합이 9의 배수.
1. 10의 배수: 일의 자리가 무조건 0.
1. 10n의 배수: 가장 끝의 n개의 자리가 모두 0.
1. 7, 11, 13의 배수: 일의 자리부터 세 자리씩 끊은 뒤, 각 부분을 교대로 빼고 더한 값이 7, 11, 13의 배수.[4][5][6]
1. 15의 배수: [math(N)]이 5의 배수이면서 3의 배수.
1. 25의 배수: 맨 뒤 두 자리가 00 또는 25의 배수(25, 50, 75)
1. 12의 배수: [math(N)]이 3의 배수이면서 4의 배수.
1. 20의 배수: [math(N)]이 4의 배수이면서 5의 배수.
1. 30의 배수: [math(N)]이 5의 배수이면서 6의 배수.
1. 48의 배수: [math(N)]이 3의 배수이면서 16의 배수.
1. 72의 배수: [math(N)]이 8의 배수이면서 9의 배수.
1. 27, 37의 배수: 일의 자리부터 3자리씩 끊은 뒤 이들을 모두 합한 결과가 27, 37의 배수인 수.[7][8]
보다 일반적으로 n이 합성수이고, 소인수가 2개 이상일 때, n의 배수를 판별하는 방법은 d가 n의 유니타리 약수라고 했을 때 d와 n÷d의 공배수 여야 하므로 이 둘의 배수판정법을 동시에 만족해야 한다는 것이다. 1. 2의 배수[2]: 일의 자리 숫자가 짝수.[3]
1. 3의 배수: 각 자릿수의 합이 3의 배수.
1. 4의 배수: 맨 뒤 두 자리가 00이거나 4의 배수.
1. 5의 배수: 일의 자리가 0이거나 5인 경우.
1. 6의 배수: [math(N)]이 2의 배수이면서 3의 배수.
1. 8의 배수: 맨 뒤 세 자리가 000 또는 8의 배수.
1. 9의 배수: 각 자릿수의 합이 9의 배수.
1. 10의 배수: 일의 자리가 무조건 0.
1. 10n의 배수: 가장 끝의 n개의 자리가 모두 0.
1. 7, 11, 13의 배수: 일의 자리부터 세 자리씩 끊은 뒤, 각 부분을 교대로 빼고 더한 값이 7, 11, 13의 배수.[4][5][6]
1. 15의 배수: [math(N)]이 5의 배수이면서 3의 배수.
1. 25의 배수: 맨 뒤 두 자리가 00 또는 25의 배수(25, 50, 75)
1. 12의 배수: [math(N)]이 3의 배수이면서 4의 배수.
1. 20의 배수: [math(N)]이 4의 배수이면서 5의 배수.
1. 30의 배수: [math(N)]이 5의 배수이면서 6의 배수.
1. 48의 배수: [math(N)]이 3의 배수이면서 16의 배수.
1. 72의 배수: [math(N)]이 8의 배수이면서 9의 배수.
1. 27, 37의 배수: 일의 자리부터 3자리씩 끊은 뒤 이들을 모두 합한 결과가 27, 37의 배수인 수.[7][8]
또는 아래 정리를 사용할 수도 있다.증명은 아래와 같다.
[math(n)]을 합성수라 하자. 그러면 [math(n=ab,\,1<a,b<n)]이다. 만약 [math(a,b)]가 둘 다 [math(\sqrt n)]보다 크다면, [math(n=\sqrt n\sqrt n<ab=n)]이 되어 모순이다. 따라서 [math(a,b)]중 적어도 하나는 [math(\sqrt n)]보다 같거나 작다.
이 정리에 의해 어떤 큰 수를 소인수분해 할 때, 그 수의 제곱근 보다 큰 수로 나눌 필요는 없다는 사실을 알 수 있다. 이는
노가다를 통해 소인수분해를 하는 시간을 크게 단축시켜 준다.2.1. 알고리즘
프로그래밍으로 소인수를 구할 때는 위와 같은 자질구레한 규칙을 따질 필요 없이, 주어진 숫자 n의 소인수를 구한다고 할 경우 아래와 같은 순서로 진행하면 된다.* 1. i=2로 시작하여 i++ 하면서 n%i == 0 인지 체크한다.
* 2. n%i==0이 성립하는 경우 i를 소인수로 등록한 후 n은 i로 나눈 값을 저장하고 i는 i++ 하지 않고 i부터 다시 시작하도록 한다.
* 3. n이 1이 될 때까지 위 과정을 반복한다.
* 2. n%i==0이 성립하는 경우 i를 소인수로 등록한 후 n은 i로 나눈 값을 저장하고 i는 i++ 하지 않고 i부터 다시 시작하도록 한다.
* 3. n이 1이 될 때까지 위 과정을 반복한다.
이 알고리즘으로 소인수를 구하면 천억이 넘는 숫자도 소인수가 순식간에 구해진다.
간단하게 파이썬으로 코딩 해보면 다음과 같다.
#!syntax python
# -*- coding: utf-8 -*-
import os
import sys
def find_prime(input_num):
if input_num <= 2:
return [input_num,]
for idx in range(2,input_num):
if input_num % idx == 0:
ret_list = []
val_a = find_prime(idx)
val_b = find_prime(int(input_num/idx))
ret_list = val_a + val_b
return ret_list
return [input_num,]
def main():
try:
input_num = int(sys.argv[1])
except:
print("usage: python main.py <number>")
print(" ex> python main.py 12345")
quit()
prime_list = find_prime(input_num)
check_num = 1
for prime_at in prime_list:
check_num *= prime_at
print("[%s] input_num=%d, check_num=%d" % (input_num == check_num, input_num, check_num))
print("%s" % prime_list)
main()
다만 위의 프로그램은 프로그래밍을 익히는 용도로는 유용할수 있으나, 실제 소인수분해 용으로 쓰기에는 적합하지 않다. 실제로 컴퓨터로 다루는 수는 1000억은 '겨우'라는 소리가 나올만큼 큰 수를 다룰 필요가 있기 때문이다.
가장 쉬운 방법은 다른 프로그램을 이용해서 미리 소수 테이블을 작성해 두고, 이를 활용하는 것이다. 예를 들어 216 보다 작은 소수는 6542개인데, 이를 미리 배열에 저장해 두면, 42억 (=232 ) 보다 작은 수는 겨우 6542번 나누어 보기만 하면 소수인지 판정하거나, 1개 이상의 소인수를 구할 수 있다. 232 보다 작은 소수는 모두 약 2억개(203,280,221 개) 인데, 이를 미리 구해서 적절한 DB 에 저장해 두면 약 1844 경 (= 264 = 18,446,744,073,709,551,616) 보다 작은 수의 소인수 분해를 쉽게 할 수 있다.
20자리 정도 되는 이정도 수면 큰 수라고 생각할 수 있지만, RSA 암호화같은 암호학에서 기본 수백자리 수를 다뤄야 한다. RSA 넘버를 보면 가장 작은 것이 100자리 부터 시작하는데, 그마저 250자리 수 까지는 모두 소인수분해되었다. 가장 큰 RSA-2048 은 무려 617자리 수이다. 수의 단위 중 이름이 붙은 최고 단위인 구골이 101자리 수라는 것을 생각해보면, RSA 암호화에서 다루는 수는 사람에게는 어마어마하게 큰 수이다.
밑과 지수를 구하는 기본적인 파이썬 함수는 여기서 설명되어 있다.
3. 관련 문서
[1]
합성수가 아니어도 되지만,
소수의 경우 자기 자신이 곧 자기 자신의 소인수분해 결과가 된다.
[2]
짝수.
[3]
끝자리가 0, 2, 4, 6, 8 중 하나이며, 참고로, 0도 짝수다.
[4]
123456789를 예시로 들면, 123-456+789=456이 7의 배수가 아니므로 원래 수는 7의 배수가 아니다. 59255924를 예시로 들면, 59-255+924=728이 7의 배수이므로 원래 수는 7의 배수이다.
[5]
이 방법은 1001=7*11*13, 999999=33*37*1001 임을 이용한 방법이다. 이 외에도 다른 방법들이 있다.
[6]
11의 배수는 다른 방법으로, 만약 홀수 번째 자리(일의 자리, 백의 자리, 만의 자리... 등)와 짝수 번째 자리(십의 자리, 천의 자리, 십만의 자리... 등)의 각각의 합의 차가 0 또는 11의 배수이면 그 수는 11의 배수이다. (예: 11110 → 1+1+0=2, 1+1=2, 2-2=0 → 11의 배수.)
[7]
이 방법은 999가 27, 37의 배수인 것을 이용했다.
[8]
다른 방법(스펜스의 방법)으로는 27의 경우 일의 자리를 8배 하며, 37의 경우 일의 자리 숫자를 11배 하여 나머지 자리 값에서 뺀다 나머지 자리에서 뺀 값이 27/37의 배수이면 원래 수는 27/37의 배수이다.