深度学习进阶课程04---随机梯度下降算法实现

这篇文章写一下如何实现梯度下降算法
来实现一个简单的手写数字识别算法:
我们用的数据集是之间介绍过的MINIST数据集:
训练集(train):50000
验证集(validation):10000
测试(test):10000
下面来写一下如何具体的实现梯度下降算法
在这里插入图片描述
首先定义一个网络类:

class Network(object):
    
    def __init__(self,sizes):
        self.num_layers=len(sizes)
        self.sizes=sizes
        self.biases=[np.random.randn(y,1) for y in sizes[1:]]
        self.weights=[np.random.randn(y,x) for x,y in zip(sizes[:-1],sizes[1:])]#zip对传入的可循环的两组量产生新的量

sizes:每层神经元的个数,例如:第一层2个神经元,第二层3个神经元
则:net=Network([2,3,1])
np.random.randn(y,1):随机从正态分布(均值0,方差1)中生成
net.weights[1]存储连接第二层和第三层的权重(Python索引从0开始数)
来看一下我们的网络结构:

net=Network([2,3,1])
#np.random.randn(y,1):随机从正态分布(均值0,方差1)中生成
#net.weights[1]存储连接第二层和第三层的权重(Python索引从0开始数) 
print(net.num_layers)
print(net.sizes)
print(net.biases)
print(net.weights)

在这里插入图片描述
3表示有三层
[2,3,1]表示输入层神经元个数为2,隐藏层神经元个数为3,输出层神经元个数为1
array([[1.2437818],
[1.37606921],
[-0.14247446]]),array([[-0.88268682]])表示隐藏层三个神经元所对应的偏向和输出层神经元所对应的的偏向
在这里插入图片描述
表示隐藏层3个神经元分别和输入层两个神经元之间的权重以及输出层神经元和隐藏层三个神经元之间的权重
sigmoid funcition:
在这里插入图片描述

    def feedforward(self,a):
        "Return the output of the network if 'a' is inpit"
        for b,w in zip(self.biases,self.weights):
            a=sigmoid(np.dot(w,a)+b)
        return a

随机梯度下降算法

 def SGD(self,training_data,epochs,mini_batch_size,eta,test_data=None):
        '''Train the neural network using mini-batch stochastic gradient descent.
        The 'training_data' is a list of tuples'(x,y)'representing the training inputs
        and the desired outputs. The other non-optional parameters are self-explanatory.
        If  'test_data' is provided then the network will be evaluated against the test data
        after each epoch, and partial progress printed out. This is useful for tracking progress
        but slows things down substantially.'''
        if test_data:n_test=len(test_data)
        n=len(training_data)
        for j in xrange(epochs):
            random.shuffle(training_data)#打乱数据
            mini_batchs=[
                    training_data[k:k+mini_batch_size]#从数据集中随机抽取一部分
                    for k in xrange(0,n,mini_batch_size)]
            for mini_batch in mini_batchs:
                self.update_mini_batch(mini_batch,eta)#参数更新方程
            if test_data:
                print('Epoch {0}:{1}/{2}'.format(j,self.evaluate(test_data),n_test))
            else:
                print('Epoch {0} complete'.format(j))

参数更新方程
在这里插入图片描述

  def update_mini_batch(self,mini_batch,eta):
        '''Update the network's weights and biases by applying gradient descent
        using backpropagation to a single mini batch. The 'mini_batch' is a list of tuples
        (x,y),and 'eta' is the learning rate.'''
        nabla_b=[np.zeros(b.shape) for b in self.biases]
        nabla_w=[np.zeros(w.shape) for w in self.weights]
        
        for x,y in mini_batch:
            delta_nabla_b,delta_nabla_w=self.backprop(x,y)#backpropagation方法
            nabla_b=[nb+dnb for nb,dnb in zip(nabla_b,delta_nabla_b)]
            nabla_w=[nw+dnw for nw,dnw in zip(nabla_w,delta_nabla_w)]
        self.weights=[w-(eta/len(mini_batch))*nw for w,nw in zip(self.weights,nabla_w)]
        self.biases=[b-(eta/len(mini_batch)*nb) for b,nb in zip(self.biases,nabla_b)]

下面来说一下如何去github下载代码:
GitHub代码网址
可以参考我这一篇文章:
一招解决从GItHub下载文件过慢问题

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值