f_
frhyme.code
•python-libs•โฑ ์•ฝ 6๋ถ„ ์†Œ์š”

Scipy - matrix exponential

matrix exponential: scipy.linalg.expm(A)

  • matrix exponential์€ square matrix์— exponential function์„ ์ ์šฉํ•˜์—ฌ ๋„์ถœ๋œ matrix๋ฅผ ๋งํ•˜๋ฉฐ, ์ผ๋ฐ˜์ ์œผ๋กœ ์ƒ๊ฐํ•˜๋Š” exp(x)์™€ ๋™์ผํ•ฉ๋‹ˆ๋‹ค. ๋‹ค๋งŒ, ์ ์šฉํ•˜๋Š” ๋Œ€์ƒ์œผ 1์ฐจ์›์˜ ์ˆ˜๊ฐ€ ์•„๋‹ˆ๋ผ, matrix๋ผ๋Š” ๊ฒƒ์ด ๋‹ค๋ฅผ ๋ฟ์ด์ฃ .
  • ์•„๋ž˜์˜ ๊ฐ„๋‹จํ•œ ์ฝ”๋“œ๋ฅผ ๋ณด์‹œ๋ฉด,
    • ์ฒซ๋ฒˆ์งธ๋Š” matrix์— ๋Œ€ํ•ด์„œ exponential function์„ ์ ์šฉํ–ˆ๊ธฐ ๋•Œ๋ฌธ์— zero matrix์— ๋Œ€ํ•ด์„œ ์ ์šฉํ–ˆ์„ ๋•Œ, ์ •์ƒ์ ์ธ identity matrix๊ฐ€ ๋‚˜์˜ค์ง€๋งŒ,
    • ๋‘๋ฒˆ์งธ ์ฝ”๋“œ์˜ ๊ฒฝ์šฐ๋Š” Identity matrix๊ฐ€ ๋‚˜์˜ค์ง€ ์•Š์Šต๋‹ˆ๋‹ค.
A = np.zeros([2, 2])  # zero matrix
# applied matrix exponential function for matrix
assert np.all(
    scipy.linalg.expm(A) == np.identity(2)
)
# applied just exponential function for matrix
assert np.all(
    np.exp(A)== np.array([1, 1, 1, 1]).reshape(2, 2)
)

Use scipy.linalg.expm

  • scipy.linalg.expm๋ฅผ ๋‹ค์Œ๊ณผ ๊ฐ™์ด ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.
import numpy as np
from scipy import linalg as sp_linalg
"""
- 1์ฐจ์›์˜ ๊ฐ’๋“ค์— ๋Œ€ํ•ด์„œ๋Š” np.exp()๋กœ ๊ฐ„๋‹จํ•˜๊ฒŒ exponential์„ ์ ์šฉํ•  ์ˆ˜ ์žˆ๋‹ค. 
- ๊ทธ๋Ÿฌ๋‚˜, 1์ฐจ์›์ด ์•„๋‹Œ matrix์ธ ๊ตฌ์กฐ์ผ ๋•Œ๋Š” np.exp()๋ฅผ matrix์˜ ๊ฐ element์— exponential์„ ์ฒ˜๋ฆฌํ•œ๋‹ค๊ณ  ํ•ด์„œ, 
์›ํ•˜๋Š” ๊ฒฐ๊ณผ๊ฐ€ ๋‚˜์˜ค์ง€ ์•Š๋Š”๋‹ค.
- ์ด์ฒ˜๋Ÿผ matrix์— ๋Œ€ํ•ด์„œ exponential์„ ์ฒ˜๋ฆฌํ•˜๊ธฐ ์œ„ํ•œ ํ•จ์ˆ˜๊ฐ€ ๋ฐ”๋กœ `sp_linalg.expm`๋ฅผ ์‚ฌ์šฉํ•ฉ๋‹ˆ๋‹ค. 
    - check1: ์šฐ์„ , `sp_linalg.expm(zero_matrix)== Identity matrix`๋ฅผ ํ™•์ธ 
    - check2: euler identity ์˜ matrix form์— ์ ์šฉ. 
"""

N = 2
zero_mat = np.zeros([N, N])
print("== zero_mat")
print(zero_mat)
print("--"*20)
# ํ•ด๋‹น matrix์— exponential ๋ฅผ ์ ์šฉํ•จ.
# zero์— ์ ์šฉํ•œ ๊ฒƒ์ด๋ฏ€๋กœ, exp(Zeros) = I ๊ฐ€ ๋‚˜์˜ค๊ฒŒ ๋จ.
print("== sp_linalg.expm(zero_mat)")
print(sp_linalg.expm(zero_mat))
print("--" * 20)
# ๋ฐ˜๋Œ€๋กœ, ๊ทธ๋Œ€๋กœ np.exp๋ฅผ ์”Œ์šฐ๋ฉด ๋ชจ๋“  ๋ชจ๋“  ์›์†Œ๊ฐ€ 1์ด๋ฏ€๋กœ, matrix์— ๋งž๋Š” function์ด ์•„๋‹˜
print("== np.exp(zero_mat)")
print(np.exp(zero_mat))
print("--" * 20)

"""
Eulerโ€™s identity (exp(i*theta) = cos(theta) + i*sin(theta)) applied to a matrix:
"""
N = 2
X = np.random.normal(0, 1, N**2).reshape(N, N)

# `j` means imaginary parth
LHS = sp_linalg.expm(1j*X) # ij*X ์— exponential function ์ ์šฉ
RHS = sp_linalg.cosm(X) + 1j*sp_linalg.sinm(X)

print("== LHS")
print(LHS)
print("--" * 20)
print("== RHS")
print(RHS)
print("--" * 20)
== zero_mat
[[0. 0.]
 [0. 0.]]
----------------------------------------
== sp_linalg.expm(zero_mat)
[[1. 0.]
 [0. 1.]]
----------------------------------------
== np.exp(zero_mat)
[[1. 1.]
 [1. 1.]]
----------------------------------------
== LHS
[[-0.87798962+0.62059534j  0.6962854 -0.2663728j ]
 [-0.19544771+0.074771j    1.06801666-0.12387402j]]
----------------------------------------
== RHS
[[-0.87798962+0.62059534j  0.6962854 -0.2663728j ]
 [-0.19544771+0.074771j    1.06801666-0.12387402j]]
----------------------------------------

wrap-up

  • ๋‹ค์‹œ ๋งํ•˜์ง€๋งŒ, ๋ถ„๋ช…ํžˆ ๊ณผ๊ฑฐ์— ๋‹ค ๋ฐฐ์› ๋˜ ๋‚ด์šฉ์ผ ๊ฒ๋‹ˆ๋‹ค. ์‚ฌ์‹ค ์ƒ์‹์ ์œผ๋กœ๋งŒ ์ƒ๊ฐํ•ด๋„, matrix์— ์ ์šฉํ•  ๋•Œ๋Š” ํ•จ์ˆ˜๋“ค์ด ๋‹ค๋ฅธ ํ˜•ํƒœ์—ฌ์•ผ ํ•œ๋‹ค๋Š” ๊ฒƒ์„ ์•Œ๊ณ  ์žˆ์ง€๋งŒ, ์ด์ œ๋Š” ์ด๋Ÿฐ๊ฒƒ๋„ ๋‹ค์‹œ ๋ณต๊ธฐํ•˜๋Š”๋ฐ ์‹œ๊ฐ„์ด ๊ฑธ๋ฆฌ๋„ค์š”.

reference

๐Ÿ’กRELATED ARTICLES ยท ํ•จ๊ป˜ ์ฝ์œผ๋ฉด ์ข‹์€ ์—ฐ๊ด€ ํฌ์ŠคํŠธ

๊ธ€ ์ฃผ์†Œ๊ฐ€ ํด๋ฆฝ๋ณด๋“œ์— ๋ณต์‚ฌ๋˜์—ˆ์Šต๋‹ˆ๋‹ค.