Tips Python 数学モジュール/ライブラリ
簡易的なメモです。
Sympy : 代数演算
・sympy.var('x y'):シンボリック変数
・sympy.logcombine():対数の式をまとめる関数
対数公式
$${log(x)+log(y)=log(x∗y)}$$
$${y∗log(x)=log(x^y)}$$
を確かめる。
# xとyをシンボリック変数とする
sympy.var('x y') # シンボリック変数
f = sympy.log(x) + sympy.log(y) # 式を定義
sympy.logcombine(f, force=True) # log(x*y) を出力
g = y*sympy.log(x)
sympy.logcombine(g, force=True) # log(x**y) を出力
・sympy.diff( ) <- 微分
import sympy
# xをシンボリック変数として定義
sympy.var('x') # x が出力
# 関数に名前をつけて定義
f = x**3 + x**2 + x
# 微分(一階)
sympy.diff(f) # 3*x**2 + 2*x + 1 が出力
# 指数表記など数式を見やすく表示する設定
sympy.init_printing()
# 微分(一階)
sympy.diff(f) # 以下の結果が出力
>> 出力結果
2
3⋅x + 2⋅x + 1
・sympy.solve() <- 方程式を解く。解は[-1,1]のようにリスト型。
この0番目の解を取り出すにはsympy.solve()[0]とします。
・subs()メソッド:式の変数に数値代入。
式.subs(変数, 数値)
# 代数演算ライブラリSymPyモジュールをインポートします
import sympy
# xをシンボリック変数として定義します。
sympy.var('x')
# 2次関数 y = -x2 + x を定義します
y = -x**2 + x
# y の微分 y'を求めます。sympy.diff(y)
# 微分y'=0 という方程式を解いて解(リスト)を求めます。sympy.solve()
# 解リストの0番目を取り出したものを変数solxに代入します。sympy.solve()[0]
solx = sympy.solve(sympy.diff(y))[0]
# y=-x2+x のxに解solを数値代入します。
y.subs(x, solx)
・sympy.integrate(関数):不定積分を返します。積分定数は0です。
import sympy
# xをシンボリック変数と定義
sympy.var('x')
# 式を見やすく表示する設定
sympy.init_printin()
#積分
sympy.integrate(x) # 以下の結果が出力
>>出力結果
2
x
──
2
sympy.integrate(sympy.cos(x)) # sin(x) が出力
sympy.integrate(sympy.exp(x)) # 以下の結果が出力
>>出力結果
x
ℯ
sympy.integrate(1/x) # log(x) が出力
#### 定積分 ####
# sympy.integrate(関数, (x, a, b))は下端a、上端bの定積分の値を返します。
sympy.integrate(x, (x, 0, 1)) # 1/2 が出力
sympy.integrate(sympy.exp(x), (x, 0, 1)) # -1 + ℯ が出力
sympy.integrate(1/x, (x, 1, 2)) # log(2) が出力
・isprime() <- 素数の判定
・sieve.primerange() <- 素数リストの生成
from sympy import isprime, sieve
isprime(11) # True と出力
isprime(10) # False と出力
print([i for i in sieve.primerange(1,100)])
# 1以上100未満の素数をリストアップします
# [2, 3, 5, 7, 11, 13, 17, 19, 23, 29, 31, 37, 41, 43, 47, 53, 59, 61, 67, 71, 73, 79, 83, 89, 97]
・sympy.N() / evalf()メソッド<- Calls x.evalf(n, **options).
Both .n() and N() are equivalent to .evalf(); use the one that you like better. See also the docstring of .evalf() for information on the options.
>>> from sympy import Sum, oo, N
>>> from sympy.abc import k
>>> Sum(1/k**k, (k, 1, oo))
Sum(k**(-k), (k, 1, oo))
>>> N(_, 4)
1.291
・等差数列
等差数列の4つのパラメータ:【初項】【末項】【公差】【項数】
公差 =(末項 ー 初項)/(項数-1)
・range(初項a, STOP, 公差d):数列は0スタート(初項が第0項)、range(n)の引数nは項数。
・少数を扱えない。
・末項は計算してみないとわからない
t = range(初項a, STOP, 公差d)
数列t[k]:初項aから公差dでSTOPを超えない範囲の等差数列
t[0]=a, t[1]=a+d, t[2]=a+2d, …, t[?]=? < STOP
# range(STOP)は、初項0、公差1、項数STOP、末項STOP-1の等差数列を生成
t = range(5)
print(t[0]) # 0 が出力
print(t[4]) # 4 が出力
print(list(t)) # [0, 1, 2, 3, 4] が出力
# range(初項a,STOP)は、初項a、公差1、項数STOP、末項STOP-1の等差数列
t = range(1, 5)
print(list(t)) # [1, 2, 3, 4] が出力
# range(初項a, STOP, 公差d)は、初項a、公差dの等差数列をSTOPを超えない範囲で生成
t = range(1, 10, 2)
print(list(t)) # [1, 3, 5, 7, 9] が出力
t = range(1, 10, 3)
print(list(t)) # [1, 4, 7] が出力
・numpy.arange(初項a, STOP, 公差d):数列は0スタート(初項が第0項)、arange(n)の引数nは項数。
・少数を扱えない。
・末項は計算してみないとわからない少数を扱える。
import numpy
t = numpy.arange(初項a, STOP, 公差d)
#数列t[k]:初項aから公差dでSTOPを超えない範囲の等差数列
t[0]=a, t[1]=a+d, t[2]=a+2d, …, t[?]=? < n
# numpy.arange(STOP)は、初項0、公差1、項数STOP、末項STOP-1の等差数列
t = numpy.arange(5)
print(t[0]) # 0 が出力
print(t[4]) # 4 が出力
print(list(t)) # [0, 1, 2, 3, 4] が出力
# numpy.arange(初項a,STOP)は、初項a、公差1、項数STOP、末項STOP-1の等差数列
t = numpy.arange(1, 5)
print(list(t)) # [1, 2, 3, 4] が出力
t = numpy.arange(0.5, 3, 0.5)
print(list(t)) # [0.5, 1. , 1.5, 2. , 2.5] が出力
t = numpy.arange(1, 10, 2.5)
print(list(t)) # [1. , 3.5, 6. , 8.5] が出力
・numpy.linspace(初項a, 末項b, 項数N):数列は0スタート(初項が第0項)。
・末項を引数に持つようにした
・公差が計算してみないとわからない
・numpy.linspace(初項a, 末項b, 項数N)の公差:d = (b-a)/(N-1)
・sum( )メソッド:数列の和
import numpy
t = numpy.linspace(初項a, 末項b, 項数N)
#数列t[k]:初項aから末項dまで項数Nの等差数列
#t[0]=a, t[1]=a+d, t[2]=a+2d, …, t[N-1]=b
#ただし、公差d=(b-a)/(N-1)
# numpy.linspace(初項a, 末項b)は、初項a、末項b、項数50(省略した場合)の等差数列を生成
t = numpy.linspace(1, 50)
print(t[0]) # 1.0 が出力
print(t[49]) # 50.0 が出力
# 公差:d = (b-a)/(N-1)
t = numpy.linspace(0, 5, 11) # 公差d = (5-0)/(11-1) = 0.5
print(list(t)) # [0. , 0.5, 1. , 1.5, 2. , 2.5, 3. , 3.5, 4. , 4.5, 5. ] が出力
t = numpy.linspace(1, 10, 4) # 公差d = (10-1)/(4-1) = 3
print(list(t)) # [ 1., 4., 7., 10.] が出力
# sum メソッド
# [1, 2, 3, 4]の和1+2+3+4を求める
numpy.arange(1, 5).sum() # 10 が出力
# [ 1., 4., 7., 10.]の和1+4+7+10を求める
numpy.linspace(1, 10, 4).sum() # 22.0 が出力
# [1, 2, 3, 4]それぞれの2乗和12+22+32+42を求める
(numpy.arange(1, 5)**2).sum() # 30 が出力
Numpy
ベクトル
・numpy.array( ):ベクトルの定義
・len( ):ベクトルの次元(要素数)
・numpy.linalg.norm( ):ベクトルの大きさ
・numpy.dot(a, b):ベクトルの内積
・numpy.cross(a, b):ベクトルの外積 (クロス積)
a = numpy.array([1, 2])
print(a) # [1 2] が出力
# ベクトルの次元
a = numpy.array([1, 2])
b = numpy.array([1, 2, 3])
print(len(a)) # 2 が出力
print(len(b)) # 3 が出力
# ベクトルの大きさ(ノルム)
a = numpy.array([3, 4])
numpy.linalg.norm(a) # 5.0 が出力
b = numpy.array([1, 1, 1])
numpy.linalg.norm(b) # 1.7320508075688772 が出力
# ベクトルの和、差、スカラー倍
a = numpy.array([5, 7])
b = numpy.array([2, 3])
print(a+b) # [ 7 10] が出力
print(a-b) # [3 4] が出力
print(2*a) # [10 14] が出力
print(-3*b) # [-6 -9] が出力
# ベクトル\vec{a} とベクトル\vec{b} の内積はnumpy.dot(a, b)を使います。
# これは、内積はdot product(ドット積)とも呼ばれることに由来しています。
a = numpy.array([5, 7])
b = numpy.array([2, 3])
print(numpy.dot(a, b)) # 31 が出力
c = numpy.array([1, 2, 3])
d = numpy.array([2, 3, 4])
print(numpy.dot(c, d)) # 20 が出力
# 2つの空間ベクトル(3次元ベクトル)に対し、それらに垂直なベク トルが外積です。
# ベクトル\vec{a} とベクトル\vec{b} の外積はnumpy.cross(a, b)を使います。
# これは、外積がcross product(クロス積)とも呼ばれることに由来しています。
a = numpy.array([1, 2, 3])
b = numpy.array([-1, 0, 2])
print(numpy.cross(a, b)) # [ 4 -5 2] が出力
a = numpy.array([1, 0, 0]) # x軸
b = numpy.array([0, 1, 0]) # y軸
print(numpy.cross(a, b)) # [0 0 1] (z軸)が出力
行列
行ベクトルを集めたものが行列
・numpy.array( ):行列の定義
A[行-1, 列-1]:行列Aの(行, 列)成分を取得する。
Pythonルール:ナンバリングは0スタートより、1行(列)、2行(列)、3行(列)は、Pythonではそれぞれ0、1、2となります
・A.shape メソッド:行列Aの行と列をタプル(行, 列)として取得。
・A.size メソッド:行列Aの要素数を取得する
・numpy.dot(A, B):行列の積AB
・numpy.dot(A, x):行列Aとベクトルxの積
・numpy.linalg.inv(A):行列Aの逆行列(inverse matrix)
[逆行列を用いた方程式の解]
Av=cから、解ベクトル$${\vec{v}v}}$$を、
$${\vec{v}=A^{-1}cv=A−1c}$$として求める
A = numpy.array([[1, 2], [3, 4]])
print(A)
[[1 2]
[3 4]]
B = numpy.array([[1, 2, 3],[4, 5, 6],[7, 8, 9]])
print(B)
[[1 2 3]
[4 5 6]
[7 8 9]]
# 行列の形状
A = numpy.array([[1, 2], [3, 4]])
print(A.shape) # (2, 2) が出力
B = numpy.array([[1, 2, 3],[4, 5, 6],[7, 8, 9]])
print(B.shape) # (3, 3) が出力
C = numpy.array([[11, 12, 13], [21, 22, 23]])
print(C.shape) # (2, 3) が出力
# 要素数の取得
A = numpy.array([[1, 2], [3, 4]])
print(A.size) # 4 が出力
B = numpy.array([[1, 2, 3],[4, 5, 6],[7, 8, 9]])
print(B.size) # 9 が出力
C = numpy.array([[11, 12, 13], [21, 22, 23]])
print(C.size) # 6 が出力
# 行列の積ABABはnumpy.dot(A, B)
A = numpy.array([[1, 2], [3, 4]])
B = numpy.array([[1, 1], [1, 1]])
print(numpy.dot(A, B))
[[3 3]
[7 7]]
# 行列Aとベクトルxの積
A = numpy.array([[1, 2], [3, 4]])
x = numpy.array([5, 6])
print(numpy.dot(A, x)) # [17 39] が出力
print(A@x) # [17 39] が出力
# 方程式の解
# NumPyモジュールをインポートします
import numpy as np
# 係数行列Aの定義
A = np.array([[1,1],[2,4]])
# 右辺の50,156を列ベクトルcとして定義
c = np.array([50,156])
# 解ベクトルvをv=A^{-1}cとして計算
v = np.dot(np.linalg.inv(A), c)
# 解ベクトルの出力
v
標準モジュール
itertools 効率的なループ実行のためのイテレータ生成関数
・itertools.permutations() <- 順列
import pprint
card = ('a', 'b', 'c')
permutations = list(itertools.permutations(card))
pprint.pprint(permutatios)
output >>
[('a', 'b', 'c'),
('a', 'c', 'b'),
('b', 'a', 'c'),
('b', 'c', 'a'),
('c', 'a', 'b'),
('c', 'b', 'a')]
・itertools.combinations() <- 組合せ
card = ('a', 'b', 'c', 'd', 'e')
combinations = list(itertools.combinations(card, 3))
pprint.pprint(combinations)
output>>
[('a', 'b', 'c'),
('a', 'b', 'd'),
('a', 'b', 'e'),
('a', 'c', 'd'),
('a', 'c', 'e'),
('a', 'd', 'e'),
('b', 'c', 'd'),
('b', 'c', 'e'),
('b', 'd', 'e'),
('c', 'd', 'e')]
pprint データ出力の整然化
・pprint() <- Pythonの任意のデータ構造をインタープリタへの入力で使われる形式にして "pretty-print" できます
set 集合を扱う
・リスト型では要素に重複があるのに対し、set型では要素に重複はない
・リスト型では要素に順番があるのに対し、set型では要素に順番はない
s = {1, 2, 3, 1, 2, 1, 2, 3}
print(s) # {1, 2, 3} が出力
print(type(s)) # <class 'set'> が出力
s = {'a', 'c', 'b'}
print(s) # {'b', 'a', 'c'} が出力
print(type(s)) # <class 'set'> が出力
s = set(('dadcba'))
print(s) # {'b', 'd', 'a', 'c'} が出力
print(type(s)) # <class 'set'> が出力
s = {1, 2, 3}
s.add(4)
print(s) # {1, 2, 3, 4} が出力
s = {1, 2, 3}
s.remove(2)
print(s) # {1, 3} が出力
s = {1, 2, 3}
s.clear()
print(s) # set() が出力
A = set('abc')
B = set('bdce')
# 和集合
print(A|B) # {'b', 'd', 'a', 'e', 'c'} が出力
# 積集合
print(A&B) # {'b', 'c'} が出力
# 差集合
print(A - B) # {'a'} が出力
print(B - A) # {'d', 'e'} が出力
decimal (十進数)
小数と誤差 Python'0.1'問題を解決
"""
0.1 + 0.2 # 0.3 と出力
0.1 + 0.1 + 0.1 # 0.30000000000000004 と出力
0.1 + 0.1 + 0.1 == 0.3 # False と出力
0.1 + 0.1 == 0.2 # True と出力
"""
from decimal import Decimal
d1 = Decimal('0.1')
d3 = Decimal('0.3')
d1 + d1 + d1 == d3 # True と出力
type(d1) # <class 'decimal.Decimal'> と出力
format(d1 + d1 + d1,'.30f') # format(引数, '.30f')で引数を小数点以下30桁表示 '0.300000000000000000000000000000' と出力
format(d3,'.30f') # '0.300000000000000000000000000000' と出力
・getcontext().prec <- 有効数字の桁数の設定
random
・random.randint(a, b) <- aからbの範囲のランダムな整数値
標準関数
# 13 ÷ 4 = 3 余り 1
divmod(13, 4) # (3, 1) が出力される
・指数関数: a**x or pow(a, x)
2**3 # 8 が出力
pow(2, 3) # 8 を出力
この記事が気に入ったらサポートをしてみませんか?