BP神经网络的计算
最近学习了浙江大学的机器学习课程,又学习了一些内容,用python实现了BP神经网络
代码如下:
#定义sigmoid和它的导数
import numpy as np
import random,math
def make_matrix(m,n):
return np.random.random(size=(m,n))
def sigmoid(x):
return 1.0/(1.0+np.exp(-x))
def simgmoid_derivate(x):
return x*(1-x)
#定义类
class BPNeuralNetwork:
def __init__(self):
#输入层
self.input_n = 0
self.hidden_n = 0
self.output_n = 0
self.input_cells = []
self.hidden_cells = []
self.output_cells = []
self.input_weights = []
self.output_weights = []
self.input_correction = []
self.output_correction = []
def set_up(self,ni,nh,no):
self.input_n= ni
self.hidden_n = nh
self.output_n = no
#初始化cell
self.input_cells = [1.0] * self.input_n
self.hidden_cells = [1.0] * self.hidden_n
self.output_cells = [1.0] * self.output_n
# 初始化权重
self.input_weights = make_matrix(self.input_n,self.hidden_n)
self.output_weights = make_matrix(self.hidden_n,self.output_n)
#激活
#矫正矩阵
self.input_correction = make_matrix(self.input_n,self.hidden_n)
self.output_correction = make_matrix(self.hidden_n,self.output_n)
#第一次前馈
def predict(self,inputs):
for i in range(self.input_n):
self.input_cells[i] = inputs[i]
for j in range(self.hidden_n):
total = 0.0
for i in range(self.input_n):
total+=self.input_cells[i]* self.input_weights[i][j]
#若是连续的值需要修改激活函数
self.hidden_cells[j] = sigmoid(total)
#输出层计算
for k in range(self.output_n):
total = 0.0
for j in range(self.output_n):
total += self.hidden_cells[k]*self.output_weights[k][j]
self.output_cells[k] = sigmoid(total)
return self.output_cells[:]
#反向传播 学习率λ, 矫正率μ
def update(self,x,y,learn,correct):
self.predict(x)
#计算误差
output_deltas = [0.0]*self.output_n
for o in range(self.output_n):
error = y[0] -self.output_cells[0]
#如果是连续值则无需计算
output_deltas[o] = simgmoid_derivate(self.output_cells[o]) * error
#计算隐藏层的误差
hidden_deltas = [0.0] * self.hidden_n
for h in range(self.hidden_n):
for o in range(self.output_n):
change = output_deltas[o] * self.hidden_cells[h]
#更新权重
self.output_weights[h][o] += learn * change + correct * self.output_correction[h][o]
self.output_correction[h][o] = change
#更新权重
for i in range(self.input_n):
for h in range(self.hidden_n):
change=hidden_deltas[h] * self.input_cells[i]
self.input_weights[i][h] += learn * change + correct * self.input_correction[i][h]
self.input_correction[i][h] = change
#获得全局的误差
error = 0.0
for o in range(len(y)):
error += 0.5 * (y[o] - self.output_cells[o]) ** 2
return error
#开始训练设置迭代次数 学习率和矫正率
def train(self,x,y,limit=1000000,learn =0.05,correct =0.1):
for m in range(limit):
error =0.0
for i in range(len(x)):
#每次计算一个
x_item =x[i]
y_item = y[i]
error+= self.update(x_item,y_item,learn,correct)
最后测试一下
cases = [[1,1],
[2,2],
[2,4],
[1,2],
]
labels = [[0],[0],[1],[1]]
t= BPNeuralNetwork()
t.set_up(2,5,1)
t.train(cases,labels,10000,0.05,0.1)
for case in cases:
print(t.predict(case))
[0.5285172149874504]
[0.5343332825010273]
[0.5379687945071842]
[0.5336526221969785]
效果并不是很好,可能哪里需要完善。