Pythonによるベクトルの合計の計算

ベクトルの定義と和の計算

リストによる定義と計算

Pythonでベクトルの計算をするときは、NumPyやSymPyモジュールを使うことは実用的ではありませんが、計算の流れを知るためリストによる表現からはじめます。ここでは、2つのベクトルv_a=(1, 2, 3)、v_b=(4, 5, 6)をリストとして定義し、これらの和を計算します。

  1. #1 ベクトルの定義
  2. v_a = [1, 2, 3]
  3. v_b = [4, 5, 6]

カウンタを使ってforループを回す方法

最も単純な方法を使ってリストv_s1でベクトルの和を計算します。

  1. #2 リストによるベクトルの和 ~ forループによる方法
  2. v_s1 = []
  3. for i in range(len(v_a)):
  4. v_s1.append(v_a[i]+v_b[i])
  5. v_s1

[5, 7, 9]

要素同士の合計なので、ベクトルv_s1を空のリストとして定義し、for文で各要素の合計を計算した結果をappendメソッドでリストに追加していきます。うまく計算することができたものの、v_aの長さ(次元数)を使いforループを回すのはスマートではありません。

zip関数を使ってforループを回す方法

次に、zip関数を使って、2つのリストから同時に要素を取り出す方法を試してみます。

  1. #3 ベクトルの和 ~ PythonらしくZipを使う方法
  2. v_s2 = []
  3. for x, y in zip(v_a, v_b):
  4. v_s2.append(x+y)
  5. v_s2

結果は、同じです。少しPythonらしくなりましたが、さらにリスト内包表記を使って計算します。

リスト内包表記による方法

Pythonらしい計算方法である、リスト内包表記によりベクトルの和を計算します。

  1. #4 リスト内包表記によるベクトルの和
  2. [x + y for x, y in zip(v_a, v_b)]

1行で計算できるのでとても便利ですが、リスト内包表記は2つのリストを扱うとわかりにくくなるのが難点です。

lambda式による方法

lambda式でも計算することができます。

  1. #5 lambda式によるベクトルの和
  2. list(map(lambda x,y:x+y,v_a,v_b))

結果はいずれも同じです。いずれも、通常のリストを使う方法によると、Pythonのプログラミングの練習にはなりますが、単純なベクトルの和の計算だけで手間がかかります。

NumPyによる定義と計算

NumPyモジュールを使うと簡単にベクトルの計算をすることができます。NumPyの配列にはndarrayとmatrixの2つの形式があり、表記の仕方が異なります。

Ndarrayによるベクトルの和の計算

まず、一般的なndarrayからです。 ndarray はN-dimensional array の略で、N次元配列という意味合いがあります。

  1. #6 Numpyのインポートと、ndarrayによるベクトルの和の計算
  2. import numpy as np
  3. na_a = np.array([1, 2, 3])
  4. na_b = np.array([4, 5, 6])
  5. na_a + na_b

array([5, 7, 9])

NumPyにはベクトル演算という機能があり、同じサイズの配列の算術演算では、同位要素(同じ場所の要素)ごとに計算されます。単純に足し算をするだけなのでとても簡単です。

matrixによる計算

次に、matrixによる方法です。

  1. #7 NumPyのmatrixによるベクトルの定義
  2. nm_a = np.matrix('1 2 3')
  3. nm_b = np.matrix('4 5 6')
  4. nm_a + nm_b

matrix([[5, 7, 9]])

ベクトルの定義が数値の配列なのに('1 2 3')と表現するところに注意が必要です。結果はmatrixの形式で返されます。NumPyは数値計算用のモジュールで、ベクトル計算も簡単になりますが、これだけならExcelの方が手っ取り早いように思われます。Pythonのすごさはここから先になります。

SymPyによる定義と計算

SymPyモジュールはPython library for symbolic mathematicsの略で、代数を扱うことができます。SymPy ではSymPy matricesとしてベクトルを扱います。

SymPyによるベクトルの定義と和の計算

はじめにベクトルを定義して和を計算します。

  1. #8 Sympyのインポートと、Matrixによるベクトルの定義と和の計算
  2. import sympy
  3. s_a = sympy.Matrix([1, 2, 3])
  4. s_b = sympy.Matrix([4, 5, 6])
  5. s_a + s_b

結果は次の通り縦のベクトルで表示されます。

SymPyによるベクトルの数値計算
SymPyによるベクトルの数値計算

SymPy matricesとしてベクトルを定義して和を計算します。結果は、縦のベクトルで表示されます。

SymPyによるベクトルの代数計算

単純なベクトルの和ではNumPyと何ら変わりはありませんが、SymPyのすごさは代数計算をすることができることです。

  1. #9 SymPyの代数計算によるベクトルの和の計算
  2. sympy.var('a_x,a_y,a_z,b_x,b_y,b_z')
  3. sv_a = sympy.Matrix([a_x, a_y, a_z])
  4. sv_b = sympy.Matrix([b_x, b_y, b_z])
  5. sv_s = sv_a + sv_b
  6. sv_s

Sympyによるベクトルの代数計算
Sympyによるベクトルの代数計算

Pythonは変数を明示的に定義しなくてもよい仕様になっていますが、SymPyでは、1行目のようにsympy.varでa_x,a_y,a_z,b_x,b_y,b_zとして定義しておく必要があります。次に、2つのベクトルの和をsv_sに変数として格納しています。

  1. #10 SymPyの代数に辞書形式で数値を代入
  2. sv_s.subs({a_x: 1, a_y: 2, a_z: 3, b_x: 4, b_y: 5, b_z: 6})

次に変数が格納されているベクトルにsubsメソッドで数値をしてすると、前例のように計算することができます。

  1. #11 SymPyの代数計算によるベクトルの和の計算
  2. sv_s.subs([(a_x, 1), (a_y, 2), (a_z, 3), (b_x, 4), (b_y, 5), (b_z, 6)])

結果は#8と同じように縦のベクトルで表示されます。