!date
!python --version
Fri Apr 25 02:07:59 AM UTC 2025
Python 3.11.12

更新履歴

  • 2025年4月25日: 1次元配列の注意を追加。

8. numpy入門#

8.1. 達成目標#

基本的な行列作成、演算、列参照できるようになろう。

8.2. 参考サイト#

8.3. チュートリアル#

import numpy as np

# 行列の作成
a = np.array([[1,2,3], [4,5,6]])
print(a)
print(type(a))
print(a.shape)
[[1 2 3]
 [4 5 6]]
<class 'numpy.ndarray'>
(2, 3)
#行の参照
a[0]
array([1, 2, 3])
#列の参照
a[:,0]
array([1, 4])
#スライス指定も可能
a[0:2]
array([[1, 2, 3],
       [4, 5, 6]])
a[:,0:2]
array([[1, 2],
       [4, 5]])
# 「行列 + 1」は全要素に対する和を実行
a + 1
array([[2, 3, 4],
       [5, 6, 7]])
# *演算子も同様。
a * 2
array([[ 2,  4,  6],
       [ 8, 10, 12]])
#行列演算ではない!
a * a
array([[ 1,  4,  9],
       [16, 25, 36]])
#転置行列
a.T
array([[1, 4],
       [2, 5],
       [3, 6]])
#内積を求めるにはdot関数を使う
np.dot(a, a.T)
array([[14, 32],
       [32, 77]])
#逆行列
np.linalg.inv(np.dot(a, a.T))
array([[ 1.42592593, -0.59259259],
       [-0.59259259,  0.25925926]])
#ゼロ行列、1行列、対角行列
print(np.zeros((2,3)))

print(np.ones((2,3)))

print(np.eye(3))
[[0. 0. 0.]
 [0. 0. 0.]]
[[1. 1. 1.]
 [1. 1. 1.]]
[[1. 0. 0.]
 [0. 1. 0.]
 [0. 0. 1.]]
#特定範囲内で幅を指定してサンプル点を用意。
#例えば、
# 「y=x**2」のグラフを描画したいとき、
# 定義域「-10〜10の範囲で0.1刻みでサンプル点を用意」みたいなときに便利。
np.arange(0, 1, 0.3)
array([0. , 0.3, 0.6, 0.9])
#np.arangeで始点、刻み幅を省略すると0から指定個数の整数を用意。
np.arange(8)
array([0, 1, 2, 3, 4, 5, 6, 7])
#行列の形を変形できる。
np.reshape(np.arange(6),(2,3))
array([[0, 1, 2],
       [3, 4, 5]])
#刻み幅はどうでも良いからサンプル数を指定したい場合に便利。
np.linspace(0,2,3)
array([0., 1., 2.])
np.linspace(0,2,4)
array([0.        , 0.66666667, 1.33333333, 2.        ])
#行列を結合できる。
#縦方向に結合
a = np.array([[1,2,3], [4,5,6]])
b = np.array([[7,8,9], [10,11,12]])
np.r_[a, b]
array([[ 1,  2,  3],
       [ 4,  5,  6],
       [ 7,  8,  9],
       [10, 11, 12]])
#横方向に結合
np.c_[a, b]
array([[ 1,  2,  3,  7,  8,  9],
       [ 4,  5,  6, 10, 11, 12]])

8.4. np.ndarray型の補足#

np.ndarray型では行列を2次元配列(≒二重リスト)として表現します。これに対しベクトルは1次元配列(≒通常のリスト)として表現します。このことは次のような想定外の動作に繋がりがちです。

# 行ベクトルを用意。
test1 = np.array([1,2])

# test1を転地して列ベクトルを用意。
test2 = test1.T

# test1,test2のshapeや出力を確認。
print(f"{test1.shape=}, {test2.shape=}") # test1,2のshapeが同じ??
print(f"{test1=}")
print(f"{test2=}") # test1と同じ???
test1.shape=(2,), test2.shape=(2,)
test1=array([1, 2])
test2=array([1, 2])

上記のように、1重リストで用意したデータは1次元配列として表現されるだけであり、行ベクトルとか列ベクトルという概念を持っていません。

一般的な意味での行ベクトルや列ベクトルのように扱いたい場合には、以下のように明確に区別して書き分ける必要があります。

8.4.1. case 1: np.zerosやnp.onesでサイズ指定して列ベクトルを用意する。#

# 5行1列の列ベクトルを用意したい場合、
# まず zp.zeros() を使ってサイズを指定してゼロベクトルを用意する。
test3 = np.zeros((5,1))
test3
array([[0.],
       [0.],
       [0.],
       [0.],
       [0.]])
# 用意した列ベクトルに対し、必要に応じて値を変更する。
test3[0] = 1
test3
array([[1.],
       [0.],
       [0.],
       [0.],
       [0.]])

8.4.2. case 2: 直接値を列挙して作成する。#

test4 = np.array([[1], # 1行目
                    [2], # 2行目
                    [3], # 3行目
                    [4], # 4行目
                    [5]]) # 5行目

print(f"{test4.shape=}")
print(f"{test4=}")
test4.shape=(5, 1)
test4=array([[1],
       [2],
       [3],
       [4],
       [5]])

8.5. 演習演習#

  • ベクトル演算の演習

    • (1) 5個の要素を持つ列ベクトルを作成せよ。値は全て1とする。

    • (2) 1で作成した列ベクトルのうち、2番目の要素を3.14に更新せよ。なおインデックスは0から数える(0番目、1番目、2番目、、)ものとする。

    • (3) 2で作成した列ベクトルを複製し、転置により行ベクトルに変換せよ。

    • (4) 用意した列ベクトルと行ベクトルの内積を求めよ。

    • (5) np.random.randを用いて、10個の要素を持つ列ベクトルを作成せよ。

  • 行列演算の演習行列演算の演習

    • (6) np.random.normalを用いて、平均値10、標準偏差2の正規分布に基づく、2行5列の行列を作成せよ。

    • (7) 6で作成した行列から、2列目の要素を抜き出だせ。

    • (8) 6で作成した行列から、3列目と4列目の要素を抜き出せ。

    • (9) np.random.randで5行2列の行列を用意し、6で用意した行列との積を求めよ。