吴恩达深度学习笔记:深层神经网络(Deep Neural Networks)4.1-4.4

目录

  • 第一门课:神经网络和深度学习 (Neural Networks and Deep Learning)
    • 第四周:深层神经网络(Deep Neural Networks)
      • 4.1 深层神经网络(Deep L-layer neural network)
      • 4.2 前向传播和反向传播(Forward and backward propagation)
      • 4.3 深层网络中的前向传播(Forward propagation in a Deep Network)
      • 4.4 核对矩阵的维数(Getting your matrix dimensions right)

第一门课:神经网络和深度学习 (Neural Networks and Deep Learning)

第四周:深层神经网络(Deep Neural Networks)

4.1 深层神经网络(Deep L-layer neural network)

目前为止我们学习了只有一个单独隐藏层的神经网络的正向传播和反向传播,还有逻辑回归,并且你还学到了向量化,这在随机初始化权重时是很重要。

本周所要做的是把这些理念集合起来,就可以执行你自己的深度神经网络。
复习下前三周的课的内容:
1.逻辑回归,结构如下图左边。一个隐藏层的神经网络,结构下图右边:
在这里插入图片描述
注意,神经网络的层数是这么定义的:从左到右,由 0 开始定义,比如上边右图, x 1 x_1 x1 x 2 x_2 x2 x 3 x_3 x3,这层是第 0 层,这层左边的隐藏层是第 1 层,由此类推。如下图左边是两个隐藏层的神经网络,右边是 5 个隐藏层的神经网络。

在这里插入图片描述
严格上来说逻辑回归也是一个一层的神经网络,而上边右图一个深得多的模型,浅与深仅仅是指一种程度。记住以下要点:

有一个隐藏层的神经网络,就是一个两层神经网络。记住当我们算神经网络的层数时,我们不算输入层,我们只算隐藏层和输出层。

但是在过去的几年中,DLI(深度学习学院 deep learning institute)已经意识到有一些函数,只有非常深的神经网络能学会,而更浅的模型则办不到。尽管对于任何给定的问题很难去提前预测到底需要多深的神经网络,所以先去尝试逻辑回归,尝试一层然后两层隐含层,然后把隐含层的数量看做是另一个可以自由选择大小的超参数,然后再保留交叉验证数据上评估,或者用你的开发集来评估。

我们再看下深度学习的符号定义:
在这里插入图片描述
上图是一个四层的神经网络,有三个隐藏层。我们可以看到,第一层(即左边数过去第二层,因为输入层是第 0 层)有 5 个神经元数目,第二层 5 个,第三层 3 个。

我们用 L 表示层数,上图:𝐿 = 4,输入层的索引为“0”,第一个隐藏层 n [ 1 ] n^{[1]} n[1] = 5,表示有 5个隐藏神经元,同理 n [ 2 ] n^{[2]} n[2] = 5, n [ 3 ] n^{[3]} n[3] = 3, n [ 4 ] n^{[4]} n[4]= n [ L ] n^{[L]} n[L] =1(输出单元为 1)。而输入层, n [ 0 ] = n x = 3 n^{[0]} =n_x = 3 n[0]=nx=3

在不同层所拥有的神经元的数目,对于每层 l 都用 a [ l ] a^{[l]} a[l]来记作 l 层激活后结果,我们会在后面看到在正向传播时,最终能你会计算出 a [ l ] a^{[l]} a[l]

通过用激活函数 g计算 z [ l ] z^{[l]} z[l],激活函数也被索引为层数l,然后我们用 w [ l ] w^{[l]} w[l]来记作在 l 层计算 z [ l ] z^{[l]} z[l]值的权重。类似的, z [ l ] z^{[l]} z[l]里的方程b[l]也一样。

最后总结下符号约定:
输入的特征记作𝑥,但是𝑥同样也是 0 层的激活函数,所以 x = a [ 0 ] x = a^{[0]} x=a[0]
最后一层的激活函数,所以 a [ L ] a^{[L]} a[L]是等于这个神经网络所预测的输出结果。

4.2 前向传播和反向传播(Forward and backward propagation)

之前我们学习了构成深度神经网络的基本模块,比如每一层都有前向传播步骤以及一个相反的反向传播步骤,这次视频我们讲讲如何实现这些步骤。

先讲前向传播,输入 a [ l − 1 ] a^{[l−1]} a[l1],输出是 a [ l ] a^{[l]} a[l],缓存为 z [ l ] z^{[l]} z[l];从实现的角度来说我们可以缓存下 w [ l ] w^{[l]} w[l] b [ l ] b^{[l]} b[l],这样更容易在不同的环节中调用函数。
在这里插入图片描述
所以前向传播的步骤可以写成: z [ l ] = W [ l ] ⋅ a [ l − 1 ] + b [ l ] , a [ l ] = g [ l ] ( z [ l ] ) z^{[l]} = W^{[l]}⋅ a^{[l−1]} + b^{[l]} , a^{[l]} = g^{[l]}(z^{[l]}) z[l]=W[l]a[l1]+b[l],a[l]=g[l](z[l])
向量化实现过程可以写成: Z [ l ] = W [ l ] ⋅ A [ l − 1 ] + b [ l ] , A [ l ] = g [ l ] ( Z [ l ] ) Z^{[l]}= W^{[l]}⋅ A^{[l−1]} + b^{[l]} , A^{[l]} = g^{[l]}(Z^{[l]}) Z[l]=W[l]A[l1]+b[l],A[l]=g[l](Z[l])

前向传播需要喂入 A [ 0 ] A^{[0]} A[0]也就是X,来初始化;初始化的是第一层的输入值。 a [ 0 ] a^{[0]} a[0]对应于一个训练样本的输入特征,而 A [ 0 ] A^{[0]} A[0]对应于一整个训练样本的输入特征,所以这就是这条链的第一个前向函数的输入,重复这个步骤就可以从左到右计算前向传播。

下面讲反向传播的步骤:输入为𝑑𝑎[𝑙],输出为𝑑𝑎[𝑙−1],𝑑𝑤[𝑙], 𝑑𝑏[𝑙]
在这里插入图片描述

所以反向传播的步骤可以写成:
(1) d z [ l ] = d a [ l ] ∗ g [ l ] ′ ( z [ l ] ) dz^{[l]} = da^{[l]}∗ g^{[l]'}(z^{[l]}) dz[l]=da[l]g[l](z[l])
(2) d w [ l ] = d z [ l ] ⋅ a [ l − 1 ] dw^{[l]} = dz^{[l]}⋅ a^{[l−1]} dw[l]=dz[l]a[l1]
(3) d b [ l ] = d z [ l ] db^{[l]} = dz^{[l]} db[l]=dz[l]
(4) d a [ l − 1 ] = w [ l ] T ⋅ d z [ l ] da^{[l−1]} = w^{[l]T}⋅ dz^{[l]} da[l1]=w[l]Tdz[l]
(5) d z [ l ] = w [ l + 1 ] T d z [ l + 1 ] ∗ g [ l ] ′ ( z [ l ] ) dz^{[l]} = w^{[l+1]T}dz^{[l+1]}*g^{[l]'}(z^{[l]}) dz[l]=w[l+1]Tdz[l+1]g[l](z[l])
式子(5)由式子(4)带入式子(1)得到,前四个式子就可实现反向函数。

向量化实现过程可以写成:
(6) d Z [ l ] = d A [ l ] ∗ g [ l ] ′ ( Z [ l ] ) dZ^{[l]} = dA^{[l]}∗ g^{[l]'}(Z^{[l]}) dZ[l]=dA[l]g[l](Z[l])
(7) d W [ l ] = 1 m d Z [ l ] ⋅ A [ l − 1 ] T dW^{[l]} =\frac{1}{m}dZ^{[l]}⋅A^{[l−1]T} dW[l]=m1dZ[l]A[l1]T
(8) d b [ l ] = 1 m n p . s u m ( d z [ l ] , a x i s = 1 , k e e p d i m s = T r u e ) db^{[l]} =\frac{1}{m}np.sum(dz[l], axis = 1, keepdims =True) db[l]=m1np.sum(dz[l],axis=1,keepdims=True)
(9) d A [ l − 1 ] = W [ l ] T . d Z [ l ] dA^{[l−1]} = W^{[l]T}. dZ[l] dA[l1]=W[l]T.dZ[l]

总结一下:
在这里插入图片描述
第一层你可能有一个 ReLU 激活函数,第二层为另一个 ReLU 激活函数,第三层可能是sigmoid 函数(如果你做二分类的话),输出值,用来计算损失;这样你就可以向后迭代进行反向传播求导来求 d w [ 3 ] , d b [ 3 ] , d w [ 2 ] , d b [ 2 ] , d w [ 1 ] , d b [ 1 ] dw^{[3]},db^{[3]} ,dw^{[2]} ,db^{[2]} ,dw^{[1]} ,db^{[1]} dw[3]db[3]dw[2]db[2]dw[1]db[1]。在计算的时候,缓存会把 z [ 1 ] , z [ 2 ] , z [ 3 ] z^{[1]},z^{[2]},z^{[3]} z[1],z[2],z[3]传递过来,然后回传 d a [ 2 ] , d a [ 1 ] da^{[2]},da^{[1]} da[2]da[1] ,可以用来计算 d a [ 0 ] da^{[0]} da[0],但我们不会使用它,这里讲述了一个三层网络的前向和反向传播,还有一个细节没讲就是前向递归——用输入数据来初始化,那么反向递归(使用 Logistic 回归做二分类)——对 A [ l ] A^{[l]} A[l] 求导。

4.3 深层网络中的前向传播(Forward propagation in a Deep Network)

跟往常一样,我们先来看对其中一个训练样本 x 如何应用前向传播,之后讨论向量化的版本。

第一层需要计算 z [ 1 ] = w [ 1 ] x + b [ 1 ] , a [ 1 ] = g [ 1 ] ( z [ 1 ] ) z^{[1]} = w^{[1]}x + b^{[1]},a^{[1]} = g^{[1]}(z^{[1]}) z[1]=w[1]x+b[1]a[1]=g[1](z[1])(x可以看做 a [ 0 ] a^{[0]} a[0]
第二层需要计算 z [ 2 ] = w [ 2 ] a [ 1 ] + b [ 2 ] , a [ 2 ] = g [ 2 ] ( z [ 2 ] ) z^{[2]} = w^{[2]}a^{[1]} + b^{[2]},a^{[2]} = g^{[2]}(z^{[2]}) z[2]=w[2]a[1]+b[2]a[2]=g[2](z[2])
以此类推,第四层为 z [ 4 ] = w [ 4 ] a [ 3 ] + b [ 4 ] , a [ 4 ] = g [ 4 ] ( z [ 4 ] ) z^{[4]} = w^{[4]}a^{[3]} + b^{[4]},a^{[4]} = g^{[4]}(z^{[4]}) z[4]=w[4]a[3]+b[4]a[4]=g[4](z[4])
前向传播可以归纳为多次迭代 z [ l ] = w [ l ] a [ l − 1 ] + b [ l ] , a [ l ] = g [ l ] ( z [ l ] ) z^{[l]} = w^{[l]}a^{[l−1]} + b^{[l]},a^{[l]} = g^{[l]}(z^{[l]}) z[l]=w[l]a[l1]+b[l]a[l]=g[l](z[l])

在这里插入图片描述
向量化实现过程可以写成: Z [ l ] = W [ l ] a [ l − 1 ] + b [ l ] , A [ l ] = g [ l ] ( Z [ l ] ) ( A [ 0 ] = X ) Z^{[l]} = W^{[l]}a^{[l−1]} + b^{[l]},A^{[l]} = g^{[l]}(Z^{[l]}) (A^{[0]} = X) Z[l]=W[l]a[l1]+b[l]A[l]=g[l](Z[l])(A[0]=X)

这里只能用一个显式 for 循环,𝑙从 1 到𝐿,然后一层接着一层去计算。下一节讲的是避免代码产生 BUG,我所做的其中一件非常重要的工作。

4.4 核对矩阵的维数(Getting your matrix dimensions right)

当实现深度神经网络的时候,其中一个我常用的检查代码是否有错的方法就是拿出一张纸过一遍算法中矩阵的维数。
𝑤的维度是(下一层的维数,前一层的维数),即 w [ l ] : ( n [ l ] , n [ l − 1 ] ) w^{[l]}: (n^{[l]},n^{[l−1]}) w[l]:(n[l],n[l1])
𝑏的维度是(下一层的维数,1),即: b [ l ] : ( n [ l ] , 1 ) b^{[l]}: (n^{[l]},1) b[l]:(n[l],1)
z [ l ] , a [ l ] : ( n [ l ] , 1 ) z^{[l]},a^{[l]}:(n^{[l]}, 1) z[l],a[l]:(n[l],1);
d w [ l ] dw^{[l]} dw[l] w [ l ] w^{[l]} w[l]维度相同, d b [ l ] db^{[l]} db[l] b [ l ] b^{[l]} b[l]维度相同,且w和b向量化维度不变,但𝑧,𝑎以及𝑥的维度会向量化后发生变化。

在这里插入图片描述
向量化后:
Z [ l ] Z^{[l]} Z[l]可以看成由每一个单独的 Z [ l ] Z^{[l]} Z[l]叠加而得到, Z [ l ] = ( z [ l ] [ 1 ] , z [ l ] [ 2 ] , z [ l ] [ 3 ] , … , z [ l ] [ m ] ) Z^{[l]} = (z^{[l][1]},z^{[l][2]},z^{[l][3]},…,z^{[l][m]}) Z[l]=(z[l][1]z[l][2]z[l][3]z[l][m]),𝑚为训练集大小,所以 Z [ l ] Z^{[l]} Z[l]的维度不再是 ( n [ l ] , 1 ) (n^{[l]}, 1) (n[l],1),而是 ( n [ l ] , m ) (n^{[l]}, m) (n[l],m)
A [ l ] : ( n [ l ] , m ) , A [ 0 ] = X = ( n [ l ] , m ) A^{[l]}:(n^{[l]}, m),A^{[0]} = X = (n^{[l]}, m) A[l](n[l],m)A[0]=X=(n[l],m)

在这里插入图片描述
在你做深度神经网络的反向传播时,一定要确认所有的矩阵维数是前后一致的,可以大大提高代码通过率。下一节我们讲为什么深层的网络在很多问题上比浅层的好。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/302533.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

“逃离”OpenAI!36人出走,已拿600亿融资

“逃离”OpenAI!36人出走,已拿600亿融资© 由 智东西 提供 智东西 作者 | 程茜 编辑 | 心缘 最近OpenAI频繁高薪挖人,把马斯克惹毛了。 马斯克在社交平台X上公开爆料:OpenAI一直在高薪挖特斯拉工程师,甚至还想…

四、书城开发-2、热门搜索/推荐页面的开发

热门搜索的开发 热门搜索页面的交互主要有4个交互点 第一个交互是点击搜索框时,热门搜索会渐影显示;第二个交互是点击返回图标时热门搜索会渐影消失;第三个交互是热门搜索滑动页面的时候搜索栏下面会出现阴影,回到顶部时阴影会消…

深入浅出 -- 系统架构之微服务标准组件及职责

我们来认识一下微服务架构在Java体系中依托哪些组件实现的。 相对于单体架构的简单粗暴,微服务的核心是将应用打散,形成多个独立提供的微服务,虽然从管理与逻辑上更符合业务需要。但微服务架构也带来了很多急需解决的核心问题: 1…

PDF锐化

PDF Shaper Ultimate(pdf转图片) 编辑->添加文件->选中一个要处理的pdf 操作->转换->PDF转为图片 ComicEnhancerPro设置(把图片锐化) PDF Shaper Ultimate(图片转pdf) 编辑-添加图片->选中所有锐化处理后的图片 转换->图片转为pdf(会把所有图…

最新AI工具系统ChatGPT网站运营源码SparkAi系统V6.0版本,GPTs应用、AI绘画、AI换脸、垫图混图、Suno-v3-AI音乐生成大模型全支持

一、前言 SparkAi创作系统是基于ChatGPT进行开发的Ai智能问答系统和Midjourney绘画系统,支持OpenAI-GPT全模型国内AI全模型。本期针对源码系统整体测试下来非常完美,那么如何搭建部署AI创作ChatGPT?小编这里写一个详细图文教程吧。已支持GPT…

《深入Linux内核架构》第4章 进程虚拟内存(2)

目录 4.3 内存映射原理 4.4 数据结构 4.4.1 树和链表 4.4.2 虚拟内存区域VMA的表示 4.4.3 相关数据结构 本节讲VMA结构体struct vm_area_struct和struct address_space。 4.3 内存映射原理 所有进程的虚拟空间总和比物理内存大得多,因此只有最常用的虚拟空间…

生活日常韩语成人外语培训中为什么韩国人说话喜欢用“~도록”?

많이 받는 질문 중 하나가 ‘~도록’을 자신에게 쓸 수 있는가 하는 것이다. 즉 “제가 하도록 하겠습니다” “조심하도록 하겠습니다” “말씀드리도록 하겠습니다” 등과 같은 표현이다. 我经常被问到的问题之一就是能否将“~도록”用于自己。比如“我来做吧”、“我会小心…

深度学习500问——Chapter06: 循环神经网络(RNN)(2)

文章目录 6.4 CNN和RNN的区别 6.5 RNNs与FNNs有什么区别 6.6 RNNs训练和传统ANN训练异同点 6.7 为什么RNN训练的时候Loss波动很大 6.8 标准RNN前向输出流程 6.9 BPTT算法推导 6.9 RNN中为什么会出现梯度消失 6.10 如何解决RNN中的梯度消失问题 6.4 CNN和RNN的区别 类别特点描述…

sfml sdl2 windows vscode 调试和coderunner插件运行

链接库写在编译链接命令里,如果没有使用到不会加入到生成的可执行文件里。所以tasks.json可以这样写, {"version": "2.0.0","tasks": [{"type": "cppbuild","label": "C/C: g.exe 生…

Apache Pulsar源码解析之Lookup机制

文章目录 引言Lookup是什么客户端实现原理服务端实现原理总结 引言 在学习Pulsar一段时间后,相信大家也或多或少听说Lookup这个词,今天就一起来深入剖析下Pulsar是怎么设计的它吧 Lookup是什么 在客户端跟服务端建立TCP连接前有些信息需要提前获取&am…

arm-linux-gnueabihf-gcc默认目录

默认编译的头文件目录: /usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/arm-linux-gnueabihf/lib 默认编译的库文件目录: /usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/arm-linux-gnueabihf/include/ …

vscode 重命名很慢或失败 vscode renames are slow

网上问题, 插件问题(我遇见的排除,不是)被其他程序占用问题,(我这边是这个) 解决方案: 打开【资源管理器】,使用火绒 或其他软件,查看文件夹 or 文件 被哪个…

2024.4.9-day12-CSS 常用样式属性和字体图标

个人主页&#xff1a;学习前端的小z 个人专栏&#xff1a;HTML5和CSS3悦读 本专栏旨在分享记录每日学习的前端知识和学习笔记的归纳总结&#xff0c;欢迎大家在评论区交流讨论&#xff01; 文章目录 作业 作业 <!DOCTYPE html> <html lang"zh-CN"><he…

go之web框架gin

介绍 Gin 是一个用 Go (Golang) 编写的 Web 框架。 它具有类似 martini 的 API&#xff0c;性能要好得多&#xff0c;多亏了 httprouter&#xff0c;速度提高了 40 倍。 如果您需要性能和良好的生产力&#xff0c;您一定会喜欢 Gin。 安装 go get -u github.com/gin-gonic/g…

【C++】unordered 系列关联式容器

文章目录 1. unordered 系列关联式容器2. unordered_map2.1 unordered_map 的文档介绍2.2 unordered_map 的接口说明 3. unordered_set4. 在线 OJ 1. unordered 系列关联式容器 在 C 98 中&#xff0c;STL 提供了底层为红黑树结构的一系列关联式容器&#xff0c;在查询时效率可…

STM32中C编程引入C++程序

C具备类的创建思想很实用于实际场景多相似性的框架搭建&#xff1b;同种类型或相似类型的C的优势明显因此进行相互嵌套使用 需要在C中使用C类的话&#xff0c;你可以通过C的“extern "C"”语法来实现。这允许你在C代码中使用C的链接方式&#xff0c;而在C代码中使用…

实现RAG:使用LangChain实现图检索查询

你是不是有时会遇到这样的问题&#xff1a;你可能遇到的任何主题或问题&#xff0c;都有大量的文档&#xff0c;但是当尝试将某些内容应用于自己的用途时&#xff0c;突然发现很难找到所需的内容。 在这篇博文中&#xff0c;我们将看一下LangChain是如何实现RAG的&#xff0c;这…

kali基础渗透学习,永恒之蓝,木马实战

简介 kali的学习本质是在linux上对一些攻击软件的使用&#xff0c;只是学习的初期 先在终端切换到root用户&#xff0c;以便于有些工具对权限的要求 下载链接 镜像源kali 攻击流程 公网信息搜集 寻找漏洞&#xff0c;突破口&#xff0c;以进入内网 进入内网&#xff0c…

码蹄集部分题目(第五弹;OJ赛2024年第10期)

&#x1f40b;&#x1f40b;&#x1f40b;竹鼠通讯&#xff08;钻石&#xff1b;分治思想&#xff1b;模板题&#xff1a;就算几何平面点对问题&#xff09; 时间限制&#xff1a;3秒 占用内存&#xff1a;128M &#x1f41f;题目描述 在真空中&#xff0c;一块无限平坦光滑…

秋招算法刷题6

20240408 1.两数之和 &#xff08;时间复杂度是O&#xff08;n的平方&#xff09;&#xff09; public int[] twoSum(int[] nums, int target){int nnums.length; for(int i0;i<n;i){ for(int j1;j<n;j){ if(nums[i][j]target){ …