Python写BP神经网络(二):带偏置的3层结构BPNN

理解了BP神经网络的原理,接下来实现一个结构比较完整的BP神经网络:3个输入节点,3个隐含层节点,2个输出节点。

对Numpy不是很熟悉,看例子琢磨了好久,才做通,还是不错。

一点体会:Numpy真是强。

这里是把4个样本一次性训练完,然后累积误差;然后下一个循环再次学习这4个样本。

这一点和教材把学习样本一个一个的学习,有点不一样。

import numpy as np

# --------------------------------------------
# 激活函数
# 当derive为True时,是对sigmoid函数求一阶导数后的函数,f'=y*(1-y)
def f_sigmoid(x, derive=False):
    if not derive:
        return 1 / (1 + np.exp(-x))
    else:
        return x * (1 - x)#这里的x实际上是f(x)

# --------------------------------------------

# 学习的样本,3个维度,共4个样本,因此是3x4的矩阵
X = np.array([[1, 1, 1],
              [1, 1, 2],
              [1, 2, 2],
              [2, 2, 2]])
# 预期输出,即监督值
Y = np.array([[0, 0],
              [0, 1],
              [1, 0],
              [1, 1]])
# Weights
np.random.seed(3)
# 4 x 3 ,说明隐藏层有3个结点,但是包括1个偏置
W = 2 * np.random.random((3, 3)) - 1
print('\nW=\n', W)
#
Bias1 = np.ones((4, 3)) * 0.1
print('Bias1=\n', Bias1)
#把Bias1要扩展成5x3,因为有5个样本,有3个隐含层节点

# 4 x 1 ,说明输出层有1个结点,包含了偏置之后,维度增加1
V = 2 * np.random.random((3, 2)) - 1
print('\nV=\n', V)
Bias2 = np.ones((4, 2)) * 0.1 #输出层偏置,设置为
print('Bias2=\n', Bias2)

#学习的速率
learn_rate = 0.95

#为隐含层的输入增加偏置向量
'''Bias_S = (2 * np.random.random((3, 1)) - 1).dot(np.array([[1, 1, 1]]))
print('Bias_S =\n', Bias_S)'''

MAX_LEARN_COUNT = 6000
nLearn_Count = 0
while nLearn_Count < MAX_LEARN_COUNT :
    #--------------------------------------------
    # 隐含层的结点总输入
    S = np.dot(X, W) + Bias1
    B = f_sigmoid(S)
    #--------------------------------------------
    # 输出层的计算
    L = np.dot(B, V) + Bias2
    C = f_sigmoid(L)
    #--------------------------------------------
    Diff = Y - C   # Diff是监督值与实际输出之间的误差,5x1 矩阵
    #print('\nCost=\n', Diff)
    zDiff = np.mean(np.abs(Diff)) #np.abs()把矩阵的元素逐个求绝对值,保存回原来的位置
    print('绝对误差值 zDiff={0}'.format(zDiff))

    Delta_C = Diff * f_sigmoid(C, True)
    ##print('#Delta_C=\n', Delta_C)  # Delta_C记录了

    Delta_V = np.dot(B.T, Delta_C)  # B相当于是输出层的输入,把每个节点的5次训练产生的delta_V累积了
    Delta_Bias2 = Delta_C.sum(axis=0) #按列求和,把每个输出节点的每个样本训练后的效果都累积下来
    ##print('Delta_Bias2=', Delta_Bias2)
    #print('Delta_V=\n', Delta_V)  # 记录了5次训练的Delta_V, 5x4 矩阵
    V = V + learn_rate * Delta_V
    Bias2 = Bias2 + learn_rate * Delta_Bias2
    ##print('调整后V=\n', V)
    #print('调整后Bias2=\n', Bias2)

    # 计算隐含层的权的调整
    Delta_B = np.dot(Delta_C, V.T) * f_sigmoid(B, derive=True)
    ##print('中间 Delta_B=\n', Delta_B)
    Delta_Bias1 = Delta_B.sum(axis=0)
    #print('Delta_Bias1=\n', Delta_Bias1)
    Delta_W = np.dot(X.T, Delta_B)  # 把多个样本的每个节点的偏差累积
    Bias1 = Bias1 + learn_rate * Delta_Bias1
    W = W + learn_rate * Delta_W

    #print('Delta_W=\n', Delta_W)
    nLearn_Count += 1
    #end of while
#-------------------------------------------------------------

你可能感兴趣的:(神经网络)