本文分享书中对“从Python Numpy实现单层感知机和神经网络的过程”的阅读理解。
一、引言
Numpy作为Python的类库,应用广泛,对于了解底层逻辑和实现,对于我们之后学习和了解深度学习框架和LLM开发很有帮助,是深度学习的基础库。
没有隐藏层的神经网络,叫单层感知机,也被广泛的称为神经元,它是一种二分类模型;包含隐藏层的神经网络,就是深度神经网络DNN,最简单的DNN就是只有一个隐藏层的DNN。
神经网络的模型调优通过反向传播和权重更新来实现,基本原理是梯度下降思想。
二、单层感知机numpy实现
文中实现了一个单层感知机,网络参数通过随机确定,不能得到准确的结果;通过训练对网络参数的优化,最后达到了预期目的。
我在实现过程中,出现了即便加大训练次数也不能改善学习效果的情况,然后又调整了学习率,也没有改善,最后我对权重和偏差参数的初值进行了设计,得到了准确的结果。
三、神经网络numpy实现
书中实现了一个简单的神经网络,相比于单层感知机的实现,反向传播的梯度计算稍微复杂一些,单层感知机在训练中是权重更新,多层感知网络则是基于链式法则,引入后向反馈,通过梯度算法,经过多轮训练得到网络参数。
参考书中代码,我进行了测试,运行正常,具体实现过程:(numpy代码解析)。
书中将神经网络以类的形式进行了封装(NeuralNetwork),蓝色方块内是我添加的语句,用来将返给外界调用者的变量初始化,forward是前馈网络,backward是反向传播,在训练时被调用来更正权重和偏差参数。
train是训练方法,蓝色方框内是我添加的语句,它将参数{轮数、损失、学习率}返给调用者,以便通过之后的图例进行比较。
calculate_loss方法计算损失,sigmoid是激活函数。
下面是对神经网络的调用,首先进行实例化给nn,采用(10,15,5)的网络结构,训练次数是10000,学习率为0.1。
下图是训练的损失曲线,可以看到学习率为0.1时的训练效果还是不错的。
四、实现、推广与比较
1、布尔运算的实现。
对于简单的基本布尔运算,如与、或、非运算,可以用单层感知机来实现。
通过numpy实现布尔和的单层感知机的处理,我发现对权重参数和偏差参数的初始值的选择对学习很关键,另外,我认为,布尔运算的例子可以通过对参数的简单设计轻松实现,同时也看出参数初值和超参数的选择是有技巧的,这与模型自身的特性(敏感度、鲁棒性等)是有关联的。
按照书中代码我进行了测试,发现对于单层感知机,对权重参数和激活函数的设计其实是很关键的,如果仅采用随机初值,增大训练次数和改变学习率等超参数,并不能有效的提升学习效果,这是我的一个试验体会,我考虑是由于布尔模型的固有特性的缘故,这从其损失值非0即1这一点上也可以看出一些端倪。
2、布尔运算网络。
多个单层感知机组成的布尔运算网络,依然是一种二分类器,例如用三个二分类器组成神经网络,对于神经网络的组成部分,布尔运算按照单层感知机给出权重和偏差,用含有一个隐藏层的神经网络来实现,并给出训练轮数及误差的比较,我把这个作为一个议题,留给感兴趣的人员进行讨论(思路:构建合适的损失函数,避免0-1振荡,来保证训练过程的收敛)。
五、小结与讨论
通过这一主题的学习,我实现了利用numpy库构建单层感知机和神经网络,并用来解决一些问题,对于LLM,网络参数十分庞大,所需算力资源都很可观,借助于深度学习框架,如tensorflow、pytorch、mxnet等,可以更加有效的解决这个问题,通过numpy构建神经网络的学习,为之后的进一步学习奠定了基础。
推荐阅读和参考资料:1、深度学习架构。
2、神经网络的PyTorch实现。