機械学習チートシート(ベクトル、行列、画像、Python)

Python による 機械学習 に向けて、プログラミングメモを作成しています。   (2019/12/24版)

環境、ライブラリ

In [1]:
import numpy as np
import matplotlib.pyplot as plt
np.random.seed(seed=0) # 乱数の種を指定
!python -V
Python 3.7.4

データの作成

ベクトル vector
In [2]:
l= [0, 1] # リスト   list.shapeは無い
v = np.array(l) # ベクトル化 vector、形状(2) np.array()
v12 = v.reshape((1, -1)) # 行ベクトル化、形状(1,2) Row vector 
v21 = v.reshape((-1, 1)) # 列ベクトル化、形状(2,1) Column vector 
print((list, v, v12, v21, v.shape, v12.shape, v21.shape))
print(v.tolist(), v12.tolist(), v21.tolist()) # リスト化 tolist()
vf = v.flatten() # flatten() -> ベクトル化
v12f = v12.flatten()
v21f = v21.flatten()
print([vf ,v12f ,v21f ,vf.shape, v12f.shape, v21f.shape])
(<class 'list'>, array([0, 1]), array([[0, 1]]), array([[0],
       [1]]), (2,), (1, 2), (2, 1))
[0, 1] [[0, 1]] [[0], [1]]
[array([0, 1]), array([0, 1]), array([0, 1]), (2,), (2,), (2,)]
In [3]:
a = np.arange(2) # 要素の取り出し
b = np.arange(2).reshape((1, 2)) # 行ベクトル Row vector
c = np.arange(2).reshape((2, 1)) # 列ベクトル Column vector 
(a[0] ,b[0] ,c[0], a[1], b[0,1], c[1,0], a.shape, b.shape, c.shape)
Out[3]:
(0, array([0, 1]), array([0]), 1, 1, 1, (2,), (1, 2), (2, 1))
In [4]:
a = np.array([])   # 空 行ベクトル  どちらも array([])
b = np.array([[]]) # 空 列ベクトル
(a, a.shape, a.tolist(), b, b.shape, b.tolist())
Out[4]:
(array([], dtype=float64),
 (0,),
 [],
 array([], shape=(1, 0), dtype=float64),
 (1, 0),
 [[]])
In [5]:
a = np.array([0] * 2)   # ゼロ 行ベクトル
b = np.array([[0]] * 2) # ゼロ 列ベクトル
(a, a.shape, b, b.shape)
Out[5]:
(array([0, 0]), (2,), array([[0],
        [0]]), (2, 1))
In [6]:
a = np.array([0, 1] * 2) # 繰り返し
b = np.array([[0, 1]] * 2) # 行ベクトル
c = np.array([[0],[1]] * 2) # 列ベクトル
(a, b, c, a.shape, b.shape, c.shape)
Out[6]:
(array([0, 1, 0, 1]), array([[0, 1],
        [0, 1]]), array([[0],
        [1],
        [0],
        [1]]), (4,), (2, 2), (4, 1))
In [7]:
np.concatenate([np.array([0] * 3) ,np.array([1] * 3)]) # ベクトルの結合
Out[7]:
array([0, 0, 0, 1, 1, 1])
In [8]:
a = np.arange(2).reshape((1, -1)) # 形状の推測 1つの次元だけ -1 を指定して、推測指定ができる
b = np.arange(2).reshape((-1, 1))
(a,b)
Out[8]:
(array([[0, 1]]), array([[0],
        [1]]))
In [9]:
a = np.array([0,1]) # arrayのネスト
b = np.array(a) # 何も起きない
c = np.array([a])
(a, b, c, a.shape, b.shape, c.shape)
Out[9]:
(array([0, 1]), array([0, 1]), array([[0, 1]]), (2,), (2,), (1, 2))
In [10]:
np.random.seed(seed=32) # 乱数 Seed有り
(np.random.randint(0, 2, 5), np.random.randint(0,10,10)) 
Out[10]:
(array([1, 1, 1, 0, 0]), array([8, 3, 7, 9, 3, 5, 9, 4, 1, 3]))
In [11]:
np.random.seed(seed=None) # 乱数 Seed無し
(np.random.randint(0, 2, 5), np.random.randint(0,10,10))
Out[11]:
(array([0, 1, 0, 0, 0]), array([8, 4, 0, 5, 5, 4, 4, 8, 6, 0]))
In [12]:
np.sin(np.linspace(0, np.pi, 4)) # sinデータ
Out[12]:
array([0.00000000e+00, 8.66025404e-01, 8.66025404e-01, 1.22464680e-16])
In [13]:
a = np.arange(5) # clip() 上下値制限
np.clip(a, 1, 3)
Out[13]:
array([1, 1, 2, 3, 3])
In [14]:
a = np.array([1.2, 2.6]) # 型変換  float -> int
b = np.round(a).astype(np.int32)
(b, a.dtype, b.dtype)
Out[14]:
(array([1, 3]), dtype('float64'), dtype('int32'))
In [15]:
a = np.arange(3).reshape(1,-1) # 行ベクトルの1つ取り出しは、リスト[]でなくarray[]になる。 
b = a[0]
print((a, b, a.shape, b.shape))
a = np.arange(3).reshape(-1,1) # 列ベクトルの1つ取り出しは、リスト[]でなくarray[]になる。 
b = a[0]
print((a, b, a.shape, b.shape))
(array([[0, 1, 2]]), array([0, 1, 2]), (1, 3), (3,))
(array([[0],
       [1],
       [2]]), array([0]), (3, 1), (1,))
In [16]:
a = np.array([[1]]) # flatten 動作確認  外側の[]が1つ削除されるのみ
b = a.flatten()
(a, a.shape, b, b.shape)
Out[16]:
(array([[1]]), (1, 1), array([1]), (1,))
In [17]:
fn1 = lambda x: 2 * x + 1 # 関数適用 制限有り 積和はOK、論理はNG  
fn2 = lambda x: 7 if 0 == x else 77 
v = np.arange(2).reshape((2, 1))
# fn2(v) ValueError: The truth value of an array with more than one element is ambiguous. Use a.any() or a.all()
fn2v = np.array(list(map(fn2,v))) # 動きが不安定、カーネルリセットが必要。
(fn1(v),fn2v)
Out[17]:
(array([[1],
        [3]]), array([ 7, 77]))
行列 matrix
In [18]:
np.arange(6).reshape((3, 2)) # 配列、matrix
Out[18]:
array([[0, 1],
       [2, 3],
       [4, 5]])
In [19]:
a = np.arange(4).reshape(2,2) # in 取り出し
(a[0], a[1])
Out[19]:
(array([0, 1]), array([2, 3]))
In [20]:
 2 * np.identity(2) * 3 # 単位行列、identity matrix
Out[20]:
array([[6., 0.],
       [0., 6.]])
In [21]:
x = np.arange(4).reshape((2, 2)) # zero行列 like
(np.zeros([2, 3]), np.zeros_like(x))
Out[21]:
(array([[0., 0., 0.],
        [0., 0., 0.]]), array([[0, 0],
        [0, 0]]))
In [22]:
a = np.arange(4 * 4).reshape((4, 4)) # 配列の切り出し
b = a[1:3,1:3]
(a,b)
Out[22]:
(array([[ 0,  1,  2,  3],
        [ 4,  5,  6,  7],
        [ 8,  9, 10, 11],
        [12, 13, 14, 15]]), array([[ 5,  6],
        [ 9, 10]]))

ベクトル、行列の四則演算 +-*/(Four arithmetic operations)

In [23]:
v = np.arange(4).reshape((2, 2))
2 * v * 5 # スカラー積 
Out[23]:
array([[ 0, 10],
       [20, 30]])
In [24]:
a =np.arange(4) + np.arange(4) # 和
b = np.arange(4)
b += np.arange(4)
(a, b)
Out[24]:
(array([0, 2, 4, 6]), array([0, 2, 4, 6]))
In [25]:
v = np.arange(4).reshape((2, 2)) #積 (単なる要素どうしの積)
v * v
Out[25]:
array([[0, 1],
       [4, 9]])
In [26]:
v = np.array([0, 1]) # ブロードキャスト -> [[0, 1],[0, 1]]
m = np.arange(4).reshape((2, 2))
(v * m , m * v) # (ベクトル * 行列、 行列 * ベクトル)
Out[26]:
(array([[0, 1],
        [0, 3]]), array([[0, 1],
        [0, 3]]))

ベクトル演算(Vector operation)

In [27]:
a = np.array([[1, 2]]) # 内積、inner product
(np.inner(a,a), a@a.T)
Out[27]:
(array([[5]]), array([[5]]))
In [28]:
a = np.array([[1, 2]]) # 外積、直積、outer product、vector product、direct product、tensor product
(np.outer(a,a),  a.T@a)
Out[28]:
(array([[1, 2],
        [2, 4]]), array([[1, 2],
        [2, 4]]))
In [29]:
v = np.array([1, 1]) # 長さ、ノルム0,1,2、norm、https://ja.wikipedia.org/wiki/ノルム
(np.linalg.norm(v), np.linalg.norm(v, ord=0), np.linalg.norm(v, ord=1), np.linalg.norm(v, ord=2)) 
Out[29]:
(1.4142135623730951, 2.0, 2.0, 1.4142135623730951)
In [30]:
v1 = np.array([1, 0]) # cos類似度、cos similarity、コサイン距離、https://ja.wikipedia.org/wiki/ベクトルのなす角
v2 = v1
np.dot(v1, v2) / (np.linalg.norm(v1) * np.linalg.norm(v2)) 
Out[30]:
1.0

行列演算(Matrix operation)

In [31]:
np.arange(6).reshape((2, 3)).T # 転置行列、 transposed matrix
Out[31]:
array([[0, 3],
       [1, 4],
       [2, 5]])
In [32]:
m = np.array([[0, 1], [2, 3]]) # m@v 行列ベクトル積 
v = np.array([0, 1]) 
(m @ v, np.dot(m,v), v @ m, np.dot(v,m))
Out[32]:
(array([1, 3]), array([1, 3]), array([2, 3]), array([2, 3]))
In [33]:
v = np.array([[0,1]]) # v@m  ベクトル行列積 = [2, 3]  2入力(1,2)@入力重み(2,2)(2ノード)
m = np.array([[0, 1], [2, 3]])
(v @ m, v, m, v.shape, m.shape)
Out[33]:
(array([[2, 3]]), array([[0, 1]]), array([[0, 1],
        [2, 3]]), (1, 2), (2, 2))
In [34]:
a = np.array([[0, 1], [2, 3]]) # 行列積、matrix product、array([[ 2,  3],[ 6, 11]])  
a @ a
Out[34]:
array([[ 2,  3],
       [ 6, 11]])
In [35]:
v = np.array([2]) # ??
vr = np.array([[1, 2]])
v @ vr
Out[35]:
array([2, 4])
In [36]:
m1 = np.array([[1, 0], [0, 2]]) # 逆行列  m1@m2 = I
m2 = np.array([[1, 0], [0, 0.5]]) # = https://ja.wikipedia.org/wiki/正則行列
(np.linalg.inv(m1), np.linalg.inv(m2), m1*m2, m2*m1)
Out[36]:
(array([[1. , 0. ],
        [0. , 0.5]]), array([[1., 0.],
        [0., 2.]]), array([[1., 0.],
        [0., 1.]]), array([[1., 0.],
        [0., 1.]]))
In [37]:
from scipy import linalg # 固有値 eigenvalue
# linalg.eigvals()
# Ax = λx を満たす零でないベクトル x とスカラー λ が存在するとき、x を A の固有ベクトル(右固有ベクトル)、λ を A の固有値と呼ぶ
# https://www.programcreek.com/python/example/62154/numpy.linalg.eigvals

リスト操作

In [38]:
[7] * 3 # 繰り返し
Out[38]:
[7, 7, 7]
In [39]:
[0, 1, 2][0] # 最初の要素
Out[39]:
0
In [40]:
[0, 1, 2][-1] # 最後の要素
Out[40]:
2
In [41]:
[0, 1, 2][-2] # 最後から2番目の要素
Out[41]:
1
In [42]:
len([0, 1, 2]) # 要素数
Out[42]:
3
In [43]:
a = [0, 1] + [2, 3] # 結合
b = [[0], [1], [2]] + [[0]]*3
(a, b)
Out[43]:
([0, 1, 2, 3], [[0], [1], [2], [0], [0], [0]])
In [44]:
list(zip([0, 1] ,[2, 3])) # zip
Out[44]:
[(0, 2), (1, 3)]
In [45]:
[x + y for (x, y) in zip([0, 1] ,[2, 3])] # 要素毎の加算
Out[45]:
[2, 4]
In [46]:
v = [0.5, 0.51] # map 
list(map(lambda x:round(x), v))
Out[46]:
[0, 1]

リスト スライス

In [47]:
a = [1, 2, 3, 4, 5, 6, 7, 8, 9] # 分割
(a[:3], a[3:])
Out[47]:
([1, 2, 3], [4, 5, 6, 7, 8, 9])
In [48]:
[1, 2, 3, 4, 5, 6, 7, 8, 9][1:] # 最初の要素以外
Out[48]:
[2, 3, 4, 5, 6, 7, 8, 9]
In [49]:
[1, 2, 3, 4, 5, 6, 7, 8, 9][:-1] # 最後の要素以外
Out[49]:
[1, 2, 3, 4, 5, 6, 7, 8]
In [50]:
[1, 2, 3, 4, 5, 6, 7, 8, 9][-3:] # 後ろの部分
Out[50]:
[7, 8, 9]
In [51]:
[1, 2, 3, 4, 5, 6, 7, 8, 9][:3] # 前の部分
Out[51]:
[1, 2, 3]
In [52]:
[1, 2, 3, 4, 5, 6, 7, 8, 9][1:7] # 途中の部分
Out[52]:
[2, 3, 4, 5, 6, 7]
In [53]:
[1, 2, 3, 4, 5, 6, 7, 8, 9][1:-1] # 途中の部分
Out[53]:
[2, 3, 4, 5, 6, 7, 8]
In [54]:
[1, 2, 3, 4, 5, 6, 7, 8, 9][1:7:2] # 2つ置き
Out[54]:
[2, 4, 6]
In [55]:
[1, 2, 3, 4, 5, 6, 7, 8, 9][::-1] # 逆順
Out[55]:
[9, 8, 7, 6, 5, 4, 3, 2, 1]
In [56]:
from sklearn.linear_model import LinearRegression # リッジ回帰  LinearRegression
# https://scikit-learn.org/stable/modules/generated/sklearn.linear_model.LinearRegression.html
X = np.array([[1, 1], [1, 2], [2, 2], [2, 3]])
# y = 1 * x_0 + 2 * x_1 + 3
y = np.dot(X, np.array([1, 2])) + 3
reg = LinearRegression().fit(X, y)
(reg.coef_, reg.intercept_, reg.predict(np.array([[3, 5]])))
Out[56]:
(array([1., 2.]), 3.0000000000000018, array([16.]))
In [57]:
def mean_quaared_error(y,t): # 2乗和誤差
    return 0.5 * np.sum((y-t)**2)
In [58]:
def numerical_diff(f, x): # 数値微分
    h = 1e-4 # 0.0001
    return (f(x+h) - f(x-h)) / (2*h)
In [59]:
def ReLU(x):  # ランプ関数、Rectified Linear Unit
    return np.maximum(0, x)

画像

In [60]:
from IPython.display import display_png
from PIL import Image, ImageDraw  # 新規に白黒イメージ作成、座標の原点(0, 0)は左上、白=255、黒=0
width = 64
height = 32
backcolor = 128
img = Image.new('L', (width, height),(backcolor))
for h in range(height):
    x = y = h
    img.putpixel((x, y), (255,))
draw = ImageDraw.Draw(img)
draw.rectangle((5, 10, 20, 20), fill=(0))
img.save('pict2_new.png')

display_png(img) # inline
%matplotlib inline
plt.imshow(img) # 着色される!
# img.show() # outline
(img.format, img.size, img.mode)
Out[60]:
(None, (64, 32), 'L')
In [61]:
# 公開画像リポジトリ
#「KITTI による車載カメラの映像」http://www.cvlibs.net/datasets/kitti/raw_data.php
In [62]:
from IPython.display import display_png
from PIL import Image  # 画像イメージ読み込み、切り出し  np.array版
import os
imgOrg = Image.open('pict0_org.png')
display_png(imgOrg)
imOrg = np.array(imgOrg) # (512,1392) で逆になっている!!!
small_size = 128
im_small = imOrg[:small_size, :small_size * 2]
img = Image.fromarray(im_small)
display_png(img) # 横長画像

imOrgT = imOrg.T # 転置行列
im_smallT =  imOrgT[:small_size, :small_size * 2]
imgT = Image.fromarray(im_smallT.T) 
display_png(imgT) # 縦長画像

# img.save('pict0_small.png')

(imOrg.dtype, imOrg.shape, img.mode, im_small.shape)  # RGB,L(白黒)  (dtype('uint8'), (512, 1392), 'L', (128, 256))
Out[62]:
(dtype('uint8'), (512, 1392), 'L', (128, 256))
In [63]:
 # 画像切り出しプログラム  非np.array版  入力:500, 200
from IPython.display import display_png
from PIL import Image  # 画像イメージ読み込み、切り出し
import os
imgOrg = Image.open('C:\\usr\\var\\12\\Reservoir\\video_1\\img_in\\0000000132.png')
display_png(imgOrg)
print("[imgOrg.format, imgOrg.size, imgOrg.mode]",[imgOrg.format, imgOrg.size, imgOrg.mode])
small_size = 128

''' 
while True:
    a = input("x y:") # 入力:500, 200
    if a == "q": break
    b = a.split()
    c = list(map(lambda x: int(x), b))
    print("[x,y]",c)
    img =imgOrg.crop((c[0], c[1] ,c[0] + small_size, c[1] + small_size)) # (left, upper, right, lower)
    display_png(img)
'''
([imgOrg.format, imgOrg.size, imgOrg.mode])
[imgOrg.format, imgOrg.size, imgOrg.mode] ['PNG', (1392, 512), 'L']
Out[63]:
['PNG', (1392, 512), 'L']

png からアニメーションPNGを作る(.png -> .apng)
apngasm_gui.exe APNG Assembler 2.9 https://sourceforge.net/projects/apngasm/files/2.9/

OS

In [64]:
import os # ディレクトリ、リスト、コピー
import shutil
os.getcwd()
# os.listdir(outDir)
# shutil.copy (fromFile, toFile) 
# os.makedirs(new_dir_path_recursive, exist_ok=True)    深い階層のディレクトリまで再帰的に作成
Out[64]:
'C:\\usr\\var\\12\\Reservoir'
In [65]:
# a = input('x y:') # プロンプト付きキー入力   12 34
# b = a.split()
# c = list(map(lambda x: int(x), b))
# [a,b,c] #  ['12 34', ['12', '34'], [12, 34]]
In [66]:
import datetime # 現在時刻
print(datetime.datetime.now())
datetime.datetime.now()
2019-12-24 18:43:12.825168
Out[66]:
datetime.datetime(2019, 12, 24, 18, 43, 12, 826168)

Python

In [67]:
round(1.234, 2) # 少数丸め、桁数指定
Out[67]:
1.23
In [68]:
s = '1234' # ゼロパディング
s.zfill(8)
Out[68]:
'00001234'
In [69]:
((1,), (2))  # 1要素のタプル (2)は2になりNG
Out[69]:
((1,), 2)
In [70]:
x = -3 # if 3項演算子
x if 0 < x  else 0
Out[70]:
0
In [71]:
for i, input in enumerate([5, 6]): # index付き繰り返し
    print(i,input)
for i, input in enumerate(np.arange(2)): # numpyでも使える
    print(i,input)
0 5
1 6
0 0
1 1
In [72]:
global Debug # グローバル変数
In [73]:
def f1(): # 局所関数定義
    def f2(): return 1
    return f2()
f1()
Out[73]:
1
In [74]:
# while True:   Repeat-until
#     ...
#      if cond: break

Jupyter Notebook

Jupyter Notebook の Prompt 番号 を連番にする方法

上部ツールバーで Kernel から「Clear all outputs & restart」を実行 上部ツールバーで Cell から 「Run All」を実行

セル内行番号の表示 ESC-l (Lの小文字)

その他

In [75]:
def f(loop_count): # 実行時間計測
    sum = 0
    for i in range(loop_count):
        sum += i
    print ("sum", sum)
%time f(100000)
sum 4999950000
Wall time: 5.05 ms
In [76]:
v = np.array([0, 1]) # デバッグ出力
print(v1,[v1],(v1,))  # 「array()」の有無が異なる
[1 0] [array([1, 0])] (array([1, 0]),)

ゼロから作るDeep Learning ―Pythonで学ぶディープラーニングの理論と実装 2016/9/24