吴恩达深度学习 (week3,4)

文章目录

  • 一、神经网络概述
  • 二、神经网络的表示
  • 三、神经网络的输出
  • 四、多个例子的向量化
  • 五、向量化实现的解释
  • 六、深度学习激活函数
  • 七、激活函数导数
  • 八、神经网络的梯度下降法
  • 九、深度学习随机初始化
  • 十、上述学习总结
    • 1、第一题
    • 2、第二题
    • 3、第三题
    • 4、第四题
    • 5、第五题
    • 6、第六题
    • 7、第7题
  • 十一、深层神经网络常识
  • 十二、深度学习前向和反向传播
  • 十三、编程大作业实现
    • 1、环境准备与数据集
    • 2、Logistic回归的分类效果
    • 2、定义神经网络结构
    • 3、初始化模型的参数
    • 4、sigmoid与tanh前向传播
    • 5、计算成本函数J
    • 6、反向传播(难点)
    • 7、更新参数和模型整合
    • 8、预测与运行

一、神经网络概述

推荐视频神经网络的本质与结构 3Blue1Brown

  • 前情提要:神经网络公式

在这里插入图片描述

  • 可以把许多sigmoid单元堆叠起来形成一个神经网络

在这里插入图片描述
在这里插入图片描述

在这里插入图片描述

		在逻辑回归中,通过直接计算 z 得到结果 a 。而这个神经网络中,我们反复的计算 z  和 a ,计算 a  和 z ,最后得到了最终的输出`loss function`。在逻辑回归中,有一些从后向前的计算用来计算导数 `da、dz` 。同样,在神经网络中我们也有从后向前的计算,看起来就像这样,最后会计算 da^[2]^、   dz^[2]^、   计算出来之后,然后计算dw^[2]^、   db^[2]^等,按公式3.4、3.5箭头表示的那样,从右到左反向计算。

基于逻辑回归重复使用了两次该模型得到上述例子的神经网络。

逻辑回归中的导数 ( da ) 和 ( dz ) 是损失函数关于预测概率 (a) 和线性组合输入 (z) 的偏导数,它们在反向传播算法中用于更新模型参数 (w) 和 (b)。具体来说:

  1. 导数 ( da ) 是损失函数 ( L(a,y) ) 相对于预测概率 ( a ) 的偏导数。根据二元交叉熵损失函数,我们有:
  • ( da = dL/da = -y/a + (1-y)/(1-a) )
  1. 导数 ( dz ) 是损失函数 ( L(a,y) ) 相对于 ( z ) 的偏导数,并且是通过链式法则从 ( da ) 推导得到的:
    • ( dz = dL/dz = da * a(1-a) )
  2. 在具体的梯度下降步骤中,我们会使用以下公式来更新参数 ( w ) 和 ( b ):
    • ( dw = X^Tdz ) (其中 ( X ) 是输入特征矩阵,( dz ) 是一个向量或矩阵,根据上下文而定)
    • ( db = dz ) (因为 ( b ) 是一个标量)

这些导数对于理解如何通过梯度下降来优化逻辑回归模型至关重要。在每次迭代中,我们计算这些导数值并用它们来调整 ( w ) 和 ( b ),以期减小损失函数的值,从而提高模型的预测性能。

二、神经网络的表示

下面的x1 x2 x3表示一个样本的三个特征值
在这里插入图片描述

  • 有输入特征 x 1 、 x 2 、 x 3 ,它们被竖直地堆叠起来,这叫做神经网络的输入层(Input Layer)。
  • 它包含了神经网络的输入;然后这里有另外一层我们称之为隐藏层(Hidden Layer)。
  • 在本例中最后一层只由一个结点构成,而这个只有一个结点的层被称为输出层(Output Layer),它负责产生预测值。
  • 隐藏层的含义:在一个神经网络中,使用监督学习训练它的时候,训练集包含了输入 x 也包含了目标输出 y ,所以术语隐藏层的含义是在训练集中,这些中间结点的准确值我们是不知道到的,也就是说你看不见它们在训练集中应具有的值。你能看见输入的值,你也能看见输出的值,但是隐藏层中的东西,在训练集中你是无法看到的。所以这也解释了词语隐藏层,只是表示你无法在训练集中看到他们。

现在我们再引入几个符号,就像我们之前用向量 x 表示输入特征。这里有个可代替的记号 a[0] 可以用来表示输入特征。 a 表示激活的意思,它意味着网络中不同层的值会传递到它们后面的层中,输入层将 x传递给隐藏层,所以我们将输入层的激活值称为 a[0]

下一层即隐藏层也同样会产生一些激活值,那么我将其记作 a[1],所以具体地,这里的第一个单元或结点我们将其表示为 a1[1],第二个结点的值我们记为 a2[2]以此类推。所以这里的是一个四维的向量如果写成Python代码,那么它是一个规模为4x1的矩阵或一个大小为4的列向量,如下公式,它是四维的,因为在本例中,我们有四个结点或者单元,或者称为四个隐藏层单元;

在这里插入图片描述

  • 最后输出层将产生某个数值 a ,它只是一个单独的实数,所以 y
    的值将取为 a[2] 这与逻辑回归很相似,在逻辑回归中,我们有 y
    ​直接等于 a ,在逻辑回归中我们只有一个输出层,所以我们没有用带方括号的上标。
  • 但是在神经网络中,我们将使用这种带上标的形式来明确地指出这些值来自于哪一层,有趣的是在约定俗成的符号传统中,在这里你所看到的这个例子,只能叫做一个两层的神经网络。原因是当我们计算网络的层数时,输入层是不算入总层数内,所以隐藏层是第一层,输出层是第二层。第二个惯例是我们将输入层称为第零层,所以在技术上,这仍然是一个三层的神经网络,因为这里有输入层、隐藏层,还有输出层。但是在传统的符号使用中,如果你阅读研究论文或者在这门课中,你会看到人们将这个神经网络称为一个两层的神经网络,因为我们不将输入层看作一个标准的层。

最后,我们要看到的隐藏层以及最后的输出层是带有参数的,这里的隐藏层将拥有两个参数 W和 b ,我将给它们加上上标 [1] ( W [1], b [1])

表示这些参数是和第一层这个隐藏层有关系的。之后在这个例子中我们会看到 W 是一个4x3的矩阵,而 b 是一个4x1的向量,第一个数字4源自于我们有四个结点或隐藏层单元,然后数字3源自于这里有三个输入特征,我们之后会更加详细地讨论这些矩阵的维数,到那时你可能就更加清楚了。相似的输出层也有一些与之关联的参数W [2], b [2] 从维数上来看,它们的规模分别是1x4以及1x1。1x4是因为隐藏层有四个隐藏层单元而输出层只有一个单元,之后我们会对这些矩阵和向量的维度做出更加深入的解释,所以现在你已经知道一个两层的神经网络什么样的了,即它是一个只有一个隐藏层的神经网络。

在这里插入图片描述

三、神经网络的输出

神经网络计算,从逻辑回归开始,如下图所示。用圆圈表示神经网络的计算单元,逻辑回归的计算有两个步骤,首先你按步骤计算出 z ,然后在第二步中以sigmoid函数为激活函数计算 z (得出 a ),一个神经网络只是这样子做了好多次重复计算。

在这里插入图片描述

在这里插入图片描述
如果执行神经网络的程序,用for循环来做这些看起来真的很低效。所以接下来我们要做的就是把这四个等式向量化。向量化的过程是将神经网络中的一层神经元参数纵向堆积起来,例如隐藏层中的 w 纵向堆积起来变成一个 (4,3) 的矩阵,用符号 W[1]表示。另一个看待这个的方法是我们有四个逻辑回归单元,且每一个逻辑回归单元都有相对应的参数——向量 w,把这四个向量堆积在一起,你会得出这4×3的矩阵。 因此, 公式3.8:

在这里插入图片描述
在这里插入图片描述

四、多个例子的向量化

[n]表示第n层,(i)表示第i个样本,下标表示样本的第几个特征

a[i](m)→其中i是神经网络的第几层(层数),m是第几个样本。行列式,行数代表层数,列数代表样本序号。

隐藏单元就是指每一层神经网络中的那些圆圈圈。

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
for循环是来遍历所有个训练样本。 定义矩阵 X 等于训练样本,将它们组合成矩阵的各列,形成一个 n 维或 n 乘以 m维矩阵。接下来计算见公式3.15:

以此类推,从小写的向量 x 到这个大写的矩阵 X ,只是通过组合 x 向量在矩阵的各列中。同理z[1](1), z[1](2) 等等都是 z [1](m) 的列向量,将所有 m 都组合在各列中,就的到矩阵 Z[1]

  • 同理a[1](1), a[1](2) ……a[1](m), 将其组合在矩阵各列中,如同从向量 x 到矩阵 X ,以及从向量 z 到矩阵 Z 一样,就能得到矩阵 A [1]

同样的,对于 Z[2]和A[2] ,也是这样得到。

这种符号其中一个作用就是,可以通过训练样本来进行索引。这就是水平索引对应于不同的训练样本的原因,这些训练样本是从左到右扫描训练集而得到的。

神经网络上通过在多样本情况下的向量化来使用这些等式。
在这里插入图片描述

横向是样本,竖向是隐藏层的节点

五、向量化实现的解释

在这里插入图片描述
吴恩达老师很细心的用不同的颜色表示不同的样本向量,及其对应的输出。所以从图中可以看出,当加入更多样本时,只需向矩阵 X中加入更多列。
在这里插入图片描述
所以从这里我们也可以了解到,之前我们对单个样本的计算要写成z[1](i)=W[1] x(i)+b[1] 这种形式,因为当有不同的训练样本时,将它们堆到矩阵 X 的各列中,那么它们的输出也就会相应的堆叠到矩阵 Z[1] 的各列中。现在我们就可以直接计算矩阵 Z[1] 加上 b[1] ,因为列向量 b[1] 和矩阵 Z[1] 的列向量有着相同的尺寸,而Python的广播机制对于这种矩阵与向量直接相加的处理方式是,将向量与矩阵的每一列相加。 所以这一节只是说明了为什么公式 Z [1]= W [1]X + b[1]是前向传播的第一步计算的正确向量化实现,但事实证明,类似的分析可以发现,前向传播的其它步也可以使用非常相似的逻辑,即如果将输入按列向量横向堆叠进矩阵,那么通过公式计算之后,也能得到成列堆叠的输出。

六、深度学习激活函数

在这里插入图片描述
结果表明,如果在隐藏层上使用函数 公式3.20: g (z[1]) = tanh ( z[1]) 效果总是优于sigmoid函数。因为函数值域在-1和+1的激活函数,其均值是更接近零均值的。在训练一个算法模型时,如果使用tanh函数代替sigmoid函数中心化数据,使得数据的平均值更接近0而不是0.5.

两者的优点是:

第一,在 z 的区间变动很大的情况下,激活函数的导数或者激活函数的斜率都会远大于0,在程序实现就是一个if-else语句,而sigmoid函数需要进行浮点四则运算,在实践中,使用ReLu激活函数神经网络通常会比使用sigmoid或者tanh激活函数学习的更快。

第二,sigmoidtanh函数的导数在正负饱和区的梯度都会接近于0,这会造成梯度弥散,而Relu和Leaky ReLu函数大于0部分都为常数,不会产生梯度弥散现象。(同时应该注意到的是,Relu进入负半区的时候,梯度为0,神经元此时不会训练,产生所谓的稀疏性,而Leaky ReLu不会有这问题)

z 在ReLu的梯度一半都是0,但是,有足够的隐藏层使得z值大于0,所以对大多数的训练数据来说学习过程仍然可以很快。

快速概括一下不同激活函数的过程和结论。

  • sigmoid激活函数:除了输出层是一个二分类问题基本不会用它。

  • tanh激活函数:tanh是非常优秀的,几乎适合所有场合。

  • ReLu激活函数:最常用的默认函数,,如果不确定用哪个激活函数,就使用ReLu或者Leaky ReLu。
    在这里插入图片描述

为什么需要非线性激活函数

  • 如果不设置激活函数,那么不论设置多少个隐藏层其实和设置一个隐藏层是一样的,也就是说没有激活函数,本质上都是单层的神经网络,只有有了激活函数才相当于真正扩展到了多层神经网络

七、激活函数导数

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

八、神经网络的梯度下降法

n是对于每层的节点数,比如w[1]行位置上的n[1]就是第一层那n[1]个节点,而列位置上的n[0]就是输入特征向量x有n[0]个特征,也就是输入层第0层有n[0]个节点]

n0是输入层元素个数,n1是第一层隐藏单元个数

在这里插入图片描述
在这里插入图片描述
上述是反向传播的步骤,注:这些都是针对所有样本进行过向量化, Y 是 1 ∗ m 的矩阵;这里np.sum是python的numpy命令,axis=1表示水平相加求和,keepdims是防止python输出那些古怪的秩数 ( n , ) 加上这个确保矩阵db[2]这个向量输出的维度为 ( n , 1 )这样标准的形式。

目前为止,我们计算的都和Logistic回归十分相似,但当你开始计算反向传播时,你需要计算,是隐藏层函数的导数,输出在使用sigmoid函数进行二元分类。这里是进行逐个元素乘积,因为 W[2]T dz[2]W 和 (Z[1] )这两个都为(n[1],m)矩阵;

还有一种防止python输出奇怪的秩数,需要显式地调用reshape把np.sum输出结果写成矩阵形式。

九、深度学习随机初始化

  • 当训练神经网络时,权重随机初始化是很重要的。对于逻辑回归,把权重初始化为0当然也是可以的。但是对于一个神经网络,如果你把权重或者参数都初始化为0,那么梯度下降将不会起作用。

在这里插入图片描述
在这里插入图片描述

十、上述学习总结

1、第一题

在这里插入图片描述

正解:BDEF
错因:
A:第2层的第12个神经元的激活值
C: 就是D描述
G: 就是B描述

2、第二题

在这里插入图片描述
正解:D

3、第三题

A = np.random.randn(4,3)
B = np.sum(A, axis = 1, keepdims = True)

B.shape是多少?

A.(4,) B.(1, 3) C.(, 3) D.(4, 1)

正解:D

首先,A = np.random.randn(4,3)创建了一个形状为(4, 3)的数组,即有4行3列的矩阵。

然后,B = np.sum(A, axis = 1, keepdims = True)对矩阵A进行操作,其中np.sum函数用于计算数组元素的和。参数axis = 1指定了沿着水平轴(即每一行内部)进行求和,而keepdims = True的作用是在求和后保持原有的维度不变,即不降维。

因此,经过这样的操作后,B的形状将变为(4, 1),也就是说,它仍然是一个4行的矩阵,但列数减少为1,因为原本每一行的3个元素被求和成了一个元素。

4、第四题

逻辑回归的权重w应该随机初始化,而不是全部初始化为全部零,否则,逻辑回归将无法学习有用的决策边界,因为它将无法“打破对称

这种说法并不准确。逻辑回归模型的权重w可以初始化为全零,这并不影响模型的学习能力和最终性能。

5、第五题

已经为所有隐藏的单位建立了一个使用tanh激活的网络。使用np.random.randn(…, …)*1000将权重初始化为相对较大的值。会发生什么?

A.没关系。只要随机初始化权重,梯度下降不受权重大小的影响。

B.这将导致tanh的输入也非常大,从而导致梯度也变大。因此,你必须将设置得非常小,以防止发散;这将减慢学习速度。

C.这将导致tanh的输入也非常大,导致单元被“高度激活”。与权重从小值开始相比,加快了学习速度。

D.这将导致tanh的输入也非常大,从而导致梯度接近于零。因此,优化算法将变得缓慢。

正解:D

在这里插入图片描述

6、第六题

考虑以下1个隐层的神经网络:
在这里插入图片描述

正解:BCEH

W[i]后面对应的是(i层的神经元数目,i-1层的神经元数目)⭐️⭐️⭐️⭐️⭐️

7、第7题

在这里插入图片描述

同一层的z的维度和A的相同,m是样本数目。
正解:C

十一、深层神经网络常识

在这里插入图片描述

以下面的图为例,深度学习常见记号

在这里插入图片描述

在这里插入图片描述

  • 权重矩阵的行数对应于当前层的神经元数量,列数对应于上一层的神经元数量。

核对矩阵维数

在这里插入图片描述

关于为什么要缓存z[l],因为dz[l] =da[l] dot(g[l] ′ (z [l]))
而dw[l]=a[l-1]dz[l],db[l]=dz[l],da[l-1]=w[l]Tdz[l]都间接(因为用到了dz[l])用到了z[l]

十二、深度学习前向和反向传播

在这里插入图片描述
搭建深层神经网络块

在这里插入图片描述
在这里插入图片描述

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

在这里插入图片描述

在这里插入图片描述

da又叫做a‘,导数的意思,这里是偏导数(梯度)

参数 vs 超参数

比如算法中的learning rate α \alphaα (学习率)、iterations(梯度下降法循环的数量)、 L LL (隐藏层数目)、 n [ l ] n^{[l]}n
[l]
(隐藏层单元数目)、choice of activation function(激活函数的选择)都需要你来设置,这些数字实际上控制了最后的参数 W WW 和 b bb 的值,所以它们被称作超参数。

十三、编程大作业实现

序幕:我们要建立一个神经网络,它有一个隐藏层。这个模型和上一个逻辑回归实现的模型有很大的区别。

  • 构建具有单隐藏层的2类分类神经网络。
  • 使用具有非线性激活功能激活函数tanh
  • 计算交叉熵损失(损失函数)。
  • 实现向前和向后传播。

1、环境准备与数据集

软件包环境:

numpy:是用Python进行科学计算的基本软件包。
sklearn:为数据挖掘和数据分析提供的简单高效的工具。
matplotlib :是一个用于在Python中绘制图表的库。

import numpy as np
import matplotlib.pyplot as plt
from testCases import *
import sklearn
import sklearn.datasets
import sklearn.linear_model
from planar_utils import plot_decision_boundary, sigmoid, load_planar_dataset, load_extra_datasetsnp.random.seed(1) #设置一个固定的随机种子,以保证接下来的步骤中我们的结果是一致的。

在这里插入图片描述
load_planar_dataset() 是一个用于加载平面数据集的函数。

  • 这个函数通常在机器学习和深度学习的教程或示例代码中出现,用于创建一个简单的二分类问题数据集。它返回两个矩阵,一个是特征矩阵X,另一个是对应的标签矩阵Y。
  • 在深度学习的背景下,load_planar_dataset() 可能会被用来演示如何使用神经网络来解决分类问题,特别是当数据不是线性可分的时候。例如,通过使用这个函数,可以生成一个类似于“鲜花形状”的数据集,其中包含两类不同的点,需要通过建立适当的模型来进行分类。

数据看起来像一朵红色(y = 0)和一些蓝色(y = 1)的数据点的花朵的图案。 我们的目标是建立一个模型来适应这些数据。现在,我们已经有了以下的东西:

    • X:一个numpy的矩阵,包含了这些数据点的数值
    • Y:一个numpy的向量,对应着的是X的标签【0 | 1】(红色:0 , 蓝色 :1

2、Logistic回归的分类效果

对照组

sklearn.linear_model.LogisticRegressionCV() 是一个用于逻辑回归分类的类,它结合了交叉验证和正则化。

该类使用L2正则化(岭回归)或L1正则化(套索回归),并使用交叉验证来选择最佳的正则化参数。它通过在训练集上进行多次拟合,每次使用不同的正则化参数,然后选择具有最高交叉验证得分的模型作为最终模型。

from sklearn.linear_model import LogisticRegressionCV# 创建 LogisticRegressionCV 对象
lrcv = LogisticRegressionCV(Cs=[1, 10, 100], cv=5, penalty='l2', solver='lbfgs', max_iter=100)# 拟合数据
lrcv.fit(X_train, y_train)# 预测新数据
y_pred = lrcv.predict(X_test)

在这里插入图片描述

这段代码是用于绘制逻辑回归模型的决策边界,并计算模型的准确性。

  • 首先,plot_decision_boundary(lambda x: clf.predict(x), X, Y) 这行代码调用了一个名为 plot_decision_boundary 的函数,该函数接受一个预测函数、特征矩阵 X 和标签向量 Y 作为参数。这里的预测函数是一个匿名函数 lambda x: clf.predict(x),它使用逻辑回归分类器 clf 对输入数据进行预测。(进行画红蓝分解图像)

  • 然后,LR_predictions = clf.predict(X.T) 这行代码使用逻辑回归分类器 clf 对特征矩阵 X 的转置进行预测,得到预测结果 LR_predictions

  • 最后,print("逻辑回归的准确性: %d " % float((np.dot(Y, LR_predictions) + np.dot(1 - Y, 1 - LR_predictions)) / float(Y.size) * 100) + "% " + "(正确标记的数据点所占的百分比)") 这行代码计算了逻辑回归模型的准确性。准确性是通过计算正确标记的数据点所占的百分比来得到的。这里使用了 np.dot() 函数来计算两个向量的点积,然后将结果除以标签向量 Y 的大小(即样本数量),再乘以 100 得到百分比。最后,将准确性以字符串的形式打印出来。

准确性只有47%的原因是数据集不是线性可分的,所以逻辑回归表现不佳(对照组),现在正式开始构建神经网络。

2、定义神经网络结构

在这里插入图片描述

理论公式可以看我之前写的博客

https://blog.csdn.net/QuantumYou/article/details/137249807?spm=1001.2014.3001.5502

在这里插入图片描述

def layer_sizes(X , Y):"""参数:X - 输入数据集,维度为(输入的数量,训练/测试的数量)Y - 标签,维度为(输出的数量,训练/测试数量)返回:n_x - 输入层的数量n_h - 隐藏层的数量n_y - 输出层的数量"""n_x = X.shape[0] #输入层n_h = 4 #,隐藏层,硬编码为4n_y = Y.shape[0] #输出层return (n_x,n_h,n_y)

3、初始化模型的参数

实现函数initialize_parameters()。确保我们的参数大小合适,如果需要的话,请参考上面的神经网络图。

我们将会用随机值初始化权重矩阵。

  • np.random.randn(a,b)* 0.01来随机初始化一个维度为(a,b)的矩阵。
    将偏向量初始化为零。

  • np.zeros((a,b))用零初始化矩阵(a,b)。

def initialize_parameters( n_x , n_h ,n_y):"""参数:n_x - 输入层节点的数量n_h - 隐藏层节点的数量n_y - 输出层节点的数量返回:parameters - 包含参数的字典:W1 - 权重矩阵,维度为(n_h,n_x)b1 - 偏向量,维度为(n_h,1)W2 - 权重矩阵,维度为(n_y,n_h)b2 - 偏向量,维度为(n_y,1)"""np.random.seed(2) #指定一个随机种子,以便你的输出与我们的一样。W1 = np.random.randn(n_h,n_x) * 0.01b1 = np.zeros(shape=(n_h, 1))W2 = np.random.randn(n_y,n_h) * 0.01b2 = np.zeros(shape=(n_y, 1))#使用断言确保我的数据格式是正确的assert(W1.shape == ( n_h , n_x ))assert(b1.shape == ( n_h , 1 ))assert(W2.shape == ( n_y , n_h ))assert(b2.shape == ( n_y , 1 ))parameters = {"W1" : W1,"b1" : b1,"W2" : W2,"b2" : b2 }return parameters

4、sigmoid与tanh前向传播

def forward_propagation( X , parameters ):"""参数:X - 维度为(n_x,m)的输入数据。parameters - 初始化函数(initialize_parameters)的输出返回:A2 - 使用sigmoid()函数计算的第二次激活后的数值cache - 包含“Z1”,“A1”,“Z2”和“A2”的字典类型变量"""W1 = parameters["W1"]b1 = parameters["b1"]W2 = parameters["W2"]b2 = parameters["b2"]#前向传播计算A2Z1 = np.dot(W1 , X) + b1A1 = np.tanh(Z1)Z2 = np.dot(W2 , A1) + b2A2 = sigmoid(Z2)#使用断言确保我的数据格式是正确的assert(A2.shape == (1,X.shape[1]))cache = {"Z1": Z1,"A1": A1,"Z2": Z2,"A2": A2}return (A2, cache)

5、计算成本函数J

def compute_cost(A2,Y,parameters):"""计算方程(6)中给出的交叉熵成本,参数:A2 - 使用sigmoid()函数计算的第二次激活后的数值Y - "True"标签向量,维度为(1,数量)parameters - 一个包含W1,B1,W2和B2的字典类型的变量返回:成本 - 交叉熵成本给出方程(13)"""m = Y.shape[1]W1 = parameters["W1"]W2 = parameters["W2"]#计算成本logprobs = logprobs = np.multiply(np.log(A2), Y) + np.multiply((1 - Y), np.log(1 - A2))cost = - np.sum(logprobs) / mcost = float(np.squeeze(cost))assert(isinstance(cost,float))return cost

6、反向传播(难点)

在这里插入图片描述

def backward_propagation(parameters,cache,X,Y):"""使用上述说明搭建反向传播函数。参数:parameters - 包含我们的参数的一个字典类型的变量。cache - 包含“Z1”,“A1”,“Z2”和“A2”的字典类型的变量。X - 输入数据,维度为(2,数量)Y - “True”标签,维度为(1,数量)返回:grads - 包含W和b的导数一个字典类型的变量。"""m = X.shape[1]W1 = parameters["W1"]W2 = parameters["W2"]A1 = cache["A1"]A2 = cache["A2"]dZ2= A2 - YdW2 = (1 / m) * np.dot(dZ2, A1.T)db2 = (1 / m) * np.sum(dZ2, axis=1, keepdims=True)dZ1 = np.multiply(np.dot(W2.T, dZ2), 1 - np.power(A1, 2))dW1 = (1 / m) * np.dot(dZ1, X.T)db1 = (1 / m) * np.sum(dZ1, axis=1, keepdims=True)grads = {"dW1": dW1,"db1": db1,"dW2": dW2,"db2": db2 }return grads

7、更新参数和模型整合

良好学习速率(收敛)梯度下降算法

在这里插入图片描述

不良学习速率(发散)梯度下降算法

在这里插入图片描述
图片来源Adam Harley⭐️

def update_parameters(parameters,grads,learning_rate=1.2):"""使用上面给出的梯度下降更新规则更新参数参数:parameters - 包含参数的字典类型的变量。grads - 包含导数值的字典类型的变量。learning_rate - 学习速率返回:parameters - 包含更新参数的字典类型的变量。"""W1,W2 = parameters["W1"],parameters["W2"]b1,b2 = parameters["b1"],parameters["b2"]dW1,dW2 = grads["dW1"],grads["dW2"]db1,db2 = grads["db1"],grads["db2"]W1 = W1 - learning_rate * dW1b1 = b1 - learning_rate * db1W2 = W2 - learning_rate * dW2b2 = b2 - learning_rate * db2parameters = {"W1": W1,"b1": b1,"W2": W2,"b2": b2}return parametersdef nn_model(X,Y,n_h,num_iterations,print_cost=False):"""参数:X - 数据集,维度为(2,示例数)Y - 标签,维度为(1,示例数)n_h - 隐藏层的数量num_iterations - 梯度下降循环中的迭代次数print_cost - 如果为True,则每1000次迭代打印一次成本数值返回:parameters - 模型学习的参数,它们可以用来进行预测。"""np.random.seed(3) #指定随机种子n_x = layer_sizes(X, Y)[0]n_y = layer_sizes(X, Y)[2]parameters = initialize_parameters(n_x,n_h,n_y)W1 = parameters["W1"]b1 = parameters["b1"]W2 = parameters["W2"]b2 = parameters["b2"]for i in range(num_iterations):A2 , cache = forward_propagation(X,parameters)cost = compute_cost(A2,Y,parameters)grads = backward_propagation(parameters,cache,X,Y)parameters = update_parameters(parameters,grads,learning_rate = 0.5)if print_cost:if i%1000 == 0:print("第 ",i," 次循环,成本为:"+str(cost))return parameters

8、预测与运行

def predict(parameters,X):"""使用学习的参数,为X中的每个示例预测一个类参数:parameters - 包含参数的字典类型的变量。X - 输入数据(n_x,m)返回predictions - 我们模型预测的向量(红色:0 /蓝色:1)"""A2 , cache = forward_propagation(X,parameters)predictions = np.round(A2)return predictions# 运行
parameters = nn_model(X, Y, n_h = 4, num_iterations=10000, print_cost=True)#绘制边界
plot_decision_boundary(lambda x: predict(parameters, x.T), X, Y)
plt.title("Decision Boundary for hidden layer size " + str(4))predictions = predict(parameters, X)
print ('准确率: %d' % float((np.dot(Y, predictions.T) + np.dot(1 - Y, 1 - predictions.T)) / float(Y.size) * 100) + '%')
  • predict函数,它接收两个参数:parametersXparameters是一个包含模型参数的字典,X是输入数据。

函数的主要目的是使用学习的参数为输入数据X中的每个示例预测一个类。首先,它调用forward_propagation函数,将Xparameters作为输入参数,返回A2cache。然后,通过对A2进行四舍五入操作(np.round(A2)),得到预测结果predictions。最后,函数返回预测结果predictions

在这里插入图片描述

注解:训练一个神经网络模型并绘制决策边界的。首先,通过调用nn_model函数来训练模型,传入输入数据X、标签Y、隐藏层大小n_h、迭代次数num_iterations和是否打印损失值print_cost等参数。然后,使用plot_decision_boundary函数绘制决策边界,传入预测函数(通过lambda x: predict(parameters, x.T)定义)、输入数据X和标签Y。接着,设置图表标题为"Decision Boundary for hidden layer size "加上隐藏层大小。最后,使用predict函数对输入数据X进行预测,并计算准确率,将结果打印出来。

  • 边界在机器学习中通常用于区分不同类别的数据。在这个例子中,决策边界是一条线或曲线,它将输入空间划分为两个区域:一个区域包含属于类别1的样本,另一个区域包含属于类别2的样本。通过绘制决策边界,我们可以直观地看到模型如何根据输入特征将数据点分类到不同的类别中。这对于理解模型的性能和进行模型评估非常有用。
    在这里插入图片描述

用于绘制不同隐藏层节点数量下的决策边界,并输出对应的准确率。首先设置画布大小为16x32,然后定义一个包含不同隐藏层节点数量的列表。接着使用循环遍历这个列表,每次循环中绘制一个子图,标题为当前隐藏层节点数量,调用nn_model函数训练模型,传入输入数据X、标签Y、当前隐藏层节点数量和迭代次数5000。然后调用plot_decision_boundary函数绘制决策边界,传入预测函数、输入数据X和标签Y。接着调用predict函数对输入数据X进行预测,计算准确率并输出。

  • 隐藏层节点数量是指神经网络中隐藏层的神经元数量。在这段代码中,隐藏层节点数量分别为1、2、3、4、5、20和50。

⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️⭐️

完结!

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

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

相关文章

关于Transformer的面试题

文章目录 前言1、Transformer模型1. 1 基本要点1.2 提升 2、BN和LN的区别和联系2.1 基本要点2.2 扩展 3、PreNorm和PostNorm的区别[链接](https://www.zhihu.com/question/519668254)4、Multi-head self-attention中为什么要用三个不同的矩阵 前言 Transformer大模型的一些问题…

【GEE实践应用】哨兵1号和2号数据叠加

目录 1.数据叠加代码 2.代码逐句解释 1.数据叠加代码 var geometry table; //table是我们提前导入的矢量数据 // 加载Sentinel-2影像 var sentinel2 ee.ImageCollection("COPERNICUS/S2").filterBounds(geometry) // geometry是你感兴趣区域的几何对象.filte…

Redis:发布和订阅

文章目录 一、介绍二、发布订阅命令 一、介绍 Redis的发布和订阅功能是一种消息通信模式,发送者(pub)发送消息,订阅者(sub)接收消息。这种功能使得消息发送者和接收者不需要直接建立连接,而是通…

商标没有去注册有哪些不好的影响!

有些商家咨询普推知产老杨,商标没有去注册有哪些不好的影响,其实对企业来说还有许多实际不利的影响,有时代价比注册一个商标要大很多。 想的商标名称没去注册商标,如果别人抢注拿下商标注册证,那就会涉及侵权&#xf…

工厂方法模式:解锁灵活的对象创建策略

在软件设计中,工厂方法模式是一种非常实用的创建型设计模式,它不仅提升了系统的灵活性,还简化了对象的创建过程。本文将详细探讨工厂方法模式的核心概念、实现方式、应用场景以及与其他设计模式的对比,旨在提供一份全面且实用的指…

磁悬浮鼓风机市场规模不断增长 我国行业发展面临挑战

磁悬浮鼓风机市场规模不断增长 我国行业发展面临挑战 磁悬浮鼓风机又称磁悬浮高速离心鼓风机,指基于磁悬浮技术制成的气体输送设备。磁悬浮鼓风机综合性能优良,属于高效节能磁悬浮动力装备,在众多领域需求旺盛。未来随着国家节能环保政策逐渐…

阿里云优惠口令2024最新

2024年阿里云域名优惠口令,com域名续费优惠口令“com批量注册更享优惠”,cn域名续费优惠口令“cn注册多个价格更优”,cn域名注册优惠口令“互联网上的中国标识”,阿里云优惠口令是域名专属的优惠码,可用于域名注册、续…

01—JavaScript概述

一、初识Javascript JavaScript一种直译式脚本语言,是一种动态类型、弱类型、基于原型的语言,内置支持类型。它的解释器被称为JavaScript引擎,为浏览器的一部分,广泛用于客户端的脚本语言,最早是在 HTML(标…

jsoncpp 编译和使用

原文链接: jsoncpp的编译和使用 jsoncpp 编译出库文件 1.从github仓库下载 2.下载 cmake 工具 3.生成VS项目 4.编译得到需要的库文件 jsoncpp 的使用 查看原文

基于Springboot的自习室预订系统

基于SpringbootVue的自习室预订系统的设计与实现 开发语言:Java数据库:MySQL技术:SpringbootMybatis工具:IDEA、Maven、Navicat 系统展示 用户登录页 网站首页 公告信息 留言反馈 后台管理 学生信息管理 公告信息管理 留言…

入门:多层感知器Multiple-Layer Perceiver, MLP

本文将简单介绍多层感知器(MLP)的基本概念、原理和应用。MLP是一种前馈人工神经网络,由多层节点组成,每层节点通过权重和偏置与下一层节点相连。MLP在许多领域都有广泛的应用,如分类、回归、自然语言处理等。 本文将分…

SRNIC、选择性重传、伸缩性、连接扩展性、RoCEv2优化(六)

参考论文SRDMA(A Scalable Architecture for RDMA NICs ):https://download.csdn.net/download/zz2633105/89101822 借此,对论文内容总结、加以思考和额外猜想,如有侵权,请联系删除。 如有描述不当之处&…

04异常Lambda算法正则

异常 异常是什么? 异常是代码在编译或者执行的过程中可能出现的错误。避免异常的出现,同时处理可能出现的异常,让代码更稳健。 异常分为几类? 编译时异常、运行时异常。编译时异常:没有继承RuntimeExcpetion的异常…

Linux: 工具: tshark 抓到了收方向的ESP明文包?

根据这个描述,看着是正常的, 抓到包之后,可以方便的分析问题,省去在wireshark里解码的问题。 经过调查发现是内核将ESP解开之后,如果是tunnel模式,内核又重新将skb丢给了interface去做处理。这样tshark/tcp…

Java基础(三)--常用工具类

文章目录 第三章、常用工具类一、Java异常1、什么是异常2、异常处理3、常见的异常类型4、throws5、throw6、自定义异常7、异常链 二、包装类1、包装类2、字符串与基本数据类型转换3、包装类的比较 三、String 类1、创建String对象的方法2、String的常用方法3、字符串的存储4、字…

360安全卫士去除广告方法

大安全时代,360 安全卫士为您提供全面安全服务,电脑端下载: https://urlqh.cn/orQqc 在当今数字化时代,网络安全已成为人们日常生活中的重要关切。在这片浩瀚的网络海洋中,360安全卫士犹如一座坚不可摧的灯塔&#xf…

基于微信公众号,搭建一套简单的电商支付环境(下)-- 微信公众号的对接

一、接着上文 上文把部署情况介绍了,侧重于网络及代理,本文选择把微信公众号的对接实现介绍一下。 还是那句话,微信官方的文档已非常详细,这里先摘抄一些重要的概念。 其次,待对接微信公众号的接口众多,…

Qt | 视频播放器(multimedia、multimediawidgets)

QT +=multimedia 通俗解释: 此代码行告诉编译器在构建应用程序时包含多媒体库。这意味着您的应用程序将能够播放和显示音频和视频文件。 使用分步说明构建模型: 创建一个新的 Qt 项目。 在 .pro 文件中添加以下行: QT += multimedia 导入必要的多媒体头文件: #include &l…

普乐蛙VR航天体验馆设备VR太空飞船VR元宇宙展厅

三天小长假就要来啦!五一假期也即将到来。老板们想捉住人流量这个财富密码吗?那快快行动起来!开启VR体验项目,假期赚翻天!小编亲测!!这款设备刺激好玩,想必会吸引各位家长小孩、学生…

java使用ShutdownHook优雅地停止服务

在Java程序中可以通过添加关闭钩子,实现在程序退出时关闭资源、平滑退出的功能。 使用Runtime.addShutdownHook(Thread hook)方法,可以注册一个JVM关闭的钩子,这个钩子可 这通常用于确保在应用程序退出时能够执行一些清理工作,比…