「.NET 開発基盤部会 Wiki」は、「Open棟梁Project」,「OSSコンソーシアム .NET開発基盤部会」によって運営されています。
ニューラルネットワークは、
「重み」のパラメタ(w1, w2, θ(-b))の決定は人手によって行われる。
という問題を、データから自動で「重み」のパラメタを学習することで解決する。
第0層 第1層 第2層~ 入力層 → 中間層(隠れ層) → 出力層
というように単一方向へのみ信号が伝播する。
ステップ関数とシグモイド関数とReUL関数がある。
なんとなくAPI仕様を知らないと難しい感じ。
"""This is a test program."""
import numpy as np
def step_function(x_1):
"""This is a test program."""
y_1 = x_1 > 0
return y_1.astype(np.int)"""This is a test program."""
import numpy as np
def step_function(x_1):
"""This is a test program."""
return np.array(x_1 > 0, dtype=np.int)-5.0 ~ 5.0までの0.1刻みのプロットをステップ関数にかけてグラフ化する。
"""This is a test program."""
import numpy as np
import matplotlib.pylab as plt
def step_function(x_1):
"""This is a test program."""
# 上記のいずれかの実装を選択。
X = np.arange(-5.0, 5.0, 0.1)
Y = step_function(X)
plt.plot(X, Y)
plt.ylim(-0.1, 1.1) # 図で描画するy軸の範囲を指定
plt.show()
1
h(x) = ────────
1 + exp(-x)
ポイントは、Pythonのブロードキャストによって配列も計算できる点。
"""This is a test program."""
import numpy as np
def sigmoid(x_1):
"""This is a test program."""
return 1 / (1 + np.exp(-x_1))
-5.0 ~ 5.0までの0.1刻みのプロットをシグモイド関数にかけてグラフ化する。
"""This is a test program."""
import numpy as np
import matplotlib.pylab as plt
def sigmoid(x_1):
"""This is a test program."""
return 1 / (1 + np.exp(-x_1))
X = np.arange(-5.0, 5.0, 0.1)
Y = sigmoid(X)
plt.plot(X, Y)
plt.ylim(-0.1, 1.1)
plt.show()
ReUL(Rectified Linear Unit)関数
┌
│0 ( a <= 0 )
y = h(a) = <
│a ( a > 0 )
└
"""This is a test program."""
import numpy as np
def relu(x_1):
"""This is a test program."""
return np.maximum(0, x)
-5.0 ~ 5.0までの0.1刻みのプロットをReUL関数にかけてグラフ化する。
"""This is a test program."""
import numpy as np
import matplotlib.pylab as plt
def relu(x_1):
"""This is a test program."""
return np.maximum(0, x_1)
X = np.arange(-5.0, 5.0, 0.1)
Y = relu(X)
plt.plot(X, Y)
plt.ylim(-0.1, 5.1)
plt.show()
バイアスと活性化関数を省略し重みだけとする。
X行列 * W行列=Y行列
┌ ┐ ┌ ┐ ┌ ┐
│a1 b1│ │a2 b2 c2│ = │a1a2+b1d2 a1b2+b1e2 a1c2+b1f2│
└ ┘ │ │ └ ┘
│d2 e2 f2│
└ ┘
X行列 W行列 Y行列
#ref(): File not found: "simple.png" at page "ニューラルネットワーク"
┌ ┐ ┌ ┐ ┌ ┐
│a b│ │1 3 5│ = │1a+2b 3a+4b 5a+6b│
└ ┘ │ │ └ ┘
│2 4 6│
└ ┘
X行列 W行列 Y行列
>>> x=np.array([1,2])
>>> x
array([1, 2])
>>> w=np.array([[1,3,5],[2,4,6]])
>>> w
array([[1, 3, 5],
[2, 4, 6]])
>>> y=np.dot(x,w)
>>> y
array([ 5, 11, 17])
#ref(): File not found: "3tier.png" at page "ニューラルネットワーク"
┌ ┐ │w(1)11 w(1)21 w(1)31│ │w(1)12 w(1)22 w(1)32│ └ ┘
h(A(1)) = Z(1)
そのまんま実装した。
"""This is a test program."""
import numpy as np
def sigmoid(x_1):
"""sigmoid."""
return 1 / (1 + np.exp(-x_1))
def identity_function(y_1):
"""出力層の活性関数"""
return y_1
# 第一層
X1 = np.array([1.0, 0.5])
W1 = np.array([[0.1, 0.3, 0.5], [0.2, 0.4, 0.6]])
B1 = np.array([0.1, 0.2, 0.3])
print("第一層")
A1 = np.dot(X1, W1) + B1
print("A1:" + str(A1))
Z1 = sigmoid(A1)
print("Z1:" + str(Z1))
# 第二層
X2 = Z1
W2 = np.array([[0.1, 0.4], [0.2, 0.5], [0.3, 0.6]])
B2 = np.array([0.1, 0.2])
print("第二層")
A2 = np.dot(X2, W2) + B2
print("A2:" + str(A2))
Z2 = sigmoid(A2)
print("Z2:" + str(Z2))
# 第三層
X3 = Z2
W3 = np.array([[0.1, 0.3], [0.2, 0.4]])
B3 = np.array([0.1, 0.2])
print("第三層")
A3 = np.dot(X3, W3) + B3
print("A3:" + str(A3))
Z3 = identity_function(A3)
print("Z3:" + str(Z3))
"""This is a test program."""
import numpy as np
def sigmoid(x_1):
"""sigmoid."""
return 1 / (1 + np.exp(-x_1))
def identity_function(y_1):
"""出力層の活性関数"""
return y_1
def init_network():
"""ニューラルネットワーク"""
network = {}
networkw = {}
networkw[0] = np.array([[0.1, 0.3, 0.5], [0.2, 0.4, 0.6]])
networkw[1] = np.array([[0.1, 0.4], [0.2, 0.5], [0.3, 0.6]])
networkw[2] = np.array([[0.1, 0.3], [0.2, 0.4]])
networkb = {}
networkb[0] = np.array([0.1, 0.2, 0.3])
networkb[1] = np.array([0.1, 0.2])
networkb[2] = np.array([0.1, 0.2])
network["W"] = networkw
network["b"] = networkb
return network
def forward(network, zzz):
"""ニューラルネットワークの実行"""
tier = len(network["W"])
for num in range(tier - 1):
print("第" + str(num + 1) + "層")
xxx = zzz
aaa = np.dot(xxx, network["W"][num]) + network["b"][num]
print("A" + str(num + 1) + ":" + str(aaa))
zzz = sigmoid(aaa)
print("Z" + str(num + 1) + ":" + str(zzz))
print("第" + str(tier) + "層")
xxx = zzz
aaa = np.dot(xxx, network["W"][tier -1]) + network["b"][tier -1]
print("A" + str(tier) + ":" + str(aaa))
zzz = identity_function(aaa) # 出力層の活性関数
print("Z" + str(tier) + ":" + str(zzz))
return zzz
print(forward(init_network(), np.array([1.0, 0.5])))
用いることができる。
を利用する。
入力をそのまま返す。
#ref(): File not found: "identity.png" at page "ニューラルネットワーク"
exp(Ak)
Yk = ───────────
n
Σexp(Ai)
i=1
シグモイド関数の項で説明した通り、
#ref(): File not found: "softmax.png" at page "ニューラルネットワーク"
>>> a=np.array([0.3, 2.9, 4.0]) >>> a array([ 0.3, 2.9, 4. ]) >>> exp_a = np.exp(a) >>> exp_a array([ 1.34985881, 18.17414537, 54.59815003]) >>> sum_exp_a = np.sum(exp_a) >>> sum_exp_a 74.122154210163302 >>> y = exp_a / sum_exp_a >>> y array([ 0.01821127, 0.24519181, 0.73659691]) >>>
"""This is a test program."""
import numpy as np
def softmax(aaa):
"""ソフトマックス関数"""
exp_a = np.exp(aaa)
sum_exp_a = np.sum(exp_a)
return exp_a / sum_exp_a
print(softmax(np.array([0.3, 2.9, 4.0])))ソフトマックス関数は指数関数を使用するため、オーバーフローし易い。
従って、ここでは、オーバーフロー対策について考える。
exp(Ak)
Yk = ───────────
n
Σexp(Ai)
i=1
C exp(Ak)
= ───────────
n
C Σexp(Ai)
i=1
exp(Ak + logeC)
= ───────────
n
Σexp(Ai + logeC)
i=1
exp(Ak + C')
= ───────────
n
Σexp(Ai + C')
i=1
(a+b) a b X = X * X
a logxC (a+logxC) X * X = X
"""This is a test program."""
import numpy as np
def softmax(aaa):
"""ソフトマックス関数"""
exp_a = np.exp(aaa - np.max(aaa))
sum_exp_a = np.sum(exp_a)
return exp_a / sum_exp_a
# print(softmax(np.array([0.3, 2.9, 4.0])))
print(softmax(np.array([1010, 1000, 990])))