NumPy Master Class

Chapter3 Mathematical Functions: Notebook3 Exponents and Logarithms

Shin's Lab 2020. 1. 9. 17:58
3_3_Exponents_and_Logarithms

NumPy Master Class

Chapter3 Mathematical Functions

Notebook3 Exponents and Logarithms

이번 시간에는 Exponent를 구하는 방법과 그 역연산인 Logarithm에 대해 배워본다. 이때 base가 natural constant와 2일때를 다룬다. 이는 우리가 앞으로 사용하는 exp, log는 보통 base가 natural constant일 때를 말하고, 우리가 computer science, imformation theory 등을 다룰 때 base는 보통 2이기 때문이다.

사실 natural logarithm을 다루는 method들 외에는 모두 np.power()로 대체할 수 있지만 다른 사람이 쓴 코드를 알아보기 위해서라도 간단히 알아보도록 하자.

1. np.exp()
2. np.exp2()
3. np.log()
4. np.log2()
5. np.log10()
In [4]:
import numpy as np
import matplotlib.pyplot as plt

np.exp(), np.exp2()

먼저 exponent들을 다뤄보도록 하자. 밑이 natural constant일 때는, derivative나 integral을 구하기가 훨씬 수월하므로 이론적인 분석에서 자주 사용된다. 그리고 bit를 다룰 때 base가 2를 자주 사용하므로 둘 다 익혀두는 것이 좋다.

In [13]:
x_range = np.linspace(-2, 2, 500)

exp_np = np.exp(x_range)
exp2_np = np.exp2(x_range)

fig, ax = plt.subplots(figsize = (8,4))
ax.plot(x_range, exp_np, label = 'exp')
ax.plot(x_range, exp2_np, label = 'exp2')
ax.grid()
fig.legend(facecolor = (0.8, 0.8, 0.8), loc = 'upper left')
Out[13]:
<matplotlib.legend.Legend at 0x7f168a2c8eb8>

위에서 볼 수 있는 것처럼, base가 e, 2인 경우에는 direct하게 NumPy method를 이용하여 만들 수 있다.

이 외에 $3^{x}, 4^{x}, 5^{x}$와 같이 base가 다른 경우엔 np.power()를 이용하여 구할 수 있고 다음 시간에 다뤄보도록 하자.


np.exp() and np.sinh()

위의 np.exp()에 익숙해지기 위해 저번 notebook에서 배운 np.sinh() 이용하여 테스트해보도록 하자.

우리가 hyperbolic sine function은 다음과 같이 나타낸다.

$sinh(x) = \frac{e^{x} - e^{-x}}{2}$

In [31]:
radian_range = np.linspace(-3, 3, 300)

sinh_np1 = (np.exp(radian_range) - np.exp(-1*radian_range))/2
sinh_np2 = np.sinh(radian_range) + 0.5

fig, ax = plt.subplots(figsize = (8,4))
ax.plot(radian_range, sinh_np1, label = 'sinh_np1')
ax.plot(radian_range, sinh_np2, label = 'sinh_np2')
ax.grid()
fig.legend(facecolor = (0.8, 0.8, 0.8), loc = 'upper left')
Out[31]:
<matplotlib.legend.Legend at 0x7f1689c268d0>

위의 코드에서 일부러 곂치는 것을 방지하기 위해 np.sinh()의 결과에 0.5를 더해줬다.

sinh_np1을 구할 때 주목할 점은 다음과 같다.

np.exp(radian_range) - np.exp(-1*radian_range)을 구할 때, element-wise subtraction이 진행됐다.
(np.exp(radian_range) - np.exp(-1*radian_range))/2의 마지막 /2도 마찬가지로 element마다 /2를 해준 결과이다.

np.log(), np.log2(), np.log10()

다음은 base가 각각 e, 2, 10인 logarithm들을 구해보도록 하자.

In [34]:
radian_range = np.linspace(0.01, 10, 300)

log_np = np.log(radian_range)
log2_np = np.log2(radian_range)
log10_np = np.log10(radian_range)

fig, ax = plt.subplots(figsize = (8,4))
ax.plot(radian_range, log_np, label = 'log')
ax.plot(radian_range, log2_np, label = 'log2')
ax.plot(radian_range, log10_np, label = 'log10')
ax.grid()
fig.legend(facecolor = (0.8, 0.8, 0.8), loc = 'upper left')
Out[34]:
<matplotlib.legend.Legend at 0x7f1689adbb70>

Logarithms with Arbitrary Bases

Log의 특징을 이용하면 임의의 base에 대한 함수를 만들어낼 수 있다.

$log_{a}x = \frac{log_{c}x}{log_{c}a}$

위와 같은 규칙을 이용해서 c를 natural constant e로 치환하면

$log_{a}x = \frac{log_{e}x}{log_{e}a}$

가 되는 것을 알 수 있다. 따라서 base가 3, 4, 5인 log function들에 대해서 다음과 같이 구현이 가능하다.

In [44]:
radian_range = np.linspace(0.01, 10, 300)

log3_np = np.log(radian_range) / np.log(3)
log4_np = np.log(radian_range) / np.log(4)
log5_np = np.log(radian_range) / np.log(5)

fig, ax = plt.subplots(figsize = (8,4))
ax.plot(radian_range, log3_np, label = r'$log_{3}x$')
ax.plot(radian_range, log4_np, label = r'$log_{4}x$')
ax.plot(radian_range, log5_np, label = r'$log_{5}x$')
ax.grid()
fig.legend(facecolor = (0.8, 0.8, 0.8), loc = 'upper left', fontsize = 'large')
Out[44]:
<matplotlib.legend.Legend at 0x7f168966d630>