이 카테고리에서는 sympy를 이용하여 각종 수열에 관련된 내용을 다뤄볼 예정이야.
수열은 말그대로 수의 나열이라는 뜻이야. 이 수의 나열에서는 보통 규칙이 보이진 않지만, 차이가 일정하다든지(등차수열), 비율이 일정하다든지(등비수열) 하는 규칙을 보일 때가 있어.
수열을 분석하고 수열의 부분합, 더 나아가 이러한 부분합들의 극한까지 알게 되면 적분까지 마스터하게 되는 것은 덤!
먼저 항 간의 차이가 일정한 등차수열을 알아보자고.
등차수열
등차수열은 항끼리의 차이가 같은 수열을 의미해. 첫째항과 항끼리의 차이인 공차로 수열의 속성이 결정되지.
첫째항이 $a$이고 공차가 $d$인 등차수열의 $n$번째 항을 $a_n$이라 하며,
$$ a_n = a+ (n-1)d $$
가 돼.
이것을 python의 sympy 를 이용하여 구현해 보자,
import numpy as np
from sympy import *
from sympy.series.sequences import * # 아래 RecursiveSeq 를 이용하기 위해 필요
n = symbols("n", integer=True) # 수열의 항 번호
a = symbols("a") # 수열의 첫째항
y = Function("y") # 점화식을 나타내기 위한 함수
d = symbols("d") # 공차
arith = RecursiveSeq(y(n - 1) + d, y(n), n, [a])
# 첫째항이 a이고 y(n-1)+d 가 y(n)이 되는데 n이라는 변수를 매개로 되는 수열
print(arith[:10]) # 10번째 항까지 출력
RecursiveSeq에 대한 자세한 내용은 튜토리얼을 보면 되지만, 간단히 설명해 보면
class sympy.series.sequences.RecursiveSeq(recurrence, yn, n, initial=None, start=0) |
recurrence : 점화식(재귀식)을 말한다. 위의 코드에서는 y(n-1) + d yn : 위의 recurrence와 일치하는 값을 말한다. 위의 코드에서는 y(n) 따라서 $ y(n) = y(n-1)+d$ 라는 등차수열을 뜻하게 됨 n : 수열의 index 을 말한다. initial : 수열의 초깃값을 말한다. 초깃값은 list형으로 주어지고, 등차수열의 경우에는 초깃값이 하나 필요하기 때문에 [a] 형태로 씀 start : 애석하게도 아직 용법이 파악 안됐습니다 . |
위 code의 결과를 보자면,
[a, a + d, a + 2*d, a + 3*d, a + 4*d, a + 5*d, a + 6*d, a + 7*d, a + 8*d, a + 9*d]
등차수열 arith의 첫째 항부터 10번째 항까지를 출력해 준다. 등차수열임을 알 수 있겠지?
그럼 몇몇 예제를 풀어보자고.
문제 1
등차수열이 $\{a_n\}$에 대해서 $a_{59}=70, a_{66} =84$ 일 때, $a_{100}$을 구하여라.
이건 등차수열의 기본 중 기본 문제네. 간략히 풀이를 살펴보자.
$a_n = a+(n-1) d$의 형태로 쓸 수 있어. 여기서 $a, d$는 각각 첫째항과 공차를 뜻하지. 주어진 조건에서는
$$ a+ 58d = 70~,~ a+ 65d = 84$$
이고, 이 두 식을 풀면 $$a= -46, d = 2$가 나오네. 따라서
$$ a_{100} = a+99d = 152$$
를 얻지.
이제 sympy code를 살펴볼까?
import numpy as np
from sympy import *
from sympy.series.sequences import * # 아래 RecursiveSeq 를 이용하기 위해 필요
n = symbols("n", integer=True) # 수열의 항 번호
a = symbols("a") # 수열의 첫째항
y = Function("y") # 점화식을 나타내기 위한 함수
d = symbols("d") # 공차
arith = RecursiveSeq(y(n - 1) + d, y(n), n, [a])
# 점화식 생성
eqn1 = arith[58] - 70 # a(59) = arith[58] 왜냐하면 arith는 index가 0부터 시작!
eqn2 = arith[65] - 84 # a(65) = arith[64] 왜냐하면 arith는 index가 0부터 시작!
res = solve([eqn1,eqn2], a,d) # 위 두 방정식을 a,d에 대해서 풀면
print(res) # {a: ? , d:? } 형태의 dictionary 형 결과
print(arith[99].subs(res)) # a(100)을 구해야하므로 arith[99]이고 여기에 res 대입
위의 문제를 coding 하는 데 있어도 혼동하지 말아야 할 것은,
고등학교 수열은 첫째항이 1항부터 시작하고, python에서 첫째항은 index =0부터 시작한다는 것!
자세한 것은 위 코드의 주석을 참고해 주길 바라. 결론은 어떨까?
{a: -46, d: 2}
152
손으로 푼 것과 똑같지 뭐. 그럼 좀 난도를 높여볼까? 비슷한 문제를 살짝 바꿔봤어.
문제 2
등차수열이 $\{a_n\}$에 대해서 $a_{59}=70, a_{66} =84$ 일 때, $a_{n} =100$ 인 $n$ 을 구하여라.
위에서 봤듯이 $a_n = -46+(n-1)\cdot 2$이므로 $$ n= 74$$일 때, $a_n =100$이 나옴을 금방 확인할 수 있어. 이것은 coding으로 어떻게 풀까?
import numpy as np
from sympy import *
from sympy.series.sequences import * # 아래 RecursiveSeq 를 이용하기 위해 필요
n = symbols("n", integer=True) # 수열의 항 번호
a = symbols("a") # 수열의 첫째항
y = Function("y") # 점화식을 나타내기 위한 함수
d = symbols("d") # 공차
arith = RecursiveSeq(y(n - 1) + d, y(n), n, [a])
eqn1 = arith[58] - 70
eqn2 = arith[65] - 84
res = solve([eqn1, eqn2], a, d)
#--------------------------------------------------
# 위에는 문제 1번과 같음
#--------------------------------------------------
print(res)
k = 0
while arith[k].subs(res) != 100: # a(k+1)이 100 이 아닌 동안 loop를 실행
k = k + 1 # index를 1씩 증가
print(f"{k + 1}th term") # loop를 빠져나왔을 때, k+1을 구해주면 됨
결과는 당연히!
{a: -46, d: 2}
74th term
응용가능하겠지? 자, 수열에 대한 첫 번째 글이었는데 뭐 별로 어려운 건 없었어. 정리해 보자고.
정리
ResursiveSeq | 점화식을 구현 from sympy.series.sequences import * 의 import 문을 사용하여 해당 라이브러리를 탑재해 주는 것이 좋음 |
subs | 방정식에 값을 대입하는 함수. 2변수 이상일 때는 dictionary 형으로 |
solve | 2변수 이상에 대해 풀 때는 반환값이 dictionary형태이므로, 그냥 이 반환값을 subs로 방정식에 넣어 줄수 있음. 예 ) 위 코드의 subs(res) 참조 |
'파이썬으로 풀어보는 고딩수학 > 수열' 카테고리의 다른 글
등비수열 (0) | 2024.04.01 |
---|---|
등차수열 2번째 이야기(feat. 피타고라스 정리) (0) | 2024.04.01 |
댓글