提交 b7b9ef27 编写于 作者: W wizardforcel

2021-01-16 16:40:40

上级 2c597dec
......@@ -20,7 +20,7 @@
“第 2 章”,“神经网络的构建基块”,引入了神经网络的概念,并解释了当今的三种主要网络架构:人工神经网络,卷积神经网络和循环神经网络。 对于每种架构,都提供了训练过程和各层的说明。
“第 3 章”,“使用 DNN 的分类问题”,引入了要使用人工神经网络解决的现实数据问题。 探索了数据集的预处理以及定义和训练模型的过程,并通过使用误差分析提高了模型的准确
“第 3 章”,“使用 DNN 的分类问题”,引入了要使用人工神经网络解决的现实数据问题。 探索了数据集的预处理以及定义和训练模型的过程,并通过使用误差分析提高了模型的准确
“第 4 章”,“卷积神经网络”,详细介绍了卷积神经网络。 使用现实生活中的数据问题,您将学习如何构建网络架构并对其进行训练,以及如何通过使用数据扩充和批处理规范化来改善结果。
......
......@@ -18,7 +18,7 @@ PyTorch 于 2017 年推出,其主要特点是它使用**图形处理单元**
**深度学习**是机器学习的子集,它使用多层神经网络(大型神经网络),受人脑的生物结构启发,其中一层中的神经元接收一些输入数据,对其进行处理, 并将输出发送到下一层。 这些神经网络可以由成千上万个相互连接的节点(神经元)组成,大多数情况下组织在不同的层中,其中一个节点连接到上一层中的多个节点,从那里接收输入数据,还连接到上一层中的几个节点。 下一层,在处理完输出数据后,它将输出数据发送到下一层。
深度学习的普及是由于其准确。 对于诸如**自然语言处理****NLP**)之类的复杂数据问题,它已达到比其他算法更高的准确度。 深度学习的出色表现能力已经达到了机器可以胜过人类的水平,例如在欺诈检测中。 深度学习模型不仅可以优化流程,而且可以提高其质量。 这意味着在诸如安全性之类的出于安全原因至关重要的革命性领域(例如自动驾驶汽车)的进步。
深度学习的普及是由于其准确。 对于诸如**自然语言处理****NLP**)之类的复杂数据问题,它已达到比其他算法更高的准确度。 深度学习的出色表现能力已经达到了机器可以胜过人类的水平,例如在欺诈检测中。 深度学习模型不仅可以优化流程,而且可以提高其质量。 这意味着在诸如安全性之类的出于安全原因至关重要的革命性领域(例如自动驾驶汽车)的进步。
尽管神经网络在几十年前就已经理论化了,但神经网络最近变得流行有两个主要原因:
......@@ -51,7 +51,7 @@ PyTorch 于 2017 年推出,其主要特点是它使用**图形处理单元**
深度学习的一些正在开发中或正在使用的应用包括:
* **自动驾驶汽车**:诸如 Google 之类的多家公司一直在致力于开发部分或全部自动驾驶汽车,这些汽车通过使用数字传感器识别周围的物体来学习驾驶。
* **医学诊断**:深度学习通过提高诸如脑和乳腺癌等绝症的诊断准确,正在对该行业产生影响。 这是通过根据以前有或没有癌症的患者的标记 X 射线对新患者的 X 射线(或其他诊断影像机制)进行分类来完成的。
* **医学诊断**:深度学习通过提高诸如脑和乳腺癌等绝症的诊断准确,正在对该行业产生影响。 这是通过根据以前有或没有癌症的患者的标记 X 射线对新患者的 X 射线(或其他诊断影像机制)进行分类来完成的。
* **语音助手**:由于各种语音激活的智能助手(例如 Apple 的 Siri,Google Home 和亚马逊的 Alexa)的激增,它可能是当今最受欢迎的应用程序之一。
* **自动生成文本**:这意味着根据输入的句子生成新文本。 这通常用于电子邮件编写中,其中电子邮件提供者根据已编写的文本向用户建议接下来的几个单词。
* **广告**:在商业世界中,深度学习通过瞄准合适的受众并制作更有效的广告来帮助提高广告系列的投资回报。 这样的一个例子是生成内容,以产生最新的和信息丰富的博客,以帮助吸引当前客户并吸引新客户。
......@@ -314,7 +314,7 @@ loss_funct = nn.MSELoss()
首先,导入模块。 然后,定义模型架构。 `input_units`表示输入数据包含的要素数量,`hidden_​​units`表示隐藏层的节点数量, `output_units`表示 输出层的节点。
从前面的代码中可以看出,网络的架构包含一个隐藏层,其后是 ReLU 激活功能和一个输出层,然后是一个 S 型激活功能,从而使其成为两层网络。
从前面的代码中可以看出,网络的架构包含一个隐藏层,其后是 ReLU 激活函数和一个输出层,然后是一个 S 型激活函数,从而使其成为两层网络。
最后,损失函数定义为**均方误差****MSE**)。
......
......@@ -122,13 +122,13 @@ Rosenblatt 还介绍了权重的概念(`w`1,`w`2,…,`w`n),这些数
在这里,如前所述,`X`是指输入数据,`W`是确定输入数据重要程度的权重,`b`是 偏差值和 sigma(![1](img/B15778_02_Formula1.png))表示应用于线性函数的激活函数。
激活函数的目的是将非线性引入模型。 有不同的激活功能可供选择,当今最常用的激活功能列表如下:
激活函数的目的是将非线性引入模型。 有不同的激活函数可供选择,当今最常用的激活函数列表如下:
* **Sigmoid**:这是 S 形,它基本上将值转换为 0 到 1 之间的简单概率,其中通过 S 形函数获得的大多数输出​​将接近 0 和 1 的极限。
![Figure 2.7: Sigmoid activation function ](img/B15778_02_07.jpg)
图 2.7:乙状结肠激活功能
图 2.7:乙状结肠激活函数
下图显示了 S 型激活函数的图形表示:
......@@ -140,7 +140,7 @@ Rosenblatt 还介绍了权重的概念(`w`1,`w`2,…,`w`n),这些数
![Figure 2.9: Softmax activation function ](img/B15778_02_09.jpg)
图 2.9:Softmax 激活功能
图 2.9:Softmax 激活函数
考虑到其输出是概率,因此通常在分类网络的输出层中找到此激活函数。
......@@ -148,7 +148,7 @@ Rosenblatt 还介绍了权重的概念(`w`1,`w`2,…,`w`n),这些数
![Figure 2.10: Tanh activation function ](img/B15778_02_10.jpg)
图 2.10:Tanh 激活功能
图 2.10:Tanh 激活函数
下图显示了 **tanh** 激活函数的图形表示:
......@@ -160,19 +160,19 @@ Rosenblatt 还介绍了权重的概念(`w`1,`w`2,…,`w`n),这些数
![Figure 2.12: ReLU activation function ](img/B15778_02_12.jpg)
图 2.12:ReLU 激活功能
图 2.12:ReLU 激活函数
按照惯例,此激活功能用于所有隐藏层。 我们将在本章的后续部分中了解有关隐藏层的更多信息。 下图显示了 ReLU 激活功能的图形表示:
按照惯例,此激活函数用于所有隐藏层。 我们将在本章的后续部分中了解有关隐藏层的更多信息。 下图显示了 ReLU 激活函数的图形表示:
![Figure 2.13: Graphical representation of the ReLU activation function ](img/B15778_02_13.jpg)
图 2.13:ReLU 激活功能的图形表示
图 2.13:ReLU 激活函数的图形表示
### 损失函数的计算
一旦正向传播完成,训练过程的下一步就是计算损失函数,以通过比较预测相对于地面真实值的好坏来估计模型的误差。 考虑到这一点,要达到的理想值为 0,这意味着两个值之间没有差异。
这意味着训练过程的每次迭代的目标是通过更改在前向通过过程中用于执行计算的参数(权重和偏差)来最小化损失函数。
这意味着训练过程的每次迭代的目标是通过更改在正向传播过程中用于执行计算的参数(权重和偏差)来最小化损失函数。
同样,有多种损失函数可供选择。 但是,用于回归和分类任务的最常用损失函数如下:
......@@ -282,7 +282,7 @@ Rosenblatt 还介绍了权重的概念(`w`1,`w`2,…,`w`n),这些数
## 卷积神经网络简介
**卷积神经网络****CNN**)主要用于计算机视觉领域,在最近几十年中,机器达到的准确水平超过了人类的能力。
**卷积神经网络****CNN**)主要用于计算机视觉领域,在最近几十年中,机器达到的准确水平超过了人类的能力。
CNN 创建的模型使用神经元的子组来识别图像的不同方面。 这些组应该能够相互通信,以便它们可以一起形成完整的图像。
......@@ -322,7 +322,7 @@ CNN 创建的模型使用神经元的子组来识别图像的不同方面。 这
2. **Pooling layers**: Although convolutional layers are capable of extracting relevant features from images, their results can become enormous when analyzing complex geometrical shapes, which would make the training process impossible in terms of computational power, hence the invention of pooling layers.
这些层不仅实现了减少卷积层输出的目标,而且还消除了已提取特征中存在的任何噪声,最终最终有助于提高模型的准确
这些层不仅实现了减少卷积层输出的目标,而且还消除了已提取特征中存在的任何噪声,最终最终有助于提高模型的准确
可以应用两种主要类型的池化层,其背后的想法是检测在图像中表现出较强影响的区域,以便可以忽略其他区域。
......@@ -401,7 +401,7 @@ RNN 允许以输入序列,输出序列或什至同时以两种形式处理数
EDA 流程很有用,因为它有助于开发人员发现对于定义操作过程至关重要的信息。 此处说明此信息:
1. **数据量**:这既指实例数,也指特征数。 前者对于确定是否有必要甚至有可能使用神经网络甚至是深度神经网络解决数据问题至关重要,因为考虑到此类模型需要大量数据才能达到较高的准确。 另一方面,后者对于确定是否提前开发某些特征选择方法以减少特征数量,简化模型并消除任何冗余信息是否有用是有用的。
1. **数据量**:这既指实例数,也指特征数。 前者对于确定是否有必要甚至有可能使用神经网络甚至是深度神经网络解决数据问题至关重要,因为考虑到此类模型需要大量数据才能达到较高的准确。 另一方面,后者对于确定是否提前开发某些特征选择方法以减少特征数量,简化模型并消除任何冗余信息是否有用是有用的。
2. **目标特征**:对于受监督的模型,需要标记数据。 考虑到这一点,选择目标特征(我们希望通过构建模型来实现的目标)以评估特征是否具有许多缺失值或离群值非常重要。 此外,这有助于确定开发目标,该目标应与可用数据一致。
3. **Noisy data/outliers**: Noisy data refers to values that are visibly incorrect, for instance, a person who is 200 years old. On the other hand, outliers refer to values that, although they may be correct, are very far from the mean, for instance, a 10-year-old college student.
......@@ -526,7 +526,7 @@ EDA 流程很有用,因为它有助于开发人员发现对于定义操作过
## 数据缩放
尽管不需要重新缩放数据就可以将其馈送到算法中进行训练,但是如果您希望提高模型的准确,这是重要的一步。 这主要是因为每个特征具有不同的比例可能会导致模型假定给定特征比其他特征更重要,因为它具有更高的数值。
尽管不需要重新缩放数据就可以将其馈送到算法中进行训练,但是如果您希望提高模型的准确,这是重要的一步。 这主要是因为每个特征具有不同的比例可能会导致模型假定给定特征比其他特征更重要,因为它具有更高的数值。
以两个特征为例,一个特征测量一个人的孩子数量,另一个特征描述一个人的年龄。 即使年龄特征可能具有较高的数值,但在推荐学校的研究中,孩子特征的数目可能更为重要。
......
......@@ -20,7 +20,7 @@
# 问题定义
定义问题与建立模型或提高准确一样重要。 这是因为,虽然您可以使用最强大的算法并使用最先进的方法来改善其结果,但是如果您解决错误的问题或使用错误的数据,这可能毫无意义。
定义问题与建立模型或提高准确一样重要。 这是因为,虽然您可以使用最强大的算法并使用最先进的方法来改善其结果,但是如果您解决错误的问题或使用错误的数据,这可能毫无意义。
至关重要的是,学习如何深入思考以了解可以做什么和不能做什么以及如何可以完成。 考虑到当我们在学习应用机器学习或深度学习算法时,大多数课程中出现的问题总是清晰定义的,因此除训练模型和提高其性能外无需进行进一步分析,这一点尤其重要。 另一方面,在现实生活中,问题常常令人困惑,数据经常混乱。
......@@ -198,7 +198,7 @@ print("rows:",data.shape[0]," columns:", data.shape[1])
**收集更多数据**:尽管这并非总是可用的途径,但它可能有助于平衡类或允许删除过度代表的类而不会严重减少数据集。
**更改表现指标**:某些指标(例如准确)不适用于测量不平衡数据集的性能。 反过来,建议使用诸如精度或召回分类问题之类的指标来衡量性能。
**更改表现指标**:某些指标(例如准确)不适用于测量不平衡数据集的性能。 反过来,建议使用诸如精度或召回分类问题之类的指标来衡量性能。
**重采样数据集**:这需要修改数据集以平衡类。 可以通过两种不同的方式来完成此操作:在代表性不足的类中添加实例的副本(称为过采样),或删除代表性不足的类的实例(称为欠采样)。
......@@ -231,7 +231,7 @@ print("rows:",data.shape[0]," columns:", data.shape[1])
图 3.6:目标特征的类数
为了解决此问题,并且鉴于没有更多数据要添加并且性能指标实际上是准确的事实,有必要执行数据重采样。
为了解决此问题,并且鉴于没有更多数据要添加并且性能指标实际上是准确的事实,有必要执行数据重采样。
以下是对数据集执行过采样的代码片段,随机创建了代表性不足的类的重复行:
......@@ -300,7 +300,7 @@ final_data.to_csv("dccc_prepared.csv", index=False)
鉴于此,要测量与此类模型相关的性能,您应该计算地面真实值和预测值之间的差,例如,计算 125.3(预测)与 126.38(地面真实值)之间的距离 。 如前所述,有许多方法可以测量此差异,例如**均方误差****MSE**),或另一种变化是**均方根误差****RMSE**),是最常用的指标。
与此相反,分类任务的输出是属于每个输出标签或类的某些输入要素集合的概率,这是使用 Sigmoid(用于二进制分类)或 softmax(用于多类分类)完成的 )激活功能。 对于二元分类任务,输出层应包含一个(对于 Sigmoid)或两个(对于 softmax)输出节点,而对于多类分类任务,输出层应等于类标签的数量。
与此相反,分类任务的输出是属于每个输出标签或类的某些输入要素集合的概率,这是使用 Sigmoid(用于二进制分类)或 softmax(用于多类分类)完成的 )激活函数。 对于二元分类任务,输出层应包含一个(对于 Sigmoid)或两个(对于 softmax)输出节点,而对于多类分类任务,输出层应等于类标签的数量。
计算属于每个输出类别的输入特征的似然性的这种能力,再加上`argmax`函数,将以较高的概率检索类别作为最终预测。
......@@ -308,7 +308,7 @@ final_data.to_csv("dccc_prepared.csv", index=False)
在 Python 中, **argmax** 函数是能够沿轴返回最大值索引的函数。
考虑到这一点,模型的性能应与实例是否已分类到正确的类别标签有关,而不是与测量两个值之间的距离有关—因此要使用不同的损失函数( 熵是最常用的),用于训练神经网络进行分类问题,以及使用不同的性能指标,例如准确性,准确性和召回率。
考虑到这一点,模型的性能应与实例是否已分类到正确的类别标签有关,而不是与测量两个值之间的距离有关—因此要使用不同的损失函数( 熵是最常用的),用于训练神经网络进行分类问题,以及使用不同的性能指标,例如准确率,准确率和召回率。
## 好的架构
......@@ -434,7 +434,7 @@ class Classifier(torch.nn.Module):
## 定义损失函数并训练模型
重要的是要提到,交叉熵损失函数要求网络的输出是原始的(在通过使用`softmax`激活函数获得概率之前),这就是为什么通常会发现 用于分类问题的神经网络架构,而没有针对输出层的激活功能。 此外,为了通过这种方法进行预测,必须在训练模型后将`softmax`激活函数应用于网络的输出。
重要的是要提到,交叉熵损失函数要求网络的输出是原始的(在通过使用`softmax`激活函数获得概率之前),这就是为什么通常会发现 用于分类问题的神经网络架构,而没有针对输出层的激活函数。 此外,为了通过这种方法进行预测,必须在训练模型后将`softmax`激活函数应用于网络的输出。
解决此问题的另一种方法是对输出层使用`log_softmax`激活函数。 这样,损失函数可以定义为负对数似然损失(`nn.NLLLoss`)。 最后,可以通过从网络输出中获取指数来获得属于每个类别标签的一组要素的概率。 这是本章活动中将使用的方法。
......@@ -468,7 +468,7 @@ batch_size = 100
使用`topk`方法可以获得较高的类标签。
使用 scikit-learn 的“度量”部分,计算准确,精确度或查全率。 您还可以探索其他性能指标。
使用 scikit-learn 的“度量”部分,计算准确,精确度或查全率。 您还可以探索其他性能指标。
将所有批量的训练数据输入模型后,将关闭梯度计算,以通过验证数据验证当前模型的性能,如下所示:
......@@ -525,13 +525,13 @@ batch_size = 100
          "Validation Accuracy: {:.3f}".format(acc))
```
前面的代码片段将打印两组数据的损失和准确。 在下面的活动中,我们将介绍的有关构建和训练 DNN 的所有概念都将付诸实践。
前面的代码片段将打印两组数据的损失和准确。 在下面的活动中,我们将介绍的有关构建和训练 DNN 的所有概念都将付诸实践。
## 活动 3.01:构建人工神经网络
对于此活动,使用先前准备的数据集,我们将构建一个四层模型,该模型能够确定客户是否会拖欠下一次付款。 为此,我们将使用自定义模块的方法。
让我们看一下以下情况:您在一家数据科学精品店工作,该精品店专门为世界各地的银行提供机器/深度学习解决方案。 他们最近为一家银行开展了一个项目,该项目希望能够预测下个月将收到或将不会收到的款项。 探索性数据分析团队已经为您准备了数据集,他们已要求您构建模型并计算模型的准确。 请按照以下步骤完成此活动:
让我们看一下以下情况:您在一家数据科学精品店工作,该精品店专门为世界各地的银行提供机器/深度学习解决方案。 他们最近为一家银行开展了一个项目,该项目希望能够预测下个月将收到或将不会收到的款项。 探索性数据分析团队已经为您准备了数据集,他们已要求您构建模型并计算模型的准确。 请按照以下步骤完成此活动:
1. Import the following libraries:
......@@ -555,7 +555,7 @@ batch_size = 100
3. 将功能与目标分开。
4. 使用 scikit-learn 的`train_test_split`函数,将数据集分为训练,验证和测试集。 使用 60:20:20 的分配比例。 将`random_state`设置为`0`
5. 考虑到要素矩阵应为浮点型,而目标矩阵则应为非浮点型,将验证和测试集转换为张量。 目前暂时不要转换训练集,因为它们将进行进一步的转换。
6. 构建用于定义网络层的自定义模块类。 包括一个前向功能,该功能指定将应用于每层输出的激活功能。 对于除输出之外的所有层,请使用 **ReLU**,在此处应使用`log_softmax`
6. 构建用于定义网络层的自定义模块类。 包括一个前向功能,该功能指定将应用于每层输出的激活函数。 对于除输出之外的所有层,请使用 **ReLU**,在此处应使用`log_softmax`
7. 实例化模型并定义训练模型所需的所有变量。 将时期数设置为`50`,并将批大小设置为`128`。 使用`0.001`的学习率。
8. Train the network using the training set's data. Use the validation sets to measure performance. To do this, save the loss and the accuracy for both the training and validation sets in each epoch.
......@@ -564,7 +564,7 @@ batch_size = 100
训练过程可能需要几分钟,具体取决于您的资源。 如果您希望查看训练过程的进度,则添加打印语句是一种很好的做法。
9. 绘制两组损失。
10. 绘制两组数据的准确
10. 绘制两组数据的准确
最终图将如下所示:
......@@ -633,7 +633,7 @@ batch_size = 100
## 练习 3.02:执行错误分析
使用我们在上一个活动中计算的准确指标,在此活动中,我们将执行错误分析,这将有助于我们确定在即将到来的活动中针对模型执行的操作。 请按照以下步骤完成此练习:
使用我们在上一个活动中计算的准确指标,在此活动中,我们将执行错误分析,这将有助于我们确定在即将到来的活动中针对模型执行的操作。 请按照以下步骤完成此练习:
注意
......@@ -680,8 +680,8 @@ batch_size = 100
没有正确的方法来选择首先执行哪个测试,因此要有创造性和分析性。 如果模型架构中的更改减少或消除了高偏差但引入了高方差,则应考虑保留这些更改,但增加措施以应对高方差。
4. 绘制两组数据的损失和准确
5. 使用性能最佳的模型,对测试集进行预测(在微调过程中不应使用该预测)。 通过计算该组模型的准确,将预测结果与真实情况进行比较。
4. 绘制两组数据的损失和准确
5. 使用性能最佳的模型,对测试集进行预测(在微调过程中不应使用该预测)。 通过计算该组模型的准确,将预测结果与真实情况进行比较。
预期输出:通过模型架构和此处定义的参数获得的精度应为 80% 左右。
......@@ -948,7 +948,7 @@ prediction = traced_script(input)
在涵盖了前几章的大部分理论知识之后,本章使用了一个实际案例研究来巩固我们的知识。 这样做的目的是鼓励通过动手实践来学习。
本章首先介绍了深度学习对要求准确的众多行业的影响。 推动深度学习发展的主要行业之一是银行和金融业,这些算法被用于诸如贷款申请评估,欺诈检测以及过去决策评估以预测未来行为等领域,这主要是由于 在这些方面,算法具有超越人类性能的能力。
本章首先介绍了深度学习对要求准确的众多行业的影响。 推动深度学习发展的主要行业之一是银行和金融业,这些算法被用于诸如贷款申请评估,欺诈检测以及过去决策评估以预测未来行为等领域,这主要是由于 在这些方面,算法具有超越人类性能的能力。
本章使用来自台湾一家银行的真实数据集,目的是预测客户是否会拖欠付款。 本章通过解释定义任何数据问题的内容,原因和方式以及分析手头的数据以对其进行最佳利用的重要性,开始开发针对此问题的解决方案。
......
......@@ -28,7 +28,7 @@ CNN 是处理图像数据问题时的理想架构。 但是,由于它们通常
## 为什么将 CNN 用于图像处理?
图像是像素矩阵,那么为什么不将矩阵展平为矢量并使用传统的神经网络架构对其进行处理呢? 答案是,即使使用最简单的图像,也存在一些像素相关性会改变图像的含义。 例如,猫眼,汽车轮胎甚至物体边缘的表示都是由以某种方式布置的几个像素构成的。 如果我们将图像展平,则这些依赖关系将丢失,传统模型的准确也会丢失:
图像是像素矩阵,那么为什么不将矩阵展平为矢量并使用传统的神经网络架构对其进行处理呢? 答案是,即使使用最简单的图像,也存在一些像素相关性会改变图像的含义。 例如,猫眼,汽车轮胎甚至物体边缘的表示都是由以某种方式布置的几个像素构成的。 如果我们将图像展平,则这些依赖关系将丢失,传统模型的准确也会丢失:
![Figure 4.1: Representation of a flattened matrix ](img/B15778_04_01.jpg)
......@@ -217,7 +217,7 @@ CNN 可以执行不同的任务,这些任务适用于所有监督学习问题
每当值是**浮点型**时,都应四舍五入。 这基本上意味着输入的某些区域将被忽略,并且不会从中提取任何特征。
最后,一旦输入已通过所有滤波器,则将输出馈送到激活函数以破坏线性,这类似于传统神经网络的过程。 尽管在此步骤中可以应用多种激活功能,但是首选功能是 ReLU 功能,因为它在 CNN 中显示了出色的效果。 我们在此处获得的输出将成为后续层(通常是池化层)的输入。
最后,一旦输入已通过所有滤波器,则将输出馈送到激活函数以破坏线性,这类似于传统神经网络的过程。 尽管在此步骤中可以应用多种激活函数,但是首选功能是 ReLU 功能,因为它在 CNN 中显示了出色的效果。 我们在此处获得的输出将成为后续层(通常是池化层)的输入。
## 练习 4.01:计算卷积层的输出形状
......@@ -293,7 +293,7 @@ class CNN_network(nn.Module):
        return x
```
在这里,层的定义发生在**顺序**容器内部。 通常,一个容器包括卷积层,激活功能和池化层。 一组新的层包含在其下面的不同容器中。
在这里,层的定义发生在**顺序**容器内部。 通常,一个容器包括卷积层,激活函数和池化层。 一组新的层包含在其下面的不同容器中。
在前面的示例中,在**顺序**容器内定义了卷积层和激活层。 因此,在`forward`方法中,不需要卷积层的输出通过激活函数,因为已经使用容器对其进行了处理。
......@@ -409,7 +409,7 @@ class CNN_network(nn.Module):
正如我们之前提到的,池化层还包含在激活函数下方与卷积层相同的容器中。 在新的**顺序**容器中,下面将定义一组后续层(卷积,激活和池化)。
同样,`forward`方法不再需要单独调用每个层; 而是通过容器传递信息,该容器既包含层又包含激活功能
同样,`forward`方法不再需要单独调用每个层; 而是通过容器传递信息,该容器既包含层又包含激活函数
### 全连接层
......@@ -443,7 +443,7 @@ class CNN_network(nn.Module):
        return x
```
使用与上一节相同的编码示例,在`__init__`方法内部,将两个 FC 层添加到网络。 接下来,在`forward`函数内部,使用`view()`函数将池化层的输出展平。 然后,它通过第一 FC 层,该层应用激活功能。 最后,数据连同其激活功能一起通过最终的 FC 层。
使用与上一节相同的编码示例,在`__init__`方法内部,将两个 FC 层添加到网络。 接下来,在`forward`函数内部,使用`view()`函数将池化层的输出展平。 然后,它通过第一 FC 层,该层应用激活函数。 最后,数据连同其激活函数一起通过最终的 FC 层。
同样,使用与之前相同的编码示例,可以使用自定义模块和**顺序**容器将 FC 层添加到我们的模型中,如下所示:
......@@ -557,19 +557,19 @@ test_loader = torch.utils.data.DataLoader(test_data, \
Conv3:一个卷积层,它将输入数据通过大小为 3 的 40 个过滤器传递。填充和跨距都应设置为 1。
在每个卷积层之后使用 ReLU 激活功能
在每个卷积层之后使用 ReLU 激活函数
每个卷积层之后的池化层,滤镜大小和跨度为 2。
展平图像后,滤除项设置为 20%。
线性 1:一个全连接层,接收上一层的展平矩阵作为输入,并生成 100 个单位的输出。 为此层使用 ReLU 激活功能。 此处,辍学期限设置为 20%。
线性 1:一个全连接层,接收上一层的展平矩阵作为输入,并生成 100 个单位的输出。 为此层使用 ReLU 激活函数。 此处,辍学期限设置为 20%。
Linear2:一个全连接层,可生成 10 个输出,每个类标签一个。 将`log_softmax`激活功能用于输出层。
Linear2:一个全连接层,可生成 10 个输出,每个类标签一个。 将`log_softmax`激活函数用于输出层。
7. 定义训练模型所需的所有参数。 将纪元数设置为 50。
8. 训练您的网络,并确保保存训练和验证集的损失和准确值。
9. 绘制两组的损失和准确
8. 训练您的网络,并确保保存训练和验证集的损失和准确值。
9. 绘制两组的损失和准确
10. Check the model's accuracy on the testing set—it should be around 72%.
注意
......@@ -663,9 +663,9 @@ test_data = datasets.CIFAR10('data', train=False, download=True, \
## 活动 4.02:Im 补充数据增强
在此活动中,数据增强将引入到我们在上一个活动中创建的模型中,以测试其准确是否可以提高。 让我们看一下以下情况。
在此活动中,数据增强将引入到我们在上一个活动中创建的模型中,以测试其准确是否可以提高。 让我们看一下以下情况。
您创建的模型不错,但是其准确达不到期望的水平。 您被要求考虑一种可以改善模型性能的方法。 请按照以下步骤完成此活动:
您创建的模型不错,但是其准确达不到期望的水平。 您被要求考虑一种可以改善模型性能的方法。 请按照以下步骤完成此活动:
1. 复制上一个活动中的笔记本。
2. Change the definition of the **transform** variable so that it includes, in addition to normalizing and converting the data into tensors, the following transformations:
......@@ -682,13 +682,13 @@ test_data = datasets.CIFAR10('data', train=False, download=True, \
![Figure 4.19: Resulting plot showing the accuracy of the sets ](img/B15778_04_19.jpg)
图 4.19:结果图显示了集合的准确
图 4.19:结果图显示了集合的准确
注意
由于每个时代的数据改组,结果将无法精确再现。 但是,您应该能够得到类似的结果。
4. 计算测试集上所得模型的准确
4. 计算测试集上所得模型的准确
预期输出:模型在测试集上的性能应为 75% 左右。
......@@ -756,7 +756,7 @@ class CNN(nn.Module):
对于此活动,我们将在前一个活动的架构上实现批量归一化,以查看是否有可能进一步提高测试集上模型的性能。 让我们看一下以下情况。
您在性能方面所做的最后改进使您的队友印象深刻,现在他们对您的期望更高。 他们要求您最后一次尝试改进模型,以使准确提高到 80%。 请按照以下步骤完成此活动:
您在性能方面所做的最后改进使您的队友印象深刻,现在他们对您的期望更高。 他们要求您最后一次尝试改进模型,以使准确提高到 80%。 请按照以下步骤完成此活动:
1. 复制上一个活动中的笔记本。
2. 将批量归一化添加到每个卷积层以及第一个 FC 层。
......
......@@ -312,7 +312,7 @@ for i in range(1, epochs+1):
上图中每个门的功能可以解释如下:
* **学习门**:短期记忆(也称为隐藏状态)和当前事件都进入学习门,在此分析信息,并忽略所有不需要的信息。 在数学上,这是通过使用线性函数和激活函数(*tanh*)将短期记忆和当前事件结合在一起来实现的。 它的输出乘以忽略因子,从而删除所有不相关的信息。 为了计算忽略因子,通过线性函数传递短期记忆和当前事件。 然后,将它们通过 **Sigmoid** 激活功能压缩在一起:
* **学习门**:短期记忆(也称为隐藏状态)和当前事件都进入学习门,在此分析信息,并忽略所有不需要的信息。 在数学上,这是通过使用线性函数和激活函数(*tanh*)将短期记忆和当前事件结合在一起来实现的。 它的输出乘以忽略因子,从而删除所有不相关的信息。 为了计算忽略因子,通过线性函数传递短期记忆和当前事件。 然后,将它们通过 **Sigmoid** 激活函数压缩在一起:
![Figure 6.14: The mathematical computations that occur in the learn gate ](img/B15778_06_14.jpg)
......@@ -744,7 +744,7 @@ NLP 是**人工智能**(**AI**)的子字段,它通过使计算机能够理
* 从中得到的“快乐”
* “十年”作为对象情感的时间范围
如您所见,情感分析的概念对于任何具有在线业务的公司而言都是关键的,因为它能够以惊人的速度对需要立即关注的评论做出快速响应,并且其准确类似于人类。 。
如您所见,情感分析的概念对于任何具有在线业务的公司而言都是关键的,因为它能够以惊人的速度对需要立即关注的评论做出快速响应,并且其准确类似于人类。 。
作为情感分析的示例用例,某些公司可能选择对每天收到的大量消息进行情感分析,以便优先处理对包含抱怨或负面情绪的消息的响应。 这不仅有助于减轻特定客户的负面情绪; 它还将帮助公司快速纠正错误并与客户建立信任关系。
......@@ -836,14 +836,14 @@ class LSTM(nn.Module):
7. 使用 3 个 LSTM 层的 64 个嵌入尺寸和 128 个神经元实例化模型。
8. 定义损失函数,优化算法以及要训练的时期数。 例如,您可以将二进制交叉熵损失用作损失函数,Adam 优化器,并训练 10 个历元。
9. 创建一个`for`循环,该循环将经历不同的时期并分别经历每个审核。 对于每次审核,都要进行预测,计算损失函数并更新网络参数。 此外,根据该训练数据计算网络的准确
10. 随时间绘制损失的进度和准确
9. 创建一个`for`循环,该循环将经历不同的时期并分别经历每个审核。 对于每次审核,都要进行预测,计算损失函数并更新网络参数。 此外,根据该训练数据计算网络的准确
10. 随时间绘制损失的进度和准确
最终的精度图将如下所示:
![Figure 6.25: Plot displaying the progress of the accuracy score ](img/B16118_06_25.jpg)
图 6.25:显示准确得分进度的图
图 6.25:显示准确得分进度的图
注意
......
......@@ -503,11 +503,11 @@
“验证损失:{:. 3f} ..” .format(dev_loss),\
“训练准确:{:. 3f} ..” \
“训练准确:{:. 3f} ..” \
.format(running_acc / iterations),\
“验证准确:{:. 3f}”。format(acc))
“验证准确:{:. 3f}”。format(acc))
9. Plot the loss of both sets:
......@@ -533,7 +533,7 @@
plt.plot(train_acc,label =“训练精度”)
plt.plot(dev_acc,label =“验证准确”)
plt.plot(dev_acc,label =“验证准确”)
plt.legend(frameon = False,fontsize = 15)
......@@ -741,11 +741,11 @@
“验证损失:{:. 3f} ..” .format(dev_loss),\
“训练准确:{:. 3f} ..” \
“训练准确:{:. 3f} ..” \
.format(running_acc / iterations),\
“验证准确:{:. 3f}”。format(acc))
“验证准确:{:. 3f}”。format(acc))
注意
......@@ -781,7 +781,7 @@
plt.plot(x_axis,train_acc,label =“训练精度”)
plt.plot(x_axis,dev_acc,label =“验证准确”)
plt.plot(x_axis,dev_acc,label =“验证准确”)
plt.legend(frameon = False,fontsize = 15)
......@@ -1067,15 +1067,15 @@
Conv3:一个卷积层,它将输入数据通过大小为 3 的 40 个过滤器传递。填充和跨距都应设置为 1。
在每个卷积层之后使用 ReLU 激活功能
在每个卷积层之后使用 ReLU 激活函数
在每个卷积层之后使用池化层,滤镜大小和步幅为 2。
展平图像后,使用掉落项设置为 20%。
线性 1:一个全连接层,接收上一层的展平矩阵作为输入,并生成 100 个单位的输出。 为此层使用 ReLU 激活功能。 此处的辍学期限设置为 20%。
线性 1:一个全连接层,接收上一层的展平矩阵作为输入,并生成 100 个单位的输出。 为此层使用 ReLU 激活函数。 此处的辍学期限设置为 20%。
Linear2:一个全连接层,可生成 10 个输出,每个类标签一个。 将`log_softmax`激活功能用于输出层:
Linear2:一个全连接层,可生成 10 个输出,每个类标签一个。 将`log_softmax`激活函数用于输出层:
CNN(nn.Module)类:
......@@ -1227,7 +1227,7 @@
dev_top_class)
#损失和准确将附加打印
#损失和准确将附加打印
train_losses.append(损失/迭代)
......@@ -1247,11 +1247,11 @@
.format(dev_losss / iter_2),\
“训练准确:{:. 3f} ..” \
“训练准确:{:. 3f} ..” \
.format(acc / iterations),\
“验证准确:{:. 3f}” \
“验证准确:{:. 3f}” \
.format(dev_accs / iter_2))
......@@ -1353,7 +1353,7 @@
dev_top_class.to(“ cpu”))
#损失和准确将附加打印
#损失和准确将附加打印
train_losses.append(损失/迭代)
......@@ -1373,11 +1373,11 @@
.format(dev_losss / iter_2),\
“训练准确:{:. 3f} ..” \
“训练准确:{:. 3f} ..” \
.format(acc / iterations),\
“验证准确:{:. 3f}” \
“验证准确:{:. 3f}” \
.format(dev_accs / iter_2))
......@@ -1401,7 +1401,7 @@
plt.plot(x_axis,train_acc,label =“训练精度”)
plt.plot(x_axis,dev_acc,label =“验证准确”)
plt.plot(x_axis,dev_acc,label =“验证准确”)
plt.legend(frameon = False)
......@@ -1411,7 +1411,7 @@
![Figure 4.24: Resulting plot showing the accuracy of the sets ](img/B15778_04_24.jpg)
图 4.24:结果图显示了集合的准确
图 4.24:结果图显示了集合的准确
可以看出,在第 15 个时期之后,过度拟合开始影响模型。
......@@ -1437,7 +1437,7 @@
打印(acc_test / iter_3)
使用我们之前创建的数据加载器,可以对测试集数据进行图像分类,以估计模型在看不见数据上的准确
使用我们之前创建的数据加载器,可以对测试集数据进行图像分类,以估计模型在看不见数据上的准确
如果您的计算机具有可用的 GPU,则对前面的代码进行一些修改,如下所示:
......@@ -1463,7 +1463,7 @@
打印(acc_test / iter_3)
测试集的准确性与其他两组所达到的准确性非常相似,这意味着该模型能够对看不见的数据表现出同样出色的性能。 它应该在 72% 左右。
测试集的准确率与其他两组所达到的准确率非常相似,这意味着该模型能够对看不见的数据表现出同样出色的性能。 它应该在 72% 左右。
注意
......@@ -1513,7 +1513,7 @@
如果您的计算机具有可用的 GPU,请确保使用代码的 GPU 版本来训练模型。
在训练和验证集上得出的损失和准确图应与此处显示的图相似:
在训练和验证集上得出的损失和准确图应与此处显示的图相似:
![Figure 4.25: Resulting plot showing the loss of the sets ](img/B15778_04_25.jpg)
......@@ -1521,7 +1521,7 @@
![Figure 4.26: Resulting plot showing the accuracy of the sets ](img/B15778_04_26.jpg)
图 4.26:结果图显示了集合的准确
图 4.26:结果图显示了集合的准确
通过添加数据扩充,可以改善模型的性能,并减少发生的过度拟合。
......@@ -1599,7 +1599,7 @@
3. Train the model for 100 epochs.
如果您的计算机具有可用的 GPU,请确保使用代码的 GPU 版本来训练模型。 训练和验证集的损失和准确的结果图应类似于此处所示:
如果您的计算机具有可用的 GPU,请确保使用代码的 GPU 版本来训练模型。 训练和验证集的损失和准确的结果图应类似于此处所示:
![Figure 4.27: Resulting plot showing the loss of the sets ](img/B15778_04_27.jpg)
......@@ -2789,7 +2789,7 @@
图 6.31:显示损失函数进度的图
以下代码用于绘制准确得分:
以下代码用于绘制准确得分:
x_range =范围(len(acc))
......@@ -2797,7 +2797,7 @@ plt.plot(x_range,acc)
plt.xlabel(“时代”)
plt.ylabel(“准确得分”)
plt.ylabel(“准确得分”)
plt.show()
......@@ -2805,7 +2805,7 @@ plt.show()
![Figure 6.32: Plot displaying the progress of the accuracy score ](img/B15778_06_32.jpg)
图 6.32:显示准确得分进度的图
图 6.32:显示准确得分进度的图
注意
......
......@@ -18,7 +18,7 @@
第 3 章,“基于模型的方法”探索了两种架构,其内部架构有助于训练 k-shot 学习模型。
第 4 章,“基于优化的方法”探索了各种形式的优化算法,即使数据量很少,它们也有助于提高准确
第 4 章,“基于优化的方法”探索了各种形式的优化算法,即使数据量很少,它们也有助于提高准确
第 5 章,“基于生成模型的方法”探索了一种用概率模型表示对象类别的贝叶斯学习框架的开发。
......
......@@ -283,7 +283,7 @@ print('Accuracy of our model is equal ' + str(round(accuracy, 2)) + ' %.')
Accuracy of our model is equal 50.0 %.
```
对于我们当前的情况,我们可以看到神经网络的准确不如 kNN。 这可能是由于许多原因造成的,包括数据集的随机性,邻居的选择以及层数。 但是,如果我们运行足够的时间,我们会发现 kNN 总是会存储更好的数据,因为它总是存储数据点,而不是像神经网络那样学习参数。 因此,kNN 可以称为单次学习方法。
对于我们当前的情况,我们可以看到神经网络的准确不如 kNN。 这可能是由于许多原因造成的,包括数据集的随机性,邻居的选择以及层数。 但是,如果我们运行足够的时间,我们会发现 kNN 总是会存储更好的数据,因为它总是存储数据点,而不是像神经网络那样学习参数。 因此,kNN 可以称为单次学习方法。
# 概要
......
......@@ -157,7 +157,7 @@ Logistic 回归是**判别式分类器**的一种形式,在判别式分类器
# 应用领域
通常,可以使用各种方法解决问题。 例如我们手机上的人脸检测。 图像分类是一种需要大量数据点的方法,而如果使用单次学习的连体网络架构,则仅需几个数据点就可以实现更高的准确。 连体网络架构已成为软件行业采用的最流行的一键式学习架构之一。 它可用于各种其他应用程序,例如面部检测,手写检测和垃圾邮件检测。 但是仍然有很多改进的余地,并且各种各样的研究者正在为此努力。 在下一节中,以相似的主题进行工作,我们将学习匹配的网络架构,该架构使用注意机制和不同的训练过程来学习训练集标签上的概率分布。
通常,可以使用各种方法解决问题。 例如我们手机上的人脸检测。 图像分类是一种需要大量数据点的方法,而如果使用单次学习的连体网络架构,则仅需几个数据点就可以实现更高的准确。 连体网络架构已成为软件行业采用的最流行的一键式学习架构之一。 它可用于各种其他应用程序,例如面部检测,手写检测和垃圾邮件检测。 但是仍然有很多改进的余地,并且各种各样的研究者正在为此努力。 在下一节中,以相似的主题进行工作,我们将学习匹配的网络架构,该架构使用注意机制和不同的训练过程来学习训练集标签上的概率分布。
# 了解匹配网络
......@@ -1031,7 +1031,7 @@ Epoch 1: train_loss:2.97 train_accuracy:0.20 valid_loss:2.97 valid_accuracy:0.28
Epoch 2: train_loss:2.95 train_accuracy:0.31 valid_loss:2.94 valid_accuracy:0.37
```
10. 现在,通过运行以下代码块来获得测试的准确
10. 现在,通过运行以下代码块来获得测试的准确
```py
total_test_c_loss, total_test_accuracy = run_epoch(total_test_batches,'test')
......
......@@ -206,7 +206,7 @@ MANN 的读取操作与 NTM 的读取操作非常相似,唯一的区别是此
在选择嵌入网络时,元网络使用 LSTM 架构。 如我们所见,匹配网络和 LSTM 元学习器也遵循相同的策略,分别用于提取数据和元信息的上下文嵌入。 这是因为 LSTM 架构倾向于记住历史,这使得元学习器的目标能够跨任务提取重要信息。
例如,假设我们正在训练我们的网络以完成多种任务,例如猫的品种分类和狗的品种分类。 当我们使用 LSTM 元学习器进行训练时,它会学习例如狗品种分类中体重更新的策略,并使用这些学习到的信息以较少的步骤和较少的数据来优化其用于猫品种分类的操作。 使用元网络在 Omniglot 数据集上达到了 95.92% 的准确性,而人类的准确性仅为 95.5%,因此,元网络被认为是最新模型之一。
例如,假设我们正在训练我们的网络以完成多种任务,例如猫的品种分类和狗的品种分类。 当我们使用 LSTM 元学习器进行训练时,它会学习例如狗品种分类中体重更新的策略,并使用这些学习到的信息以较少的步骤和较少的数据来优化其用于猫品种分类的操作。 使用元网络在 Omniglot 数据集上达到了 95.92% 的准确率,而人类的准确率仅为 95.5%,因此,元网络被认为是最新模型之一。
# 编码练习
......
......@@ -53,7 +53,7 @@
在学习不平衡的情况下,我们有一个不平衡的数据集。 也就是说,我们从一个类别中获得的样本要多于从其他类别中获得的样本。 这也被普遍称为**偏态分布数据集**。让我们看一下处理偏斜数据集的一些流行方法:
* **度量标准的选择**:度量标准的多种形式可以帮助评估模型的准确,例如混淆矩阵,精度,召回率和 F1 得分。
* **度量标准的选择**:度量标准的多种形式可以帮助评估模型的准确,例如混淆矩阵,精度,召回率和 F1 得分。
* **算法的选择**:参数算法通过数据集学习其参数,因此,如果数据集存在偏差,则参数模型最有可能也会受到偏差。 对于有偏数据集,非参数方法(例如 k 最近邻)和集合(例如 AdaBoost,XGBoost 等)被证明是最佳方法。
* **数据采样方法的选择**:也可以考虑进行数据采样以确保数据集不会保持偏斜。
......
......@@ -12,23 +12,23 @@
# 这本书涵盖的内容
[“第 1 章”](../Text/1.html#_idTextAnchor015) *是机器学习和深度学习的基础知识*,概述了机器学习和神经网络的基本方面。
“第 1 章”,“机器学习和深度学习的基础知识”,概述了机器学习和神经网络的基本方面。
[“第 2 章”](../Text/2.html#_idTextAnchor029) *,用于 NLP 的 PyTorch 1.x 入门*,向您展示如何下载,安装和启动 PyTorch。 我们还将介绍该软件包的一些基本功能。
“第 2 章”,“用于 NLP 的 PyTorch 1.x 入门”,向您展示如何下载,安装和启动 PyTorch。 我们还将介绍该软件包的一些基本功能。
[“第 3 章”](../Text/3.html#_idTextAnchor051) *,NLP 和文本嵌入*展示了如何为 NLP 创建文本嵌入并在基本语言模型中使用它们。
“第 3 章”,“NLP 和文本嵌入”展示了如何为 NLP 创建文本嵌入并在基本语言模型中使用它们。
[“第 4 章”](../Text/4.html#_idTextAnchor070) *,文本预处理,词干和词法化*展示了如何预处理文本数据以用于 NLP 深度学习模型。
“第 4 章”,“文本预处理,词干提取和词形还原”,展示了如何预处理文本数据以用于 NLP 深度学习模型。
[“第 5 章”](../Text/5.html#_idTextAnchor092) *,循环神经网络和情感分析*,介绍了循环神经网络的基础知识,并向您展示如何使用它们来建立情感神经网络分析模型。 刮。
“第 5 章”,“循环神经网络和情感分析”,介绍了循环神经网络的基础知识,并向您展示如何使用它们来建立情感神经网络分析模型。 刮。
[“第 6 章”](../Text/6.html#_idTextAnchor112) *,用于文本分类的卷积神经网络*,介绍了卷积神经网络的基础知识,并向您展示了如何使用它们为 分类文本。
“第 6 章”,“用于文本分类的卷积神经网络”,介绍了卷积神经网络的基础知识,并向您展示了如何使用它们为 分类文本。
[“第 7 章”](../Text/7.html#_idTextAnchor124) *,使用序列到序列神经网络的文本翻译*介绍了深度学习的序列到序列模型的概念,并介绍了如何 使用它们来构建将文本翻译成另一种语言的模型。
“第 7 章”,“使用序列到序列神经网络的文本翻译”介绍了深度学习的序列到序列模型的概念,并介绍了如何 使用它们来构建将文本翻译成另一种语言的模型。
[“第 8 章”](../Text/8.html#_idTextAnchor139) *,使用基于注意力的神经网络构建聊天机器人*,涵盖了在序列到序列深度学习模型中使用的注意概念,并显示了 您将了解如何使用它们从头开始构建功能全面的聊天机器人。
“第 8 章”,“使用基于注意力的神经网络构建聊天机器人”,涵盖了在序列到序列深度学习模型中使用的注意概念,并显示了 您将了解如何使用它们从头开始构建功能全面的聊天机器人。
[“第 9 章”](../Text/9.html#_idTextAnchor156) *(前进的道路*涵盖了 NLP 深度学习中当前使用的一些最新模型,并探讨了一些挑战 以及 NLP 领域面临的问题。
“第 9 章”,“前方的路”涵盖了 NLP 深度学习中当前使用的一些最新模型,并探讨了一些挑战 以及 NLP 领域面临的问题。
# 要充分利用这本书
......@@ -69,7 +69,7 @@
本书中使用了许多文本约定。
**文本中的代码**:指示文本中的代码字,数据库表名称,文件夹名称,文件名,文件扩展名,路径名,虚拟 URL,用户输入和 Twitter 句柄。 这是一个示例:“将下载的 **WebStorm-10 * .dmg** 磁盘映像文件安装为系统中的另一个磁盘。”
**文本中的代码**:指示文本中的代码字,数据库表名称,文件夹名称,文件名,文件扩展名,路径名,虚拟 URL,用户输入和 Twitter 句柄。 这是一个示例:“将下载的`WebStorm-10*.dmg`磁盘映像文件安装为系统中的另一个磁盘。”
代码块设置如下:
......
......@@ -14,7 +14,7 @@
# 机器学习概述
从根本上讲,机器学习是用于识别模式并从数据中提取趋势的算法过程。 通过在数据上训练特定的机器学习算法,机器学习模型可以学习对人眼不是立即显而易见的见解。 医学成像模型可能会学会从人体图像中检测出癌症,而情感分析模型可能会发现书评中包含*良好**优秀**与包含*不好*,*糟糕*和*无聊*的单词相比,娱乐*更可能是一项积极的评价
从根本上讲,机器学习是用于识别模式并从数据中提取趋势的算法过程。 通过在数据上训练特定的机器学习算法,机器学习模型可以学习对人眼不是立即显而易见的见解。 医学成像模型可能会学会从人体图像中检测出癌症,而情感分析模型可能会学习,与包含*不好**糟糕**无聊*的书评相比,包含*良好**优秀**有意思*的书评更可能是正面的
广义上讲,机器学习算法分为两大类:监督学习和无监督学习。
......@@ -32,7 +32,7 @@
图 1.2 –外壳数据输出
给定此历史数据,我们可以使用此数据来估计**大小**X)和**价格**(Y)之间的关系。 现在我们已经估算了大小和价格之间的关系,如果给了我们只知道房子大小的新房子,我们可以使用学习的函数使用它来预测价格:
给定此历史数据,我们可以使用此数据来估计**大小**`X`)和**价格**`Y`)之间的关系。 现在我们已经估算了大小和价格之间的关系,如果给了我们只知道房子大小的新房子,我们可以使用学习的函数使用它来预测价格:
![Figure 1.3 – Predicting house prices ](img/B12365_01_3.jpg)
......@@ -40,15 +40,11 @@
因此,给定许多输入与输出之间的关系的示例,所有监督学习任务旨在学习模型输入的某些函数以预测输出:
*假设有很多(X,y),请学习:*
*F(X)= y*
给定很多`(X, y)`,请学习`F(X) = y`
您电话号码的输入可以包含任意数量的功能。 我们的简单房价模型仅包含一个功能(**大小**),但我们可能希望添加更多功能以提供更好的预测(例如,卧室数量,花园大小等) 上)。 因此,更具体地说,我们的监督模型学习了一个函数,以便将许多输入映射到输出。 由以下等式给出:
给定许多*([X0,X1,X2,…,Xn],y),*学习:
*f(X* *0,X1,X2,…,Xn)= y*
给定许多`([X0, X1, X2, …, Xn], y)`,学习`f(X0, X1, X2, …, Xn) = y`
在前面的示例中,我们学习的功能如下:
......@@ -64,15 +60,15 @@
正如我们稍后将更详细地研究一样,他们也可以从文本中学习:
*我喜欢这部电影*->好评
我喜欢这部电影 -> 好评
*这部电影很糟糕*->底片
这部电影很糟糕 -> 差评
*我今年看过的最好的电影*->
我今年看过的最好的电影 ->
## 无监督学习
**非监督学习** 与监督学习的不同之处在于非监督学习不使用输入和输出对*X,y*进行学习。 相反,我们仅提供输入数据,模型将学习有关输入数据的结构或表示的知识。 无监督学习的最常见方法之一是**聚类**
**非监督学习** 与监督学习的不同之处在于非监督学习不使用输入和输出对`(X, y)`进行学习。 相反,我们仅提供输入数据,模型将学习有关输入数据的结构或表示的知识。 无监督学习的最常见方法之一是**聚类**
例如,我们获取了来自四个不同国家/地区的温度和降雨测度读数的数据集,但没有关于这些读数取自何处的标签。 我们可以使用聚类算法来识别数据中存在的不同聚类(国家):
......@@ -98,7 +94,7 @@
图 1.6 –梯度下降
我们首先用随机值初始化![](img/Formula_01_009.png)。 为了使损失最小化,我们需要*下坡*从损失函数进一步下移,到达山谷的中部。 为此,我们首先需要知道向哪个方向移动。在我们的初始点,我们使用基本演算来计算坡度的初始坡度:
我们首先用随机值初始化![](img/Formula_01_009.png)。 为了使损失最小化,我们需要从损失函数进一步下移,到达山谷的中部。 为此,我们首先需要知道向哪个方向移动。在我们的初始点,我们使用基本演算来计算坡度的初始坡度:
![](img/Formula_01_010.png)
......@@ -112,15 +108,15 @@
图 1.7 –拟合不足和过度拟合的示例
当我们的模型由于缺乏功能,数据不足或模型规格不足而无法很好地拟合数据时,我们将其称为**,即不适合**。 我们注意到我们数据的梯度越来越大,并怀疑如果使用多项式,则模型可能更合适。 例如![](img/Formula_01_015.png)。 稍后我们将看到,由于神经网络的复杂结构,欠拟合很少成为问题:
当我们的模型由于缺乏功能,数据不足或模型规格不足而无法很好地拟合数据时,我们将其称为**欠拟合**。 我们注意到我们数据的梯度越来越大,并怀疑如果使用多项式,则模型可能更合适。 例如![](img/Formula_01_015.png)。 稍后我们将看到,由于神经网络的复杂结构,欠拟合很少成为问题:
考虑以下示例。 在这里,我们使用房价模型拟合的函数不仅适用于房屋的大小(`X`),而且适用于二阶和三阶多项式*(X2,X3)* 。 在这里,我们可以看到我们的新模型非常适合我们的数据点。 但是,这不一定会产生良好的模型:
考虑以下示例。 在这里,我们使用房价模型拟合的函数不仅适用于房屋的大小(`X`),而且适用于二阶和三阶多项式`(X2, X3)`。 在这里,我们可以看到我们的新模型非常适合我们的数据点。 但是,这不一定会产生良好的模型:
![Figure 1.8 – Sample output of overfitting ](img/B12365_01_8.jpg)
图 1.8 –过度拟合的样本输出
我们现在有一个房子,其大小为 **110 平方米**,以预测价格。 根据我们的直觉,由于该房屋比 **100 平方米**房屋大,我们希望这所房屋的价格会更高,大约 **$ 340,000** 。 使用我们的拟合多项式模型,我们可以看到预测的价格实际上低于小房子,约为 **$ 320,000** 。 我们的模型适合我们训练有素的数据,但不能很好地推广到一个新的,看不见的数据点。 这就是,称为**过拟合**。 由于过度拟合,重要的是不要根据训练的数据评估模型的性能,因此我们需要生成单独的一组数据以评估我们的数据。
我们现在有一个房子,其大小为 **110 平方米**,以预测价格。 根据我们的直觉,由于该房屋比 **100 平方米**房屋大,我们希望这所房屋的价格会更高,大约 **340,000 美元**。 使用我们的拟合多项式模型,我们可以看到预测的价格实际上低于小房子,约为 **320,000 美元**。 我们的模型适合我们训练有素的数据,但不能很好地推广到一个新的,看不见的数据点。 这就是,称为**过拟合**。 由于过度拟合,重要的是不要根据训练的数据评估模型的性能,因此我们需要生成单独的一组数据以评估我们的数据。
### 训练与测试
......@@ -128,17 +124,17 @@
### 评估模型
尽管我们试图将模型中的损失降到最低,但仅此一项并不能给我们太多有关模型在实际进行预测方面的优势的信息。 考虑一个反垃圾邮件模型,该模型可以预测收到的电子邮件是否为垃圾邮件,并自动将垃圾邮件发送到垃圾文件夹。 评估性能的一种简单方法是**准确**
尽管我们试图将模型中的损失降到最低,但仅此一项并不能给我们太多有关模型在实际进行预测方面的优势的信息。 考虑一个反垃圾邮件模型,该模型可以预测收到的电子邮件是否为垃圾邮件,并自动将垃圾邮件发送到垃圾文件夹。 评估性能的一种简单方法是**准确**
![](img/Formula_01_016.png)
为了计算准确性,我们只需将正确预测为垃圾邮件/非垃圾邮件的电子邮件数量除以我们做出的预测总数即可。 如果我们正确地预测了 1,000 封电子邮件中的 990 封电子邮件,则我们的准确性为 99%。 但是,高精度不一定意味着我们的模型是好的:
为了计算准确率,我们只需将正确预测为垃圾邮件/非垃圾邮件的电子邮件数量除以我们做出的预测总数即可。 如果我们正确地预测了 1,000 封电子邮件中的 990 封电子邮件,则我们的准确率为 99%。 但是,高精度不一定意味着我们的模型是好的:
![Figure 1.9 – Table showing data predicted as spam/non-spam ](img/B12365_01_9.jpg)
图 1.9 –该表显示了被预测为垃圾邮件/非垃圾邮件的数据
在这里,我们可以看到,尽管我们的模型正确地预测了 990 封电子邮件不是垃圾邮件(称为真实否定邮件),但它也预测了 10 封属于垃圾邮件的邮件被视为非垃圾邮件(称为错误否定邮件)。 我们的模型仅假设所有电子邮件都不是垃圾邮件,这根本不是一个很好的反垃圾邮件过滤器! 我们不仅应该使用准确性,还应该使用**精度评估模型并调用**。 在这种情况下,我们的模型的召回率为零(意味着未返回正结果)将立即成为危险信号:
在这里,我们可以看到,尽管我们的模型正确地预测了 990 封电子邮件不是垃圾邮件(称为真实否定邮件),但它也预测了 10 封属于垃圾邮件的邮件被视为非垃圾邮件(称为错误否定邮件)。 我们的模型仅假设所有电子邮件都不是垃圾邮件,这根本不是一个很好的反垃圾邮件过滤器! 我们不仅应该使用准确率,还应该使用**精度和召回**评估模型。 在这种情况下,我们的模型的召回率为零(意味着未返回正结果)将立即成为危险信号:
![](img/Formula_01_017.jpg)
......@@ -146,7 +142,7 @@
# 神经网络
在前面的示例中,我们主要讨论了![](img/Formula_01_019.png)形式的回归。 我们接触过使用多项式来拟合更复杂的方程式,例如![](img/Formula_01_020.png)。 但是,随着我们向模型中添加更多功能,何时使用原始功能的转换成为反复试验的案例。 使用**神经网络**,我们可以将更复杂的函数 *y = f(X)*拟合到我们的数据中,而无需设计或转换我们现有的功能。
在前面的示例中,我们主要讨论了![](img/Formula_01_019.png)形式的回归。 我们接触过使用多项式来拟合更复杂的方程式,例如![](img/Formula_01_020.png)。 但是,随着我们向模型中添加更多功能,何时使用原始功能的转换成为反复试验的案例。 使用**神经网络**,我们可以将更复杂的函数`y = f(x)`拟合到我们的数据中,而无需设计或转换我们现有的功能。
## 神经网络的结构
......@@ -170,27 +166,27 @@
由于全连接层中的每个节点都将`X`的所有值作为输入,因此神经网络能够学习输入特征之间的交互特征。 多个全连接层可以链接在一起,以学习更复杂的功能。 在本书中,我们将看到我们构建的所有神经网络都将使用该概念。 将不同品种的多层链接在一起,以构建更复杂的模型。 但是,在我们完全理解神经网络之前,还有另外一个关键要素要涵盖:激活函数。
## 激活功能
## 激活函数
虽然将各种权重链接在一起可以使我们学习更复杂的参数,但最终,我们的最终预测仍将是权重和特征的线性乘积的组合。 如果希望神经网络学习一个真正复杂的非线性函数,则必须在模型中引入非线性元素。 这可以通过使用**激活功能**来完成:
虽然将各种权重链接在一起可以使我们学习更复杂的参数,但最终,我们的最终预测仍将是权重和特征的线性乘积的组合。 如果希望神经网络学习一个真正复杂的非线性函数,则必须在模型中引入非线性元素。 这可以通过使用**激活函数**来完成:
![Figure 1.12 – Activation functions in neural networks ](img/B12365_01_12.jpg)
图 1.12 –神经网络中的激活函数
我们将激活函数应用于全连接层中的每个节点。 这意味着全连接层中的每个节点都将特征和权重之和作为输入,对结果值应用非线性函数,并输出转换后的结果。 尽管激活功能有许多不同,但最近使用最频繁的是 **ReLU****整流线性单元**
我们将激活函数应用于全连接层中的每个节点。 这意味着全连接层中的每个节点都将特征和权重之和作为输入,对结果值应用非线性函数,并输出转换后的结果。 尽管激活函数有许多不同,但最近使用最频繁的是 **ReLU****整流线性单元**
![Figure 1.13 – Representation of ReLU output ](img/B12365_01_13.jpg)
图 1.13 – ReLU 输出的表示
ReLU 是非常简单的非线性函数,当![](img/Formula_01_031.png)*y = X* 0 时,返回 *y = 0* 。 在将这些激活函数引入我们的模型后,我们最终的学习函数将变为非线性,这意味着我们可以创建比单独使用传统回归和特征工程相结合的模型更多的模型。
ReLU 是非常简单的非线性函数,当`x <= 0`,返回`y = 0`;当`x > 0`时返回`y = x`。 在将这些激活函数引入我们的模型后,我们最终的学习函数将变为非线性,这意味着我们可以创建比单独使用传统回归和特征工程相结合的模型更多的模型。
## 神经网络如何学习?
使用神经网络从数据中学习的行为比使用基本回归学习时的行为稍微复杂一些。 尽管我们仍然像以前一样使用梯度下降,但是我们需要区分的实际损失函数变得更加复杂。 在没有激活函数的单层神经网络中,我们很容易计算损失函数的导数,因为很容易看到随着我们改变每个参数损失函数如何变化。 但是,在具有激活功能的多层神经网络中,这更加复杂。
使用神经网络从数据中学习的行为比使用基本回归学习时的行为稍微复杂一些。 尽管我们仍然像以前一样使用梯度下降,但是我们需要区分的实际损失函数变得更加复杂。 在没有激活函数的单层神经网络中,我们很容易计算损失函数的导数,因为很容易看到随着我们改变每个参数损失函数如何变化。 但是,在具有激活函数的多层神经网络中,这更加复杂。
我们必须首先执行**前向通过**,即,其中,使用模型的当前状态,我们计算`y`的预测值,并根据[`y`,以便获得损失的度量。 利用这一损耗,我们可以在网络中向后移动,计算网络中每个参数的梯度。 这使我们可以知道向哪个方向更新参数,以便使可以更接近损耗最小的点。 这被称为**反向传播**。 我们可以使用**链规则**计算相对于每个参数的损失函数的导数:
我们必须首先执行**正向传播**,即,其中,使用模型的当前状态,我们计算`y`的预测值,并根据`y`的真实值来评估它,以便获得损失的度量。 利用这一损耗,我们可以在网络中向后移动,计算网络中每个参数的梯度。 这使我们可以知道向哪个方向更新参数,以便使可以更接近损耗最小的点。 这被称为**反向传播**。 我们可以使用**链式规则**计算相对于每个参数的损失函数的导数:
![](img/Formula_01_032.png)
......@@ -221,9 +217,11 @@ ReLU 是非常简单的非线性函数,当![](img/Formula_01_031.png)且 *y =
表示文本的第一种也是最简单的方法是使用**词袋**表示。 此方法只对给定句子或文档中的单词进行计数,然后对所有单词进行计数。 然后将这些计数转换为向量,其中向量的每个元素都是**语料库**中每个单词出现在句子中的次数计数。 语料库是,只是出现在所有要分析的句子/文档中的所有单词。 采取以下两个句子:
*猫坐在垫子上*
```py
The cat sat on the mat
*狗坐在猫*
The dog sat on the cat
```
我们可以将每个句子表示为单词数:
......@@ -233,9 +231,11 @@ ReLU 是非常简单的非线性函数,当![](img/Formula_01_031.png)且 *y =
然后,我们可以将它们转换为单个向量:
*猫坐在垫子上-> [2,1,0,1,1,1]*
```py
The cat sat on the mat -> [2,1,0,1,1,1]
*狗坐在猫上-> [2,1,1,1,1,0]*
The dog sat on the cat -> [2,1,1,1,1,0]
```
然后,该数字表示形式可用作特征向量为![](img/Formula_01_034.png)的机器学习模型的输入特征。
......
......@@ -66,7 +66,7 @@
图 2.3 –张量选择输出
但是,请注意,与 NumPy 数组不同,从张量对象中选择单个元素会返回另一个张量。 为了从张量返回单个值,可以使用 **.item()**函数:
但是,请注意,与 NumPy 数组不同,从张量对象中选择单个元素会返回另一个张量。 为了从张量返回单个值,可以使用`.item()`函数:
打印(x [0] [1] .item())
......@@ -121,13 +121,13 @@ GPU 最初是为了有效地渲染图形而创建的,但是由于深度学习
cuda = torch.device('cuda')
这会将我们的默认 CUDA 设备的名称设置为**'cuda'**
这会将我们的默认 CUDA 设备的名称设置为`'cuda'`
3. We can then execute operations on this device by manually specifying the device argument in any tensor operations:
x = torch.tensor([5。,3.],device = cuda)
另外,我们可以通过调用 **cuda** 方法来做到这一点:
另外,我们可以通过调用`cuda`方法来做到这一点:
y = torch.tensor([4.,2.])。cuda()
......@@ -166,13 +166,13 @@ PyTorch 与其他深度学习框架之间的另一个主要区别是语法。 Py
# 在 PyTorch 中构建简单的神经网络
现在,我们将逐步在 PyTorch 中逐步构建神经网络。 在这里,我们有一个小的 **.csv** 文件,其中包含来自 MNIST 数据集的图像的几个示例。 MNIST 数据集由我们想要尝试分类的 0 到 9 之间的手绘数字组成。 以下是来自 MNIST 数据集的示例,其中包括手绘数字 1:
现在,我们将逐步在 PyTorch 中逐步构建神经网络。 在这里,我们有一个小的`.csv`文件,其中包含来自 MNIST 数据集的图像的几个示例。 MNIST 数据集由我们想要尝试分类的 0 到 9 之间的手绘数字组成。 以下是来自 MNIST 数据集的示例,其中包括手绘数字 1:
![Figure 2.11 – Sample image from the MNIST dataset ](img/B12365_02_11.jpg)
图 2.11 –来自 MNIST 数据集的样本图像
这些图像的尺寸为 28x28:总共 784 像素。 我们在 **train.csv** 中的数据集由 1,000 幅这些图像组成,每幅图像均由 784 个像素值以及正确的数字分类(在这种情况下为 1)组成。
这些图像的尺寸为 28x28:总共 784 像素。 我们在`train.csv`中的数据集由 1,000 幅这些图像组成,每幅图像均由 784 个像素值以及正确的数字分类(在这种情况下为 1)组成。
## 加载数据
......@@ -186,7 +186,7 @@ PyTorch 与其他深度学习框架之间的另一个主要区别是语法。 Py
train = train.drop(“ label”,axis = 1).values.reshape(len(train),1,28,28)
请注意,我们将输入重塑为[ **1,** **1,** **28,**`28`),每个张量为 1,000 张图像 由 28x28 像素组成。
请注意,我们将输入重塑为`[1, 1, 28, 28]`,每个张量为 1,000 张图像 由 28x28 像素组成。
2. Next, we convert our training data and training labels into PyTorch tensors so they can be fed into the neural network:
......@@ -214,7 +214,7 @@ self.fc3 = nn.Linear(196,98)
self.fc4 = nn.Linear(98,10)
我们像从 Python PyTorch 中继承 **nn.Module** 一样,在 Python 中构建普通类,从而构建分类器。 在我们的**初始**方法中,我们定义了神经网络的每一层。 在这里,我们定义了大小可变的全连接线性层。
我们像从 Python PyTorch 中继承`nn.Module`一样,在 Python 中构建普通类,从而构建分类器。 在我们的`__init__`方法中,我们定义了神经网络的每一层。 在这里,我们定义了大小可变的全连接线性层。
我们的第一层接受`784`输入,因为这是我们要分类的每个图像的大小(28x28)。 然后,我们看到一层的输出必须与下一层的输入具有相同的值,这意味着我们的第一个全连接层输出`392`个单位,而我们的第二层则采用`392`单位作为输入。 对每一层都重复一次,每次它们具有一半的单位数量,直到我们到达最终的全连接层为止,该层输出`10`个单位。 这是我们分类层的长度。
......@@ -228,7 +228,7 @@ self.fc4 = nn.Linear(98,10)
## 实施辍学
在我们的 **MNISTClassifier** 类的**初始**方法中,我们还定义了一种 dropout 方法,以帮助规范网络:
在我们的`MNISTClassifier`类的`__init__`方法中,我们还定义了一种 dropout 方法,以帮助规范网络:
self.dropout = nn.Dropout(p = 0.2)
......@@ -250,9 +250,9 @@ x = self.dropout(F.relu(self.fc3(x)))
x = F.log_softmax(self.fc4(x),dim = 1)
分类器中的 **forward()**方法是我们在其中应用激活函数并定义在我们的网络中应用 dropout 的位置的方法。 我们的**正向**方法定义了输入将通过网络的路径。 首先,它获取我们的输入 **x,**,并将其整形以在网络中使用,并将其转换为一维矢量。 然后,我们将其通过我们的第一个全连接层,并将其包装在 **ReLU** 激活函数中,以使其为非线性。 我们也将其包装在我们的[drop]中,如 **init** 方法中所定义。 我们对网络中的所有其他层重复此过程。
分类器中的`forward()`方法是我们在其中应用激活函数并定义在我们的网络中应用 dropout 的位置的方法。 我们的`forward()`方法定义了输入将通过网络的路径。 首先,它获取我们的输入`x`,并将其整形以在网络中使用,并将其转换为一维矢量。 然后,我们将其通过我们的第一个全连接层,并将其包装在 **ReLU** 激活函数中,以使其为非线性。 我们也将其包装在我们的[drop]中,如`__init__`方法中所定义。 我们对网络中的所有其他层重复此过程。
对于我们的最终预测层,我们将其包装在对数 **softmax** 层中。 我们将使用它来轻松计算我们的损失函数,如下所示。
对于我们的最终预测层,我们将其包装在`log_softmax`层中。 我们将使用它来轻松计算我们的损失函数,如下所示。
## 设置模型参数
......@@ -264,17 +264,17 @@ loss_function = nn.NLLLoss()
opt = optim.Adam(model.parameters(),lr = 0.001)
我们将 **MNISTClassifier** 类的实例初始化为模型。 我们还将的损失定义为**负对数似然损失**
我们将`MNISTClassifier`类的实例初始化为模型。 我们还将的损失定义为**负对数似然损失**
损失(y)= -log(y)
假设我们的图像为 7。如果我们以概率 1 预测类别 7,则损失为 *-log(1)= 0* ,但是如果我们仅以概率 0.7 预测类别 7,则损失为 将是 *-log(0.7)= 0.3* 。 这意味着我们与正确预测的距离越远,损失就越接近无穷大:
假设我们的图像为 7。如果我们以概率 1 预测类别 7,则损失为`-log(1) = 0`,但是如果我们仅以概率 0.7 预测类别 7,则损失为 将是`-log(0.7) = 0.3`。 这意味着我们与正确预测的距离越远,损失就越接近无穷大:
![Figure 2.13 – Representation of loss for our network ](img/B12365_02_13.jpg)
图 2.13 –我们网络的损失表示
然后将其汇总到数据集中所有正确的类中,以计算总损失。 请注意,我们在构建分类器时定义了 log softmax,因为它已经应用了 softmax 函数(将预测输出限制在 0 到 1 之间)并获取了日志。 这意味着 *log(y)*已经被计算出来,因此我们要计算网络上的总损耗所需要做的就是计算输出的负和。
然后将其汇总到数据集中所有正确的类中,以计算总损失。 请注意,我们在构建分类器时定义了 log softmax,因为它已经应用了 softmax 函数(将预测输出限制在 0 到 1 之间)并获取了日志。 这意味着`log(y)`已经被计算出来,因此我们要计算网络上的总损耗所需要做的就是计算输出的负和。
我们还将优化器定义为 Adam 优化器。 优化器控制模型中的**学习率**。 模型的学习率定义了每次训练期间参数更新的大小。 学习速率的大小越大,梯度下降期间参数更新的大小越大。 优化器动态控制该学习速率,以便在初始化模型时,参数更新很大。 但是,随着模型的学习和向损耗最小化点的靠近,优化器将控制学习率,因此参数更新变得更小,可以更精确地定位局部最小值。
......@@ -368,11 +368,11 @@ pred_table.columns = ['预测值','真实值']
图 2.16 –预测表
注意 **torch.max()**函数如何自动选择具有最高值的预测。 在这里我们可以看到,基于的少量数据,我们的模型似乎做出了一些不错的预测!
注意`torch.max()`函数如何自动选择具有最高值的预测。 在这里我们可以看到,基于的少量数据,我们的模型似乎做出了一些不错的预测!
## 评估我们的模型
既然我们已经从模型中获得了一些预测,我们就可以使用这些预测来评估模型的质量。 如上一章所述,评估模型性能的一种基本方法是**准确**。 在这里,我们只是将正确的预测(预测的图像标签等于实际的图像标签)计算为模型做出的预测总数的百分比:
既然我们已经从模型中获得了一些预测,我们就可以使用这些预测来评估模型的质量。 如上一章所述,评估模型性能的一种基本方法是**准确**。 在这里,我们只是将正确的预测(预测的图像标签等于实际的图像标签)计算为模型做出的预测总数的百分比:
preds = len(预测标签)
......@@ -384,7 +384,7 @@ preds = len(预测标签)
![Figure 2.17 – Accuracy score ](img/B12365_02_17.jpg)
图 2.17 –准确得分
图 2.17 –准确得分
恭喜你! 您的第一个神经网络能够正确识别近 90% 的看不见的数字图像。 随着我们的前进,我们将看到可能会带来更先进的性能。 但是,到目前为止,我们已经证明使用 PyTorch 创建简单的深度神经网络非常简单。 只需几行代码就可以编写代码,从而获得超越基本机器学习模型(例如回归)所能达到的性能。
......@@ -404,7 +404,7 @@ preds = len(预测标签)
(“我在图书馆”。lower()。Split(),“西班牙语”)
请注意,我们还将每个单词转换为小写,这将阻止单词在单词袋中重复计算。 如果我们有单词**本书**和单词**本书**,我们希望将它们视为相同的单词,因此将它们转换为小写。
请注意,我们还将每个单词转换为小写,这将阻止单词在单词袋中重复计算。 如果我们有单词`book`和单词`Book`,我们希望将它们视为相同的单词,因此将它们转换为小写。
2. Next, we build our word index, which is simply a dictionary of all the words in our corpus, and then create a unique index value for each word. This can be easily done with a short **for** loop:
......@@ -454,7 +454,7 @@ preds = len(预测标签)
返回 F.log_softmax(self.linear(bow_vec),dim = 1)
输入的长度为 **corpus_size** ,这只是我们的语料库中唯一词的总数。 这是因为对模型的每个输入都是一个词袋表示,由每个句子中的单词计数组成,如果给定单词​​未出现在我们的句子中,则计数为 0。 我们的输出大小为 2,这是我们可以预测的语言数量。 我们的最终预测将包括我们的句子是英语的概率与我们的句子是西班牙文的概率,而我们的最终预测是概率最高的那个。
输入的长度为`corpus_size`,这只是我们的语料库中唯一词的总数。 这是因为对模型的每个输入都是一个词袋表示,由每个句子中的单词计数组成,如果给定单词​​未出现在我们的句子中,则计数为 0。 我们的输出大小为 2,这是我们可以预测的语言数量。 我们的最终预测将包括我们的句子是英语的概率与我们的句子是西班牙文的概率,而我们的最终预测是概率最高的那个。
4. Next, we define some utility functions. We first define **make_bow_vector**, which takes the sentence and transforms it into a bag-of-words representation. We first create a vector consisting of all zeros. We then loop through them and for each word in the sentence, we increment the count of that index within the bag-of-words vector by one. We finally reshape this vector using **with .view()** for entry into our classifier:
......@@ -490,7 +490,7 @@ preds = len(预测标签)
在此循环中,我们首先将梯度归零(否则,PyTorch 会累积计算梯度),然后对于每个句子/标签对,分别将其转换为词袋矢量和目标。 然后,通过使数据向前通过模型的当前状态,我们计算出该特定句子对的预测输出。
然后使用此预测,获取我们的预测标签和实际标签,并在两者上调用定义的 **loss_function** ,以获取此句子的损失度量。 通过向后调用**向后()**,我们通过模型反向传播此损失,并在优化器上调用 **step()**,从而更新模型参数。 最后,我们每 10 个训练步骤打印一次损失:
然后使用此预测,获取我们的预测标签和实际标签,并在两者上调用定义的`loss_function`,以获取此句子的损失度量。 通过向后调用`backward()`,我们通过模型反向传播此损失,并在优化器上调用`step()`,从而更新模型参数。 最后,我们每 10 个训练步骤打印一次损失:
对于范围(100)中的时代:
......@@ -522,7 +522,7 @@ print('Epoch:',str(epoch + 1),',Loss:'+ str(loss.item())
在这里,我们可以看到,随着模型的学习,我们的损失随着时间而减少。 尽管本例中的训练集很小,但是我们仍然可以证明我们的模型学到了一些有用的东西,如下所示:
1. 我们根据未接受模型训练的测试数据中的几句话来评估模型。 在这里,我们首先设置 **torch.no_grad()**,这将停用 **autograd** 引擎,因为由于我们不再训练模型,因此不再需要计算梯度。 接下来,我们将测试句子转换为词袋向量,并将其输入模型以获取预测。
1. 我们根据未接受模型训练的测试数据中的几句话来评估模型。 在这里,我们首先设置`torch.no_grad()`,这将停用 **autograd** 引擎,因为由于我们不再训练模型,因此不再需要计算梯度。 接下来,我们将测试句子转换为词袋向量,并将其输入模型以获取预测。
2. We then simply print the sentence, the true label of the sentence, and then the predicted probabilities. Note that we transform the predicted values from log probabilities back into probabilities. We obtain two probabilities for each prediction, but if we refer back to the label index, we can see that the first probability (index 0) corresponds to Spanish, whereas the other one corresponds to English:
def make_predictions(data):
......@@ -553,7 +553,7 @@ print('Epoch:',str(epoch + 1),',Loss:'+ str(loss.item())
图 2.20 –预测的输出
在这里,我们可以看到,对于我们的两个预测,我们的模型都可以预测正确的答案,但是为什么会这样呢? 我们的模型究竟学到了什么? 我们可以看到我们的第一个测试句子包含单词 **estoy** ,该单词先前在我们的训练集中的西班牙语句子中出现过。 同样,我们可以看到**这本书**一词在我们的训练集中以英语句子出现。 由于我们的模型由单层组成,因此每个节点上的参数都易于解释。
在这里,我们可以看到,对于我们的两个预测,我们的模型都可以预测正确的答案,但是为什么会这样呢? 我们的模型究竟学到了什么? 我们可以看到我们的第一个测试句子包含单词`estoy`,该单词先前在我们的训练集中的西班牙语句子中出现过。 同样,我们可以看到`book`一词在我们的训练集中以英语句子出现。 由于我们的模型由单层组成,因此每个节点上的参数都易于解释。
3. Here, we define a function that takes a word as input and returns the weights on each of the parameters within the layer. For a given word, we get the index of this word from our dictionary and then select these parameters from the same index within the model. Note that our model returns two parameters as we are making two predictions; that is, the model's contribution to the Spanish prediction and the model's contribution to the English prediction:
......@@ -585,9 +585,9 @@ print('Epoch:',str(epoch + 1),',Loss:'+ str(loss.item())
图 2.21 –更新功能的预测输出
在这里,我们可以看到,对于单词 **estoy** 而言,此参数对西班牙语的预测为正,对英语的预测为负。 这意味着对于我们句子中的每个单词“ **estoy** ”,该句子更有可能是西班牙语句子。 类似地,对于**书**一词,我们可以看到这对句子为英语的预测有积极作用。
在这里,我们可以看到,对于单词`estoy`而言,此参数对西班牙语的预测为正,对英语的预测为负。 这意味着对于我们句子中的每个单词`estoy`,该句子更有可能是西班牙语句子。 类似地,对于`book`一词,我们可以看到这对句子为英语的预测有积极作用。
我们可以证明我们的模型仅基于对其进行了训练而学习。 如果我们尝试预测尚未训练过的单词,则可以看到它无法做出准确的决定。 在这种情况下,我们的模型认为英语单词**not”** 是西班牙语:
我们可以证明我们的模型仅基于对其进行了训练而学习。 如果我们尝试预测尚未训练过的单词,则可以看到它无法做出准确的决定。 在这种情况下,我们的模型认为英语单词`not`是西班牙语:
new_sentence =([[“ not”],“英语”)
......
# “第 4 章”:文本预处理,词干和词法化
# “第 4 章”:文本预处理,词干和词形还原
文本数据可以从许多不同的来源收集,并采用许多不同的形式。 文本可以整洁,可读或原始且混乱,也可以采用许多不同的样式和格式。 能够对这些数据进行预处理,以便可以在将其转换为 NLP 模型之前将其转换为标准格式,这就是我们将在本章中介绍的内容。
与标记化相似,词干和词根化是 NLP 预处理的其他形式。 但是,与将文档简化成单个单词的标记化不同,词干和词法化试图将这些单词进一步缩小到其词根。 例如,几乎所有英语动词都有许多不同的变体,具体取决于时态:
与标记化相似,词干和词根化是 NLP 预处理的其他形式。 但是,与将文档简化成单个单词的标记化不同,词干和词形还原试图将这些单词进一步缩小到其词根。 例如,几乎所有英语动词都有许多不同的变体,具体取决于时态:
*他跳了起来*
......@@ -395,7 +395,7 @@ lemmatize_with_pos(句子)
现在我们已经看到了残局化和词根抑制,在的问题上,仍然存在问题,在什么情况下我们应该同时使用这两种技术。 我们看到,两种技术都试图将每个单词的根都减少。 在词根提取中,可能只是目标房间的简化形式,而在词形还原中,它会还原为真正的英语单词词根。
因为词义化需要在 WordNet 语料库中交叉引用目标词,并执行词性分析以确定词义的形式,所以如果必须使用大量词,这可能会花费大量的处理时间。 形容词 这与词干相反,词干使用详细但相对较快的算法来词干。 最终,与计算中的许多问题一样,这是在速度与细节之间进行权衡的问题。 在选择将这些方法中的哪一种纳入我们的深度学习流程时,要在速度和准确性之间进行权衡。 如果时间很重要,那么阻止可能是要走的路。 另一方面,如果您需要模型尽可能详细和准确,则限制词法化可能会产生更好的模型。
因为词义化需要在 WordNet 语料库中交叉引用目标词,并执行词性分析以确定词义的形式,所以如果必须使用大量词,这可能会花费大量的处理时间。 形容词 这与词干相反,词干使用详细但相对较快的算法来词干。 最终,与计算中的许多问题一样,这是在速度与细节之间进行权衡的问题。 在选择将这些方法中的哪一种纳入我们的深度学习流程时,要在速度和准确率之间进行权衡。 如果时间很重要,那么阻止可能是要走的路。 另一方面,如果您需要模型尽可能详细和准确,则限制词形还原可能会产生更好的模型。
# 摘要
......
......@@ -535,7 +535,7 @@ print(“测试精度:{:. 2f}”。format(num_correct / len(test_loader.
图 5.19 –输出值
然后,我们将模型预测与真实标签进行比较,以获得 **correct_tensor** ,这是一个评估我们模型的每个预测是否正确的向量。 然后,我们对该向量求和,然后将其除以其长度,以获得模型的总精度。 在这里,我们获得了 76% 的准确。 尽管我们的模型肯定还远非完美,但鉴于我们的训练量很小且训练时间有限,这一点也不差! 仅用于说明从 NLP 数据学习时 LSTM 的有用性。 接下来,我们将展示如何使用模型从新数据进行预测。
然后,我们将模型预测与真实标签进行比较,以获得 **correct_tensor** ,这是一个评估我们模型的每个预测是否正确的向量。 然后,我们对该向量求和,然后将其除以其长度,以获得模型的总精度。 在这里,我们获得了 76% 的准确。 尽管我们的模型肯定还远非完美,但鉴于我们的训练量很小且训练时间有限,这一点也不差! 仅用于说明从 NLP 数据学习时 LSTM 的有用性。 接下来,我们将展示如何使用模型从新数据进行预测。
## 使用我们的模型进行预测
......
......@@ -123,7 +123,7 @@ CNN 背后的基本概念是卷积。 **卷积**本质上是一个滑动窗口
通过这种方式,我们的模型现在将能够在多个类上执行分类任务,并且我们不再局限于我们之前看过的 0 或 1 二进制分类。 具有更多类的模型可能会因预测而受到影响,因为有更多不同的类可以区分。
在二元分类模型中,假设我们有一个平衡的数据集,我们希望我们的模型仅执行随机猜测就可以达到 50% 的准确性,而具有五个不同类别的多类模型只能具有 基线精度为 20%。 这意味着仅仅因为多类模型的准确度远低于 100%,并不意味着模型本身固有地在做出预测方面就很糟糕。 当涉及从数百个不同类别进行预测的训练模型时,尤其如此。 在这些情况下,仅具有 50% 准确性的模型将被认为表现良好。
在二元分类模型中,假设我们有一个平衡的数据集,我们希望我们的模型仅执行随机猜测就可以达到 50% 的准确率,而具有五个不同类别的多类模型只能具有 基线精度为 20%。 这意味着仅仅因为多类模型的准确度远低于 100%,并不意味着模型本身固有地在做出预测方面就很糟糕。 当涉及从数百个不同类别进行预测的训练模型时,尤其如此。 在这些情况下,仅具有 50% 准确率的模型将被认为表现良好。
现在我们已经定义了多类分类问题,我们需要加载数据以训练模型。
......@@ -207,7 +207,7 @@ train_data.examples [0] .label
这表明我们的训练验证率约为 70% 至 30%。 值得注意的是,我们的输入句子是如何被标记化的,即标点符号被当作它们自己的标记。
现在我们知道我们的神经网络不会将原始文本作为输入,我们必须找到某种方法将其转换为某种形式的嵌入表示。 虽然我们可以训练自己的嵌入层,但可以改用我们在 [“第 3 章”](../Text/3.html#_idTextAnchor051) 中讨论过的预先计算的**手套**向量来转换数据 *,执行文本嵌入*。 这还具有使模型更快地训练的额外好处,因为我们将不需要从头开始手动训练嵌入层:
现在我们知道我们的神经网络不会将原始文本作为输入,我们必须找到某种方法将其转换为某种形式的嵌入表示。 虽然我们可以训练自己的嵌入层,但可以改用我们在 “第 3 章” 中讨论过的预先计算的**手套**向量来转换数据 *,执行文本嵌入*。 这还具有使模型更快地训练的额外好处,因为我们将不需要从头开始手动训练嵌入层:
issues.build_vocab(train_data,
......@@ -375,7 +375,7 @@ model.embedding.weight.data [pad_index] = Torch.zeros(embedding_dimensions)
## 训练 CNN
在定义训练过程之前,我们需要计算性能指标以说明模型的性能(希望!)如何随时间增加。 在我们的二进制分类任务中,准确性是我们用来衡量绩效的简单指标。 对于我们的多分类任务,我们将再次使用准确性,但是计算准确性的过程稍微复杂些,因为我们现在必须确定模型预测的六个类别中的哪个类别以及六个类别中的哪个类别是正确的类别。
在定义训练过程之前,我们需要计算性能指标以说明模型的性能(希望!)如何随时间增加。 在我们的二进制分类任务中,准确率是我们用来衡量绩效的简单指标。 对于我们的多分类任务,我们将再次使用准确率,但是计算准确率的过程稍微复杂些,因为我们现在必须确定模型预测的六个类别中的哪个类别以及六个类别中的哪个类别是正确的类别。
首先,我们定义一个称为 **multi_accuracy** 的函数来计算:
......@@ -389,9 +389,9 @@ acc = correct.sum()/ len(正确)
返回 acc
在这里,对于我们的预测,我们的模型使用 **torch.max** 函数对所有预测返回具有最高预测值的索引。 对于这些预测中的每一个,如果此预测索引与标签的索引相同,则将其视为正确的预测。 然后,我们对所有这些正确的预测进行计数,然后将它们除以预测的总数,以得出多类准确性的度量。 我们可以在训练循环中使用此功能来测量每个时期的准确性
在这里,对于我们的预测,我们的模型使用 **torch.max** 函数对所有预测返回具有最高预测值的索引。 对于这些预测中的每一个,如果此预测索引与标签的索引相同,则将其视为正确的预测。 然后,我们对所有这些正确的预测进行计数,然后将它们除以预测的总数,以得出多类准确率的度量。 我们可以在训练循环中使用此功能来测量每个时期的准确率
接下来,我们定义训练功能。 最初,我们将时间段的损失和准确设置为`0`,我们将其称为 **model.train()**以允许我们在训练模型时更新模型中的参数 模型:
接下来,我们定义训练功能。 最初,我们将时间段的损失和准确设置为`0`,我们将其称为 **model.train()**以允许我们在训练模型时更新模型中的参数 模型:
def 火车(模型,迭代器,优化器,标准):
......@@ -417,7 +417,7 @@ loss.backward()
Optimizer.step()
最后,我们将这一批量的损失和准确性加到整个时期的总损失和准确性中。 在循环遍历该时期内的所有批量之后,我们计算该时期的总损失和准确性并返回:
最后,我们将这一批量的损失和准确率加到整个时期的总损失和准确率中。 在循环遍历该时期内的所有批量之后,我们计算该时期的总损失和准确率并返回:
epoch_loss + = loss.item()
......@@ -445,7 +445,7 @@ model.eval()
minimum_validation_loss = float(‘inf’)
接下来,我们定义训练循环,一次将跨一个时期。 我们记录训练的开始和结束时间,以便我们可以计算出每个步骤花费的时间。 然后,我们只需使用训练数据迭代器对模型调用训练函数来计算训练损失和准确性,并在此过程中更新模型。 然后,我们使用验证迭代器上的评估函数重复此过程,以计算验证数据的损失和准确性,而无需更新模型:
接下来,我们定义训练循环,一次将跨一个时期。 我们记录训练的开始和结束时间,以便我们可以计算出每个步骤花费的时间。 然后,我们只需使用训练数据迭代器对模型调用训练函数来计算训练损失和准确率,并在此过程中更新模型。 然后,我们使用验证迭代器上的评估函数重复此过程,以计算验证数据的损失和准确率,而无需更新模型:
对于范围内的纪元(纪元):
......@@ -481,7 +481,7 @@ print(f’Epoch:{epoch + 1:02} | Epoch Time:{int(end_time-start_time
图 6.17 –测试模型
值得庆幸的是,我们发现确实存在。 训练和验证损失在每个时期都会下降,准确也会提高,这表明我们的模型确实在学习! 经过多次训练后,我们可以采用最佳模型并进行预测。
值得庆幸的是,我们发现确实存在。 训练和验证损失在每个时期都会下降,准确也会提高,这表明我们的模型确实在学习! 经过多次训练后,我们可以采用最佳模型并进行预测。
## 使用经过训练的 CNN 进行预测
......
......@@ -2,7 +2,7 @@
在前两章中,我们使用神经网络对文本进行分类并执行情感分析。 两项任务都涉及获取 NLP 输入并预测一些值。 就我们的情感分析而言,这是一个介于 0 和 1 之间的数字,代表我们句子的情感。 就我们的句子分类模型而言,我们的输出是一个多类预测,其中我们的句子属于多个类别。 但是,如果我们不仅希望做出单个预测,还希望做出整个句子,该怎么办? 在本章中,我们将构建一个序列到序列模型,该模型将一种语言的句子作为输入,并输出另一种语言的句子翻译。
我们已经探索了用于 NLP 学习的几种类型的神经网络架构,即 [“第 5 章”](../Text/5.html#_idTextAnchor092) *中的循环神经网络,循环神经网络和情感分析*,以及卷积 [“第 6 章”](../Text/6.html#_idTextAnchor112) *中的神经网络,使用 CNN 的文本分类*。 在本章中,我们将再次使用这些熟悉的 RNN,而不仅仅是构建简单的 RNN 模型,我们还将 RNN 用作更大,更复杂的模型的一部分,以执行序列到序列的翻译。 通过使用我们在前几章中了解到的 RNN 的基础,我们可以展示如何扩展这些概念,以创建适合目的的各种模型。
我们已经探索了用于 NLP 学习的几种类型的神经网络架构,即 “第 5 章” *中的循环神经网络,循环神经网络和情感分析*,以及卷积 “第 6 章” *中的神经网络,使用 CNN 的文本分类*。 在本章中,我们将再次使用这些熟悉的 RNN,而不仅仅是构建简单的 RNN 模型,我们还将 RNN 用作更大,更复杂的模型的一部分,以执行序列到序列的翻译。 通过使用我们在前几章中了解到的 RNN 的基础,我们可以展示如何扩展这些概念,以创建适合目的的各种模型。
在本章中,我们将介绍以下主题:
......@@ -297,7 +297,7 @@ self.fc_out = nn.Linear(hid_dims,output_dims)
self.dropout = nn.Dropout(辍学)
除了增加了两个关键步骤外,我们的前向通过与编码器非常相似。 首先,从上一层取消输入,以使其为进入嵌入层的正确大小。 我们还添加了一个全连接层,该层采用了 RNN 层的输出隐藏层,并使用它来预测序列中的下一个单词:
除了增加了两个关键步骤外,我们的正向传播与编码器非常相似。 首先,从上一层取消输入,以使其为进入嵌入层的正确大小。 我们还添加了一个全连接层,该层采用了 RNN 层的输出隐藏层,并使用它来预测序列中的下一个单词:
def forward(自我,输入,h,单元格):
......
......@@ -4,5 +4,5 @@
本节包含以下章节:
* [“第 1 章”](../Text/1.html#_idTextAnchor015)*机器学习和深度学习基础知识*
* [“第 2 章”](../Text/2.html#_idTextAnchor029)*NLP 的 PyTorch 1.x 入门*
\ No newline at end of file
* “第 1 章” 和*机器学习和深度学习基础知识*
* “第 2 章” 和 *NLP 的 PyTorch 1.x 入门*
\ No newline at end of file
......@@ -4,5 +4,5 @@
本节包含以下章节:
* [“第 3 章”](../Text/3.html#_idTextAnchor051)*NLP 和文本嵌入*
* [“第 4 章”](../Text/4.html#_idTextAnchor070)*词根和词法提取*
\ No newline at end of file
* “第 3 章” , *NLP 和文本嵌入*
* “第 4 章” 和*词根和词法提取*
\ No newline at end of file
......@@ -4,8 +4,8 @@
本节包含以下章节:
* [“第 5 章”](../Text/5.html#_idTextAnchor092)*循环神经网络和情感分析*
* [“第 6 章”](../Text/6.html#_idTextAnchor112)*卷积神经网络用于文本分类*
* [“第 7 章”](../Text/7.html#_idTextAnchor124)*使用序列到序列神经网络的文本翻译*
* [“第 8 章”](../Text/8.html#_idTextAnchor139)*使用基于注意力的神经网络构建聊天机器人*
* [“第 9 章”](../Text/9.html#_idTextAnchor156)*未来之路*
\ No newline at end of file
* “第 5 章” 和*循环神经网络和情感分析*
* “第 6 章” 和*卷积神经网络用于文本分类*
* “第 7 章” 和*使用序列到序列神经网络的文本翻译*
* “第 8 章” 和*使用基于注意力的神经网络构建聊天机器人*
* “第 9 章” 和*未来之路*
\ No newline at end of file
......@@ -546,7 +546,7 @@ Training loss: 0.2596
# 这个怎么运作...
在此配方中,我们更改了`__init__()`方法,以 0.25 的丢失率添加了该丢失层,这意味着将应用该丢失的层中 25% 的神经元将被随机关闭。 然后,我们编辑`forward`函数,将其应用于其中具有 256 个单位的第一个隐藏层,然后对第二个层(具有 128 个单位)应用该滤除。 在完成激活功能之后,我们在两个层中都应用了激活。 我们必须牢记,必须仅在隐藏层上应用辍学,以防止我们丢失输入数据和丢失输出。
在此配方中,我们更改了`__init__()`方法,以 0.25 的丢失率添加了该丢失层,这意味着将应用该丢失的层中 25% 的神经元将被随机关闭。 然后,我们编辑`forward`函数,将其应用于其中具有 256 个单位的第一个隐藏层,然后对第二个层(具有 128 个单位)应用该滤除。 在完成激活函数之后,我们在两个层中都应用了激活。 我们必须牢记,必须仅在隐藏层上应用辍学,以防止我们丢失输入数据和丢失输出。
# 还有更多...
......@@ -592,7 +592,7 @@ Training loss: 0.2596
# 这个怎么运作...
在此配方中,我们定义了与以前完全相同的网络,但是用`function.relu``function.log_softmax`代替了激活功能和 log softmax,这使我们的代码看起来更加简洁明了。
在此配方中,我们定义了与以前完全相同的网络,但是用`function.relu``function.log_softmax`代替了激活函数和 log softmax,这使我们的代码看起来更加简洁明了。
# 还有更多...
......
......@@ -869,7 +869,7 @@ valid_loss = valid_loss/len(valid_loader.sampler)
# 还有更多...
我们已经运行了训练有素的模型,我们需要根据保持数据或测试数据(即该模型尚未看到的数据)评估模型。 通过这样做,我们可以评估模型的真实性能。 为此,您将必须进入模型测试批量,并且对于每个批量,必须执行`_, prediction = torch.max(output, 1)`将 softmax 概率转换为实际预测,并使用`prediction.eq(target.data.view_as(prediction))`将预测与真实输出标签进行比较,其中 我们确保预测张量和输出张量的尺寸相同。 这将返回一个张量,其中匹配的张量为 1,不匹配的张量为 0。 我们可以使用它来计算每个批量中模型的准确,并将其汇总到整个测试数据集中。
我们已经运行了训练有素的模型,我们需要根据保持数据或测试数据(即该模型尚未看到的数据)评估模型。 通过这样做,我们可以评估模型的真实性能。 为此,您将必须进入模型测试批量,并且对于每个批量,必须执行`_, prediction = torch.max(output, 1)`将 softmax 概率转换为实际预测,并使用`prediction.eq(target.data.view_as(prediction))`将预测与真实输出标签进行比较,其中 我们确保预测张量和输出张量的尺寸相同。 这将返回一个张量,其中匹配的张量为 1,不匹配的张量为 0。 我们可以使用它来计算每个批量中模型的准确,并将其汇总到整个测试数据集中。
# 也可以看看
......
......@@ -228,7 +228,7 @@ return model
在此配方中,我们编写了逆归一化函数以撤消在将图像转换为具有 ImageNet 统计信息的张量时建立的归一化。 我们还定义了`misclassified_images()`方法,用于记录预测错误的图像。 然后使用`SummaryWriter`对象中的`add_image()`方法将分类错误的图像添加到 TensorBoard 中,该方法将输入图像名称,图像和计数器。
然后,我们定义了`test()`方法,该方法在模型的验证数据集上运行验证,并使用`add_scalar()`方法记录测试损失和准确性,就像在训练函数中一样。 最后,我们在验证数据集上返回了测试损失和模型准确性
然后,我们定义了`test()`方法,该方法在模型的验证数据集上运行验证,并使用`add_scalar()`方法记录测试损失和准确率,就像在训练函数中一样。 最后,我们在验证数据集上返回了测试损失和模型准确率
# 加载数据集
......@@ -557,7 +557,7 @@ Epoch | Training Loss | Test Loss | Accuracy |
![](img/fec7751c-9387-4092-ad3f-98ade9667ec3.png)
图 7:准确得分
图 7:准确得分
通过此配方,我们已经训练了模型并在 TensorBoard 中可视化了其结果。
......@@ -569,7 +569,7 @@ Epoch | Training Loss | Test Loss | Accuracy |
从 TensorBoard 图中,我们看到冻结模型中的指标为橙色,解冻后的指标为蓝色,这表明模型解冻后的性能有所提高。 然后,我们从训练数据中采样了图像网格图,并从各个时期对分类错误的示例进行了采样。
我们看到训练和测试损失在各个时期都减少了,准确提高了。
我们看到训练和测试损失在各个时期都减少了,准确提高了。
# 还有更多...
......
......@@ -282,7 +282,7 @@ RNN 是最常见的深度学习算法之一,它们席卷全球。 我们现在
#### 卷积神经网络
**卷积神经网络****CNN**)使我们能够在计算机视觉中获得超人的性能。 在的早期,我们达到了的人类准确性,并且我们仍在逐年提高准确性
**卷积神经网络****CNN**)使我们能够在计算机视觉中获得超人的性能。 在的早期,我们达到了的人类准确率,并且我们仍在逐年提高准确率
卷积网络是最易理解的网络,因为我们有可视化工具可以显示每一层的功能。 **Facebook AI Research****FAIR**)负责人 Yann LeCun 于 1990 年代发明了 CNN。 那时我们无法使用它们,因为我们没有足够的数据集和计算能力。 CNN 基本上像滑动窗口一样扫描您的输入并进行中间表示,然后在最终到达全连接层之前对其进行逐层抽象。 CNN 也成功地用于非图像数据集中。
......
......@@ -509,7 +509,7 @@ tensor([[1]], dtype=torch.uint8)
#### 注意
**Sigmoid 激活**:激活函数在神经网络的各层之间创建非线性。 这是必不可少的,因为在没有非线性的情况下,各层只是将输入值与权重相乘。 在那种情况下,神经网络的单层可以完成 100 层的确切功能; 这只是增加或减少权重值的问题。 乙状结肠激活可能是最传统的激活功能。 它将输入压缩到[0,1]的范围。
**Sigmoid 激活**:激活函数在神经网络的各层之间创建非线性。 这是必不可少的,因为在没有非线性的情况下,各层只是将输入值与权重相乘。 在那种情况下,神经网络的单层可以完成 100 层的确切功能; 这只是增加或减少权重值的问题。 乙状结肠激活可能是最传统的激活函数。 它将输入压缩到[0,1]的范围。
![The functional module](img/B09475_02_10.jpg)
......
......@@ -411,7 +411,7 @@ transform = transforms.Compose(
PyTorch 的 Python 优先方法阻止核心团队在的第一年建立一个单独的探查器,但是当模块开始转向 C / C ++内核时,就很明显需要在 Python 的 cProfiler 上安装一个独立的探查器,这就是 `autograd.profiler`故事的开始。
本节将提供更多的表和统计信息,而不是分步指导,因为 PyTorch 已经使概要分析尽可能简单。 对于概要分析,我们将使用在第二章中开发的相同的 *FizzBu​​zz* 模型。 尽管`autograd.profiler`可以分析图形中的所有操作,但是在此示例中,仅分析了主网络的前向通过,而没有损失函数和后向通过。
本节将提供更多的表和统计信息,而不是分步指导,因为 PyTorch 已经使概要分析尽可能简单。 对于概要分析,我们将使用在第二章中开发的相同的 *FizzBu​​zz* 模型。 尽管`autograd.profiler`可以分析图形中的所有操作,但是在此示例中,仅分析了主网络的正向传播,而没有损失函数和后向通过。
```py
with torch.autograd.profiler.profile() as prof:
......@@ -464,7 +464,7 @@ python -m torch.utils.bottleneck /path/to/source/script.py [args]
## 训练和验证
尽管工作流实际上以将深度模型的部署到生产中而结束,但我们已经到达深度学习工作的最后一步,我们将在第 8 章和[HTG4 PyTorch 投入生产。 在完成所有预处理和模型构建之后,现在我们必须训练网络,测试准确并验证可靠性。 在开源世界(甚至在本书中)中,我们看到的大多数现有代码实现都使用直接方法,在该方法中,我们明确编写了训练,测试和验证所需的每一行,以提高可读性,因为 可以避免样板的特定工具会增加学习曲线,尤其是对于新手。 很显然,对于那些每天都在使用神经网络的程序员来说,可以避免样板的工具将是一个救生员。 因此,PyTorch 社区构建的不是一个而是两个工具:Torchnet 和 ignite。 本次会议仅与点燃有关,因为它被发现比 Torchnet 更为有用和抽象,但两者都是积极开发的工具,有可能在不久的将来合并。
尽管工作流实际上以将深度模型的部署到生产中而结束,但我们已经到达深度学习工作的最后一步,我们将在第 8 章和[HTG4 PyTorch 投入生产。 在完成所有预处理和模型构建之后,现在我们必须训练网络,测试准确并验证可靠性。 在开源世界(甚至在本书中)中,我们看到的大多数现有代码实现都使用直接方法,在该方法中,我们明确编写了训练,测试和验证所需的每一行,以提高可读性,因为 可以避免样板的特定工具会增加学习曲线,尤其是对于新手。 很显然,对于那些每天都在使用神经网络的程序员来说,可以避免样板的工具将是一个救生员。 因此,PyTorch 社区构建的不是一个而是两个工具:Torchnet 和 ignite。 本次会议仅与点燃有关,因为它被发现比 Torchnet 更为有用和抽象,但两者都是积极开发的工具,有可能在不久的将来合并。
### 点燃
......@@ -523,7 +523,7 @@ evaluator.run(val_loader)
训练完成后,`evaluator``val_loader`开始,并通过使用评估数据集运行相同的模型来确保情况得到改善。
那很有趣,但仍然缺少一些片段。 如果用户需要在每个时期之后运行`evaluator`,或者如果用户需要训练师将模型的精度打印到终端,或者将其绘制到 Visdom,Turing 或 Network 图上,该怎么办? 在前面的设置中,有没有办法让知道验证准确是什么? 您可以通过覆盖`Engine`的默认记录器来完成大部分操作,该记录器本质上是保存在`trainer_logger`变量中的 Python 记录器,但实际的答案是事件。
那很有趣,但仍然缺少一些片段。 如果用户需要在每个时期之后运行`evaluator`,或者如果用户需要训练师将模型的精度打印到终端,或者将其绘制到 Visdom,Turing 或 Network 图上,该怎么办? 在前面的设置中,有没有办法让知道验证准确是什么? 您可以通过覆盖`Engine`的默认记录器来完成大部分操作,该记录器本质上是保存在`trainer_logger`变量中的 Python 记录器,但实际的答案是事件。
#### 活动
......@@ -562,7 +562,7 @@ def run_evaluator_on_validation_data(engine):
**注意**:在`create_supervised_trainer`的情况下,`training_loop`函数返回损失,在`create_supervised_evaluator`的情况下,`training_loop`函数返回模型的输出。 但是,如果我们定义一个自定义`training_loop`函数,则此函数返回的内容将是`Engine.state.output`保留的内容。
第二和第三事件处理程序正在`EPOCH_COMPLETED`上运行`evaluator`,但具有不同的数据集。 在第一个功能中,`evaluator`使用训练数据集,在第二个功能中,它使用评估数据集。 太好了,因为现在我们可以在每个时期完成时运行`evaluator`,而不是像第一个示例那样在整个执行结束时运行。 但是,除了运行它之外,处理程序实际上并没有做任何事情。 通常,这里是我们检查平均准确和平均损失的地方,并且我们会进行更复杂的分析,例如混淆度量的创建,我们将在后面看到。 但是,目前的主要收获是:可以为单个事件设置`n`处理程序数量,Ignite 会毫不犹豫地依次调用所有这些处理程序。 接下来是事件的内部`_fire_event`函数,该事件在`training_loop`函数的每个事件中触发。
第二和第三事件处理程序正在`EPOCH_COMPLETED`上运行`evaluator`,但具有不同的数据集。 在第一个功能中,`evaluator`使用训练数据集,在第二个功能中,它使用评估数据集。 太好了,因为现在我们可以在每个时期完成时运行`evaluator`,而不是像第一个示例那样在整个执行结束时运行。 但是,除了运行它之外,处理程序实际上并没有做任何事情。 通常,这里是我们检查平均准确和平均损失的地方,并且我们会进行更复杂的分析,例如混淆度量的创建,我们将在后面看到。 但是,目前的主要收获是:可以为单个事件设置`n`处理程序数量,Ignite 会毫不犹豫地依次调用所有这些处理程序。 接下来是事件的内部`_fire_event`函数,该事件在`training_loop`函数的每个事件中触发。
```py
def _fire_event(self, event_name, *event_args):
......
......@@ -2,7 +2,7 @@
计算机视觉是使计算机具有视觉效果的工程流。 它支持各种图像处理,例如 iPhone,Google Lens 等中的人脸识别。 计算机视觉已经存在了几十年,可能最好在人工智能的帮助下进行探索,这将在本章中进行演示。
几年前,我们在 ImageNet 挑战中达到了计算机视觉的人类准确。 在过去的十年中,计算机视觉发生了巨大的变化,从以学术为导向的对象检测问题到在实际道路上自动驾驶汽车使用的分割问题。 尽管人们提出了许多不同的网络架构来解决计算机视觉问题,但是**卷积神经网络****CNN**)击败了所有这些。
几年前,我们在 ImageNet 挑战中达到了计算机视觉的人类准确。 在过去的十年中,计算机视觉发生了巨大的变化,从以学术为导向的对象检测问题到在实际道路上自动驾驶汽车使用的分割问题。 尽管人们提出了许多不同的网络架构来解决计算机视觉问题,但是**卷积神经网络****CNN**)击败了所有这些。
在本章中,我们将讨论基于 PyTorch 构建的基本 CNN,以及它们的变体,它们已经成功地应用于一些为大公司提供支持的最新模型中。
......@@ -318,7 +318,7 @@ LinkNet 由一个初始块,一个最终块,一个带有四个卷积模块的
然后,解码器模块的输出通过最终模块,该模块将上采样两次,就像初始模块下采样两次一样。 还有更多:与其他语义分割模型相比,LinkNet 通过使用跳过连接的思想可以减少架构中的参数数量。
在每个卷积块之后,编码器块与解码器块进行通信,这使编码器块在前向通过之后会忘记某些信息。 由于编码器模块的输出不必保留该信息,因此参数的数量可能比其他现有架构的数量少得多。 实际上,该论文的作者使用 ResNet18 作为编码器,并且仍然能够以惊人的性能获得最新的结果。 下面是 LinkNet 的架构:
在每个卷积块之后,编码器块与解码器块进行通信,这使编码器块在正向传播之后会忘记某些信息。 由于编码器模块的输出不必保留该信息,因此参数的数量可能比其他现有架构的数量少得多。 实际上,该论文的作者使用 ResNet18 作为编码器,并且仍然能够以惊人的性能获得最新的结果。 下面是 LinkNet 的架构:
![LinkNet](img/B09475_04_11.jpg)
......@@ -386,7 +386,7 @@ LinkNet 中的所有卷积都紧随其后的是批处理规范化和 ReLU 层,
批处理规范化用于规范每个批处理中的数据,而不是一开始只进行一次。 在开始时,标准化对于获得相等比例的输入至关重要,这反过来又可以提高精度。 但是,随着数据流经网络,非线性和权重和偏差的增加可能导致内部数据规模不同。
标准化每一层被证明是解决此特定问题的一种方法,即使我们提高了学习速度,也可以提高准确。 批量归一化还可以帮助网络从更稳定的输入分布中学习,从而加快了网络的收敛速度。 PyTorch 对不同尺寸的输入实现了批量归一化,就像卷积层一样。 在这里我们使用`BatchNorm2d`,因为我们有四维数据,其中一维是批处理大小,另一维是深度。
标准化每一层被证明是解决此特定问题的一种方法,即使我们提高了学习速度,也可以提高准确。 批量归一化还可以帮助网络从更稳定的输入分布中学习,从而加快了网络的收敛速度。 PyTorch 对不同尺寸的输入实现了批量归一化,就像卷积层一样。 在这里我们使用`BatchNorm2d`,因为我们有四维数据,其中一维是批处理大小,另一维是深度。
`BatchNorm2d`用两个可学习的参数实现:伽玛和贝塔。 除非我们将仿射参数设置为`False`,否则 PyTorch 会在反向传播时处理这些功能的学习。 现在,`BatchNorm2d`接受特征数量,ε值,动量和仿射作为参数。
......
......@@ -14,7 +14,7 @@
注意是下一个重大发明,它可以帮助网络将注意力集中在输入的重要部分上,而不是搜索整个输入并试图找到答案。 实际上,来自 Google Brain 和多伦多大学的一个团队证明,注意力可以击败 LSTM 和 GRU 网络[1]。 但是,大多数实现都同时使用 LSTM / GRU 和注意力。
嵌入是通过比较单词在单词簇中的分布来找到单词的概念含义的另一种革命性思想。 嵌入保持单词之间的关系,并将这种关系(它从单词簇中的单词分布中找到)转换为一组浮点数。 嵌入大大减少了输入大小,并极大地提高了性能和准确。 我们将使用 word2vec 进行实验。
嵌入是通过比较单词在单词簇中的分布来找到单词的概念含义的另一种革命性思想。 嵌入保持单词之间的关系,并将这种关系(它从单词簇中的单词分布中找到)转换为一组浮点数。 嵌入大大减少了输入大小,并极大地提高了性能和准确。 我们将使用 word2vec 进行实验。
数据处理是序列数据(尤其是自然语言)的主要挑战之一。 PyTorch 提供了一些实用程序包来处理该问题。 我们将使用预处理后的数据来简化实施,但是我们将遍历实用程序包以了解它们的工作原理。 与这些实用程序包一起,我们将使用`torchtext`,它消除了处理输入数据时将面临的许多困难。
......@@ -238,7 +238,7 @@ PackedSequence(data=tensor([1., 1., 1., 2., 2., 3.]), batch_sizes=tensor([3, 2,
```
`pack_sequence`函数返回`PackedSequence`类的实例,所有用 PyTorch 编写的 RNN 模块都可以接受。 由于`PackedSequence`掩盖了输入中不需要的部分,因此提高了模型的效率和准确。 前面的示例显示了`PackedSequence`的内容。 但是,为简单起见,我们将避免在模型中使用打包序列,而将始终使用填充序列或`BucketIterator`的输出。
`pack_sequence`函数返回`PackedSequence`类的实例,所有用 PyTorch 编写的 RNN 模块都可以接受。 由于`PackedSequence`掩盖了输入中不需要的部分,因此提高了模型的效率和准确。 前面的示例显示了`PackedSequence`的内容。 但是,为简单起见,我们将避免在模型中使用打包序列,而将始终使用填充序列或`BucketIterator`的输出。
#### 编码器
......@@ -376,7 +376,7 @@ LSTM 主要由遗忘门,更新门和单元状态组成,这使得 LSTM 与常
#### GRU
GRU 是一个相对较新的设计,与 LSTM 相比,它效率高且复杂度低。 简而言之,GRU 将遗忘门和更新门合并在一起,并且只对单元状态进行一次一次性更新。 实际上,GRU 没有单独的单元状态和隐藏状态,两者都合并在一起以创建一个状态。 这些简化在不影响网络准确的前提下,极大地降低了 GRU 的复杂性。 由于 GRU 比 LSTM 具有更高的性能,因此 GRU 如今已被广泛使用。
GRU 是一个相对较新的设计,与 LSTM 相比,它效率高且复杂度低。 简而言之,GRU 将遗忘门和更新门合并在一起,并且只对单元状态进行一次一次性更新。 实际上,GRU 没有单独的单元状态和隐藏状态,两者都合并在一起以创建一个状态。 这些简化在不影响网络准确的前提下,极大地降低了 GRU 的复杂性。 由于 GRU 比 LSTM 具有更高的性能,因此 GRU 如今已被广泛使用。
![GRUs](img/B09475_05_07.jpg)
......@@ -451,7 +451,7 @@ RNN 中的层数在语义上类似于任何类型的神经网络中层数的增
##### 双向 RNN
RNN 实现通常是单向的,这就是到目前为止我们已经实现的。 单向和双向 RNN 之间的区别在于,在双向 RNN 中,后向通过等效于在相反方向上的前向通过。 因此,反向传递的输入是相同的序列,但是是反向的。
RNN 实现通常是单向的,这就是到目前为止我们已经实现的。 单向和双向 RNN 之间的区别在于,在双向 RNN 中,后向通过等效于在相反方向上的正向传播。 因此,反向传递的输入是相同的序列,但是是反向的。
事实证明,双向 RNN 的性能要优于单方向的 RNN,并且很容易理解原因,尤其是对于 NLP。 但这不能一概而论,并非在所有情况下都是如此。 从理论上讲,如果手头的任务需要过去和将来的信息,则双向 RNN 往往会工作得更好。 例如,预测单词填补空白需要上一个序列和下一个序列。
......
......@@ -165,7 +165,7 @@ for epoch in range(25):
##### 门控 PixelCNN
DeepMind 在 PixelCNN 的一篇迭代论文中成功地使用了门控 PixelCNN ,该方法通过用 S 型和 tanh 构建的门代替 ReLU 激活功能。 PixelCNN [1]的介绍性论文提供了三种用于解决同一代网络的不同方法,其中具有 RNN 的模型优于其他两种。 DeepMind 仍引入了基于 CNN 的模型来显示与 PixelRNN 相比的速度增益。 但是,随着 PixelCNN 中门控激活的引入,作者能够将性能与 RNN 变体相匹配,从而获得更大的性能增益。 同一篇论文介绍了一种避免盲点并在生成时增加全局和局部条件的机制,这超出了本书的范围,因为对于 WaveNet 模型而言这不是必需的。
DeepMind 在 PixelCNN 的一篇迭代论文中成功地使用了门控 PixelCNN ,该方法通过用 S 型和 tanh 构建的门代替 ReLU 激活函数。 PixelCNN [1]的介绍性论文提供了三种用于解决同一代网络的不同方法,其中具有 RNN 的模型优于其他两种。 DeepMind 仍引入了基于 CNN 的模型来显示与 PixelRNN 相比的速度增益。 但是,随着 PixelCNN 中门控激活的引入,作者能够将性能与 RNN 变体相匹配,从而获得更大的性能增益。 同一篇论文介绍了一种避免盲点并在生成时增加全局和局部条件的机制,这超出了本书的范围,因为对于 WaveNet 模型而言这不是必需的。
### WaveNet
......@@ -631,7 +631,7 @@ class ResidualBlock(nn.Module):
## 摘要
在本章中,我们学习了一系列全新的神经网络,这些神经网络使人工智能世界发生了翻天覆地的变化。 生成网络对我们始终很重要,但是直到最近我们才能达到人类无法比拟的准确。 尽管有一些成功的生成网络架构,但在本章中我们仅讨论了两个最受欢迎的网络。
在本章中,我们学习了一系列全新的神经网络,这些神经网络使人工智能世界发生了翻天覆地的变化。 生成网络对我们始终很重要,但是直到最近我们才能达到人类无法比拟的准确。 尽管有一些成功的生成网络架构,但在本章中我们仅讨论了两个最受欢迎的网络。
生成网络使用 CNN 或 RNN 之类的基本架构作为整个网络的构建块,但是使用一些不错的技术来确保网络正在学习生成一些输出。 到目前为止,生成网络已在艺术中得到广泛使用,并且由于模型必须学习数据分布以生成输出,因此我们可以轻松地预测生成网络将成为许多复杂网络的基础。 生成网络最有前途的用途可能不是生成,而是通过生成学习数据分发并将该信息用于其他目的。
......
......@@ -26,7 +26,7 @@ labels = torch.rand(1, 1000)
```
接下来,我们通过模型的每一层运行输入数据以进行预测。 这是**前向通过**
接下来,我们通过模型的每一层运行输入数据以进行预测。 这是**正向传播**
```py
prediction = model(data) # forward pass
......
......@@ -149,7 +149,7 @@ print(f'Result: y = {a.item()} + {b.item()} x + {c.item()} x^2 + {d.item()} x^3'
在上述示例中,我们必须手动实现神经网络的前向和后向传递。 对于小型的两层网络,手动实施反向传递并不是什么大问题,但是对于大型的复杂网络来说,可以很快变得非常麻烦。
幸运的是,我们可以使用[自动微分](https://en.wikipedia.org/wiki/Automatic_differentiation)来自动计算神经网络中的反向传递。 PyTorch 中的 **autograd** 软件包正是提供了此功能。 使用 autograd 时,网络的前向通过将定义**计算图**; 图中的节点为张量,边为从输入张量产生输出张量的函数。 然后通过该图进行反向传播,可以轻松计算梯度。
幸运的是,我们可以使用[自动微分](https://en.wikipedia.org/wiki/Automatic_differentiation)来自动计算神经网络中的反向传递。 PyTorch 中的 **autograd** 软件包正是提供了此功能。 使用 autograd 时,网络的正向传播将定义**计算图**; 图中的节点为张量,边为从输入张量产生输出张量的函数。 然后通过该图进行反向传播,可以轻松计算梯度。
这听起来很复杂,在实践中非常简单。 每个张量代表计算图中的一个节点。 如果`x`是具有`x.requires_grad=True`的张量,则`x.grad`是另一个张量,其保持`x`相对于某个标量值的梯度。
......
......@@ -4,7 +4,7 @@
经过训练的三阶多项式,可以通过最小化平方的欧几里得距离来预测\(y = \ sin(x)\)\(-pi \)\(pi \)
此实现使用 numpy 手动计算前向通过,损耗和后向通过。
此实现使用 numpy 手动计算正向传播,损耗和后向通过。
numpy 数组是通用的 n 维数组; 它对深度学习,梯度或计算图一无所知,而只是执行通用数值计算的一种方法。
......
......@@ -4,7 +4,7 @@
经过训练的三阶多项式,可以通过最小化平方的欧几里得距离来预测\(y = \ sin(x)\)\(-pi \)\(pi \)
此实现使用 PyTorch 张量手动计算前向通过,损耗和后向通过。
此实现使用 PyTorch 张量手动计算正向传播,损耗和后向通过。
PyTorch Tensor 基本上与 numpy 数组相同:它对深度学习或计算图或梯度一无所知,只是用于任意数值计算的通用 n 维数组。
......
......@@ -4,7 +4,7 @@
经过训练的三阶多项式,可以通过最小化平方的欧几里得距离来预测\(y = \ sin(x)\)\(-pi \)\(pi \)
此实现使用 PyTorch 张量上的运算来计算前向通过,并使用 PyTorch autograd 来计算梯度。
此实现使用 PyTorch 张量上的运算来计算正向传播,并使用 PyTorch autograd 来计算梯度。
PyTorch 张量表示计算图中的一个节点。 如果`x`是具有`x.requires_grad=True`的张量,则`x.grad`是另一个张量,其保持`x`相对于某个标量值的梯度。
......
......@@ -4,7 +4,7 @@
经过训练的三阶多项式,可以通过最小化平方的欧几里得距离来预测\(y = \ sin(x)\)\(-pi \)\(pi \)。 而不是将多项式写为\(y = a + bx + cx ^ 2 + dx ^ 3 \),我们将多项式写为\(y = a + b P_3(c + dx)\)其中\(P_3(x )= rac {1} {2} \ left(5x ^ 3-3x ight)\)是三次的[勒让德多项式](https://en.wikipedia.org/wiki/Legendre_polynomials)
此实现使用 PyTorch 张量上的运算来计算前向通过,并使用 PyTorch autograd 来计算梯度。
此实现使用 PyTorch 张量上的运算来计算正向传播,并使用 PyTorch autograd 来计算梯度。
在此实现中,我们实现了自己的自定义 autograd 函数来执行\(P_3'(x)\)。 通过数学,\(P_3'(x)= rac {3} {2} \ left(5x ^ 2-1 ight)\)
......
......@@ -117,7 +117,7 @@ bias = torch.zeros(10, requires_grad=True)
```
由于 PyTorch 具有自动计算梯度的功能,我们可以将任何标准的 Python 函数(或可调用对象)用作模型! 因此,我们只需编写一个普通矩阵乘法和广播加法即可创建一个简单的线性模型。 我们还需要激活功能,因此我们将编写并使用 <cite>log_softmax</cite> 。 请记住:尽管 PyTorch 提供了许多预写的损失函数,激活函数等,但是您可以使用纯 Python 轻松编写自己的函数。 PyTorch 甚至会自动为您的功能创建快速 GPU 或矢量化的 CPU 代码。
由于 PyTorch 具有自动计算梯度的功能,我们可以将任何标准的 Python 函数(或可调用对象)用作模型! 因此,我们只需编写一个普通矩阵乘法和广播加法即可创建一个简单的线性模型。 我们还需要激活函数,因此我们将编写并使用 <cite>log_softmax</cite> 。 请记住:尽管 PyTorch 提供了许多预写的损失函数,激活函数等,但是您可以使用纯 Python 轻松编写自己的函数。 PyTorch 甚至会自动为您的功能创建快速 GPU 或矢量化的 CPU 代码。
```py
def log_softmax(x):
......@@ -128,7 +128,7 @@ def model(xb):
```
在上面,`@`代表点积运算。 我们将对一批数据(在本例中为 64 张图像)调用函数。 这是一个*前向通过*。 请注意,由于我们从随机权重开始,因此在这一阶段,我们的预测不会比随机预测更好。
在上面,`@`代表点积运算。 我们将对一批数据(在本例中为 64 张图像)调用函数。 这是一个*正向传播*。 请注意,由于我们从随机权重开始,因此在这一阶段,我们的预测不会比随机预测更好。
```py
bs = 64 # batch size
......@@ -175,7 +175,7 @@ tensor(2.3735, grad_fn=<NegBackward>)
```
我们还实现一个函数来计算模型的准确。 对于每个预测,如果具有最大值的索引与目标值匹配,则该预测是正确的。
我们还实现一个函数来计算模型的准确。 对于每个预测,如果具有最大值的索引与目标值匹配,则该预测是正确的。
```py
def accuracy(out, yb):
......@@ -184,7 +184,7 @@ def accuracy(out, yb):
```
让我们检查一下随机模型的准确性,以便我们可以看出随着损失的增加,准确性是否有所提高。
让我们检查一下随机模型的准确率,以便我们可以看出随着损失的增加,准确率是否有所提高。
```py
print(accuracy(preds, yb))
......@@ -240,7 +240,7 @@ for epoch in range(epochs):
就是这样:我们完全从头开始创建并训练了一个最小的神经网络(在这种情况下,是逻辑回归,因为我们没有隐藏的层)!
让我们检查损失和准确性,并将其与我们之前获得的进行比较。 我们希望损失会减少,准确性会增加,而且确实如此。
让我们检查损失和准确率,并将其与我们之前获得的进行比较。 我们希望损失会减少,准确率会增加,而且确实如此。
```py
print(loss_func(model(xb), yb), accuracy(model(xb), yb))
......@@ -258,7 +258,7 @@ tensor(0.0811, grad_fn=<NegBackward>) tensor(1.)
现在,我们将重构代码,使其执行与以前相同的操作,只是我们将开始利用 PyTorch 的`nn`类使其更加简洁和灵活。 从这里开始的每一步,我们都应该使代码中的一个或多个:更短,更易理解和/或更灵活。
第一步也是最简单的步骤,就是用`torch.nn.functional`(通常按照惯例将其导入到名称空间`F`中)替换我们的手写激活和丢失函数,从而缩短代码长度。 该模块包含`torch.nn`库中的所有功能(而该库的其他部分包含类)。 除了广泛的损失和激活功能外,您还会在这里找到一些方便的功能来创建神经网络,例如合并功能。 (还有一些用于进行卷积,线性层等的函数,但是正如我们将看到的那样,通常可以使用库的其他部分来更好地处理这些函数。)
第一步也是最简单的步骤,就是用`torch.nn.functional`(通常按照惯例将其导入到名称空间`F`中)替换我们的手写激活和丢失函数,从而缩短代码长度。 该模块包含`torch.nn`库中的所有功能(而该库的其他部分包含类)。 除了广泛的损失和激活函数外,您还会在这里找到一些方便的功能来创建神经网络,例如合并功能。 (还有一些用于进行卷积,线性层等的函数,但是正如我们将看到的那样,通常可以使用库的其他部分来更好地处理这些函数。)
如果您使用的是负对数似然损失和对数 softmax 激活,那么 Pytorch 会提供结合了两者的单一功能`F.cross_entropy`。 因此,我们甚至可以从模型中删除激活函数。
......@@ -272,7 +272,7 @@ def model(xb):
```
请注意,我们不再在`model`函数中调用`log_softmax`。 让我们确认我们的损失和准确与以前相同:
请注意,我们不再在`model`函数中调用`log_softmax`。 让我们确认我们的损失和准确与以前相同:
```py
print(loss_func(model(xb), yb), accuracy(model(xb), yb))
......
......@@ -297,7 +297,7 @@ print('Finished Training')
![intermediate/../../_static/img/tensorboard_images.png](img/d5ab1f07cb4a9d9200c2a2d3b238340d.png)
在之前的教程中,我们研究了模型训练后的每类准确; 在这里,我们将使用 TensorBoard 绘制每个类别的精确调用曲线(在中为好解释[)。](https://www.scikit-yb.org/en/latest/api/classifier/prcurve.html)
在之前的教程中,我们研究了模型训练后的每类准确; 在这里,我们将使用 TensorBoard 绘制每个类别的精确调用曲线(在中为好解释[)。](https://www.scikit-yb.org/en/latest/api/classifier/prcurve.html)
## 6.使用 TensorBoard 评估经过训练的模型](docs / modern-java-zh /
......
......@@ -46,7 +46,7 @@ import matplotlib.pyplot as plt
本教程只有三个输入,定义如下:
* **epsilons** -用于运行的 epsilon 值列表。 在列表中保留 0 很重要,因为它表示原始测试集上的模型性能。 同样,从直觉上讲,我们期望ε越大,扰动越明显,但是从降低模型准确的角度来看,攻击越有效。 由于此处的数据范围为\([0,1] \),因此 epsilon 值不得超过 1。
* **epsilons** -用于运行的 epsilon 值列表。 在列表中保留 0 很重要,因为它表示原始测试集上的模型性能。 同样,从直觉上讲,我们期望ε越大,扰动越明显,但是从降低模型准确的角度来看,攻击越有效。 由于此处的数据范围为\([0,1] \),因此 epsilon 值不得超过 1。
* **pretrained_model** -到使用 [pytorch / examples / mnist](https://github.com/pytorch/examples/tree/master/mnist) 训练的 MNIST 模型的路径。 为简单起见,请在此处下载预训练模型[](https://drive.google.com/drive/folders/1fn83DF14tWmit0RTKWRhPq5uVXt73e0h?usp=sharing)
* **use_cuda** -布尔标志,如果需要和可用,则使用 CUDA。 请注意,具有 CUDA 的 GPU 在本教程中并不重要,因为 CPU 不会花费很多时间。
......@@ -144,7 +144,7 @@ def fgsm_attack(image, epsilon, data_grad):
### 测试功能](docs / modern-java-zh /
最后,本教程的主要结果来自`test`函数。 每次调用此测试功能都会在 MNIST 测试集上执行完整的测试步骤,并报告最终精度。 但是,请注意,此功能还需要 *epsilon* 输入。 这是因为`test`函数报告实力为\(\ epsilon \)的来自对手的攻击模型的准确性。 更具体地说,对于测试集中的每个样本,函数都会计算输入数据(\(data \ _grad \))的损耗梯度,并使用`fgsm_attack`创建一个扰动图像(\(perturbed \ _data \)) ,然后检查受干扰的示例是否具有对抗性。 除了测试模型的准确性外,该功能还保存并返回了一些成功的对抗示例,以供以后可视化。
最后,本教程的主要结果来自`test`函数。 每次调用此测试功能都会在 MNIST 测试集上执行完整的测试步骤,并报告最终精度。 但是,请注意,此功能还需要 *epsilon* 输入。 这是因为`test`函数报告实力为\(\ epsilon \)的来自对手的攻击模型的准确率。 更具体地说,对于测试集中的每个样本,函数都会计算输入数据(\(data \ _grad \))的损耗梯度,并使用`fgsm_attack`创建一个扰动图像(\(perturbed \ _data \)) ,然后检查受干扰的示例是否具有对抗性。 除了测试模型的准确率外,该功能还保存并返回了一些成功的对抗示例,以供以后可视化。
```py
def test( model, device, test_loader, epsilon ):
......@@ -213,7 +213,7 @@ def test( model, device, test_loader, epsilon ):
### 运行攻击](docs / modern-java-zh /
实现的最后一部分是实际运行攻击。 在这里,我们为 *epsilons* 输入中的每个 epsilon 值运行完整的测试步骤。 对于每个 epsilon,我们还保存最终精度,并在接下来的部分中绘制一些成功的对抗示例。 请注意,随着ε值的增加,打印的精度如何降低。 另外,请注意\(\ epsilon = 0 \)表示原始测试准确,没有受到攻击。
实现的最后一部分是实际运行攻击。 在这里,我们为 *epsilons* 输入中的每个 epsilon 值运行完整的测试步骤。 对于每个 epsilon,我们还保存最终精度,并在接下来的部分中绘制一些成功的对抗示例。 请注意,随着ε值的增加,打印的精度如何降低。 另外,请注意\(\ epsilon = 0 \)表示原始测试准确,没有受到攻击。
```py
accuracies = []
......@@ -242,9 +242,9 @@ Epsilon: 0.3 Test Accuracy = 869 / 10000 = 0.0869
## 结果](docs / modern-java-zh /
### 准确与 Epsilon](docs / modern-java-zh /
### 准确与 Epsilon](docs / modern-java-zh /
第一个结果是精度与ε曲线的关系。 如前所述,随着ε的增加,我们预计测试精度会降低。 这是因为更大的ε意味着我们朝着将损失最大化的方向迈出了更大的一步。 请注意,即使 epsilon 值是线性间隔的,曲线中的趋势也不是线性的。 例如,\(\ epsilon = 0.05 \)处的精度仅比\(\ epsilon = 0 \)低约 4%,但\(\ epsilon = 0.2 \)处的精度比\(\ epsilon = 0.15 \)。 另外,请注意,模型的准确性在\(\ epsilon = 0.25 \)和\(\ epsilon = 0.3 \)之间达到 10 类分类器的随机准确性
第一个结果是精度与ε曲线的关系。 如前所述,随着ε的增加,我们预计测试精度会降低。 这是因为更大的ε意味着我们朝着将损失最大化的方向迈出了更大的一步。 请注意,即使 epsilon 值是线性间隔的,曲线中的趋势也不是线性的。 例如,\(\ epsilon = 0.05 \)处的精度仅比\(\ epsilon = 0 \)低约 4%,但\(\ epsilon = 0.2 \)处的精度比\(\ epsilon = 0.15 \)。 另外,请注意,模型的准确率在\(\ epsilon = 0.25 \)和\(\ epsilon = 0.3 \)之间达到 10 类分类器的随机准确率
```py
plt.figure(figsize=(5,5))
......@@ -262,7 +262,7 @@ plt.show()
### 对抗示例样本](docs / modern-java-zh /
还记得没有免费午餐的想法吗? 在这种情况下,随着ε的增加,测试精度降低**,但**的扰动变得更容易察觉。 实际上,在攻击者必须考虑的准确下降和可感知性之间要进行权衡。 在这里,我们展示了每个 epsilon 值下成功对抗示例的一些示例。 绘图的每一行显示不同的ε值。 第一行是\(\ epsilon = 0 \)示例,这些示例表示没有干扰的原始“干净”图像。 每张图片的标题均显示“原始分类->对抗分类”。 注意,扰动在\(\ epsilon = 0.15 \)处开始变得明显,而在\(\ epsilon = 0.3 \)处则非常明显。 但是,在所有情况下,尽管增加了噪音,人类仍然能够识别正确的类别。
还记得没有免费午餐的想法吗? 在这种情况下,随着ε的增加,测试精度降低**,但**的扰动变得更容易察觉。 实际上,在攻击者必须考虑的准确下降和可感知性之间要进行权衡。 在这里,我们展示了每个 epsilon 值下成功对抗示例的一些示例。 绘图的每一行显示不同的ε值。 第一行是\(\ epsilon = 0 \)示例,这些示例表示没有干扰的原始“干净”图像。 每张图片的标题均显示“原始分类->对抗分类”。 注意,扰动在\(\ epsilon = 0.15 \)处开始变得明显,而在\(\ epsilon = 0.3 \)处则非常明显。 但是,在所有情况下,尽管增加了噪音,人类仍然能够识别正确的类别。
```py
# Plot several examples of adversarial samples at each epsilon
......
......@@ -270,7 +270,7 @@ scheduler = optim.lr_scheduler.StepLR(optimizer, step_size=20, gamma=0.1) # red
## 训练和测试网络](docs / modern-java-zh /
现在,我们定义一个训练函数,它将训练数据输入模型中,并执行向后传递和优化步骤。 对于训练,我们将使用的损失是负对数可能性。 然后,在每个时期之后将对网络进行测试,以查看训练期间准确如何变化。
现在,我们定义一个训练函数,它将训练数据输入模型中,并执行向后传递和优化步骤。 对于训练,我们将使用的损失是负对数可能性。 然后,在每个时期之后将对网络进行测试,以查看训练期间准确如何变化。
```py
def train(model, epoch, log_interval):
......@@ -302,7 +302,7 @@ def train(model, epoch, log_interval):
```
现在我们有了训练功能,我们需要制作一个用于测试网络准确的功能。 我们将模型设置为`eval()`模式,然后对测试数据集进行推断。 调用`eval()`将网络中所有模块中的训练变量设置为 false。 某些层(例如批处理归一化层和丢弃层)在训练期间的行为会有所不同,因此此步骤对于获取正确的结果至关重要。
现在我们有了训练功能,我们需要制作一个用于测试网络准确的功能。 我们将模型设置为`eval()`模式,然后对测试数据集进行推断。 调用`eval()`将网络中所有模块中的训练变量设置为 false。 某些层(例如批处理归一化层和丢弃层)在训练期间的行为会有所不同,因此此步骤对于获取正确的结果至关重要。
```py
def number_of_correct(pred, target):
......@@ -335,7 +335,7 @@ def test(model, epoch):
```
最后,我们可以训练和测试网络。 我们将训练网络十个时期,然后降低学习率,再训练十个时期。 在每个时期之后将对网络进行测试,以查看训练过程中准确如何变化。
最后,我们可以训练和测试网络。 我们将训练网络十个时期,然后降低学习率,再训练十个时期。 在每个时期之后将对网络进行测试,以查看训练过程中准确如何变化。
```py
log_interval = 20
......
......@@ -63,7 +63,7 @@ torch_model = SuperResolutionNet(upscale_factor=3)
```
通常,您现在将训练此模型。 但是,在本教程中,我们将下载一些预训练的权重。 请注意,此模型未经过充分训练以提供良好的准确,此处仅用于演示目的。
通常,您现在将训练此模型。 但是,在本教程中,我们将下载一些预训练的权重。 请注意,此模型未经过充分训练以提供良好的准确,此处仅用于演示目的。
在导出模型之前,请先调用`torch_model.eval()``torch_model.train(False)`,以将模型转换为推理模式,这一点很重要。 这是必需的,因为像 dropout 或 batchnorm 这样的运算符在推断和训练模式下的行为会有所不同。
......
......@@ -4,7 +4,7 @@
**作者**[Peter Goldsborough](https://www.goldsborough.me/)
PyTorch 提供了与神经网络,任意张量代数,数据整理和其他目的有关的大量操作。 但是,您仍然可能发现自己需要更多的自定义操作。 例如,您可能想使用论文中发现的新颖的激活功能,或者实现您在研究过程中开发的操作。
PyTorch 提供了与神经网络,任意张量代数,数据整理和其他目的有关的大量操作。 但是,您仍然可能发现自己需要更多的自定义操作。 例如,您可能想使用论文中发现的新颖的激活函数,或者实现您在研究过程中开发的操作。
在 PyTorch 中集成这样的自定义操作的最简单方法是通过扩展[此处](https://pytorch.org/docs/master/notes/extending.html)概述的`Function``Module`来用 Python 编写它。 这为您提供了自动区分的全部功能(使您不必编写派生函数)以及 Python 的通常表达能力。 但是,有时您的操作可以用 C ++更好地实现。 例如,您的代码可能需要*确实*快速,因为在模型中它经常被调用,或者即使很少调用也很昂贵。 另一个合理的原因是它依赖于其他 C 或 C ++库或与之交互。 为了解决这种情况,PyTorch 提供了一种非常简单的方式来编写自定义 *C ++扩展*
......@@ -14,7 +14,7 @@ C ++扩展是我们开发的一种机制,允许用户(您)创建源外定
本说明的其余部分将逐步介绍编写和使用 C ++(和 CUDA)扩展的实际示例。 如果您被追捕,或者在一天结束前仍未完成该操作,就会有人开除您,则可以跳过本节,直接进入下一部分的实施细节。
假设您想出了一种新型的循环装置,发现与现有技术相比,它具有更好的性能。 该循环单元类似于 LSTM,但不同之处在于它缺少*遗忘门*,并使用*指数线性单元*(ELU)作为其内部激活功能。 由于此设备永远不会忘记,因此我们将其称为 *LLTM**长期内存*单元。
假设您想出了一种新型的循环装置,发现与现有技术相比,它具有更好的性能。 该循环单元类似于 LSTM,但不同之处在于它缺少*遗忘门*,并使用*指数线性单元*(ELU)作为其内部激活函数。 由于此设备永远不会忘记,因此我们将其称为 *LLTM**长期内存*单元。
LLTM 与普通 LSTM 的两种区别非常重要,以至于我们无法为自己的目的配置 PyTorch 的`LSTMCell`,因此我们必须创建一个自定义单元。 这样做的第一个也是最简单的方法,并且在所有情况下都可能是一个好的第一步,是使用 Python 在纯 PyTorch 中实现我们所需的功能。 为此,我们需要子类`torch.nn.Module`并实现 LLTM 的前向传递。 看起来像这样:
......
......@@ -154,7 +154,7 @@ tune.report(loss=(val_loss / val_steps), accuracy=correct / total)
```
在这里,我们首先保存一个检查点,然后将一些指标报告给 Ray Tune。 具体来说,我们将验证损失和准确发送回 Ray Tune。 然后,Ray Tune 可以使用这些指标来决定哪种超参数配置可以带来最佳结果。 这些指标还可用于尽早停止效果不佳的试验,以避免浪费资源进行试验。
在这里,我们首先保存一个检查点,然后将一些指标报告给 Ray Tune。 具体来说,我们将验证损失和准确发送回 Ray Tune。 然后,Ray Tune 可以使用这些指标来决定哪种超参数配置可以带来最佳结果。 这些指标还可用于尽早停止效果不佳的试验,以避免浪费资源进行试验。
保存检查点是可选的,但是,如果我们想使用高级调度程序,例如[基于人口的训练](https://docs.ray.io/en/master/tune/tutorials/tune-advanced-tutorial.html),则有必要。 另外,通过保存检查点,我们可以稍后加载经过训练的模型并在测试集上对其进行验证。
......@@ -254,7 +254,7 @@ def train_cifar(config, checkpoint_dir=None, data_dir=None):
如您所见,大多数代码直接来自原始示例。
## 测试集准确](docs / modern-java-zh /
## 测试集准确](docs / modern-java-zh /
通常,机器学习模型的性能是在保持测试集上使用尚未用于训练模型的数据进行测试的。 我们还将其包装在一个函数中:
......@@ -320,7 +320,7 @@ result = tune.run(
在这里,我们还可以指定分数 GPU,因此`gpus_per_trial=0.5`之类的东西完全有效。 然后,试用版将彼此共享 GPU。 您只需要确保模型仍然适合 GPU 内存即可。
训练完模型后,我们将找到性能最好的模型,并从检查点文件中加载训练后的网络。 然后,我们获得测试仪的准确,并通过打印报告一切。
训练完模型后,我们将找到性能最好的模型,并从检查点文件中加载训练后的网络。 然后,我们获得测试仪的准确,并通过打印报告一切。
完整的主要功能如下:
......
......@@ -190,7 +190,7 @@ print(list(module.named_buffers()))
```
为了使前向通过不更改即可工作,需要存在`weight`属性。 在`torch.nn.utils.prune`中实现的修剪技术计算权重的修剪版本(通过将掩码与原始参数组合)并将它们存储在属性`weight`中。 注意,这不再是`module`的参数,现在只是一个属性。
为了使正向传播不更改即可工作,需要存在`weight`属性。 在`torch.nn.utils.prune`中实现的修剪技术计算权重的修剪版本(通过将掩码与原始参数组合)并将它们存储在属性`weight`中。 注意,这不再是`module`的参数,现在只是一个属性。
```py
print(module.weight)
......
......@@ -8,7 +8,7 @@
## 简介](docs / modern-java-zh /
量化涉及将模型的权重和激活从 float 转换为 int,这可以导致模型尺寸更小,推断速度更快,而对准确的影响很小。
量化涉及将模型的权重和激活从 float 转换为 int,这可以导致模型尺寸更小,推断速度更快,而对准确的影响很小。
在本教程中,我们将最简单的量化形式-[动态量化](https://pytorch.org/docs/stable/quantization.html#torch.quantization.quantize_dynamic)应用于基于 LSTM 的下一个单词预测模型,紧紧遵循 PyTorch 示例中的[单词语言模型](https://github.com/pytorch/examples/tree/master/word_language_model)
......
......@@ -18,7 +18,7 @@
* BERT,或者说 Transformers 的双向嵌入表示,是一种预训练语言表示的新方法,它可以在许多常见的自然语言处理(NLP)任务(例如问题解答,文本分类, 和别的。 可以在此处找到[](https://arxiv.org/pdf/1810.04805.pdf)
* PyTorch 中的动态量化支持将浮点模型转换为具有静态 int8 或 float16 数据类型的权重和动态量化激活的量化模型。 当权重量化为 int8 时,激活(每批)动态量化为 int8。 在 PyTorch 中,我们有 [torch.quantization.quantize_dynamic API](https://pytorch.org/docs/stable/quantization.html#torch.quantization.quantize_dynamic) ,该 API 用仅动态权重的量化版本替换了指定的模块,并输出了量化模型。
* 我们在通用语言理解评估基准[(GLUE)](https://gluebenchmark.com/)中演示了 [Microsoft Research Paraphrase 语料库(MRPC)任务](https://www.microsoft.com/en-us/download/details.aspx?id=52398)的准确和推理性能结果。 MRPC(Dolan 和 Brockett,2005 年)是从在线新闻源中自动提取的句子对的语料库,带有人工注释,说明句子中的句子在语义上是否等效。 由于班级不平衡(正向为 68%,负向为 32% ),我们遵循常规做法并报告 [F1 得分](https://scikit-learn.org/stable/modules/generated/sklearn.metrics.f1_score.html)。 MRPC 是用于语言对分类的常见 NLP 任务,如下所示。
* 我们在通用语言理解评估基准[(GLUE)](https://gluebenchmark.com/)中演示了 [Microsoft Research Paraphrase 语料库(MRPC)任务](https://www.microsoft.com/en-us/download/details.aspx?id=52398)的准确和推理性能结果。 MRPC(Dolan 和 Brockett,2005 年)是从在线新闻源中自动提取的句子对的语料库,带有人工注释,说明句子中的句子在语义上是否等效。 由于班级不平衡(正向为 68%,负向为 32% ),我们遵循常规做法并报告 [F1 得分](https://scikit-learn.org/stable/modules/generated/sklearn.metrics.f1_score.html)。 MRPC 是用于语言对分类的常见 NLP 任务,如下所示。
![../_img/bert.png](img/b43b70d8a6eef9ea4f75867b5e83b483.png)
......@@ -372,7 +372,7 @@ print_size_of_model(quantized_model)
本教程中使用的 BERT 模型(`bert-base-uncased`)的词汇量 V 为 30522。在嵌入量为 768 的情况下,单词嵌入表的总大小为〜4(Bytes / FP32)* 30522 * 768 = 90 MB 。 因此,借助量化,非嵌入表部分的模型大小从 350 MB(FP32 模型)减少到 90 MB(INT8 模型)。
### 3.2 评估推理准确和时间](docs / modern-java-zh /
### 3.2 评估推理准确和时间](docs / modern-java-zh /
接下来,我们比较一下动态量化后原始 FP32 模型和 INT8 模型之间的推断时间以及评估精度。
......@@ -402,7 +402,7 @@ time_model_evaluation(quantized_model, configs, tokenizer)
```
在 MRPC 任务的微调 BERT 模型上应用训练后动态量化后,我们的 F1 分数准确为 0.6%。 作为比较,在[的最新论文](https://arxiv.org/pdf/1910.06188.pdf)(表 1)中,通过应用训练后动态量化,可以达到 0.8788;通过应用量化感知训练,可以达到 0.8956。 主要区别在于我们在 PyTorch 中支持非对称量化,而该论文仅支持对称量化。
在 MRPC 任务的微调 BERT 模型上应用训练后动态量化后,我们的 F1 分数准确为 0.6%。 作为比较,在[的最新论文](https://arxiv.org/pdf/1910.06188.pdf)(表 1)中,通过应用训练后动态量化,可以达到 0.8788;通过应用量化感知训练,可以达到 0.8956。 主要区别在于我们在 PyTorch 中支持非对称量化,而该论文仅支持对称量化。
请注意,在本教程中,为了进行单线程比较,我们将线程数设置为 1。 我们还为这些量化的 INT8 运算符支持运算内并行化。 用户现在可以通过`torch.set_num_threads(N)`设置多线程(`N`是内部运算并行线程的数量)。 启用帧内并行支持的一项初步要求是使用正确的[后端](https://pytorch.org/docs/stable/notes/cpu_threading_torchscript_inference.html#build-options)(例如 OpenMP,Native 或 TBB)构建 PyTorch。 您可以使用`torch.__config__.parallel_info()`检查并行化设置。 在使用 PyTorch 和本机后端进行并行化的同一台 MacBook Pro 上,我们可以花大约 46 秒的时间来处理 MRPC 数据集的评估。
......@@ -429,7 +429,7 @@ loaded_quantized_model = torch.jit.load("bert_traced_eager_quant.pt")
## 结论](docs / modern-java-zh /
在本教程中,我们演示了如何演示如何将 BERT 等著名的最新 NLP 模型转换为动态量化模型。 动态量化可以减小模型的大小,而对准确的影响有限。
在本教程中,我们演示了如何演示如何将 BERT 等著名的最新 NLP 模型转换为动态量化模型。 动态量化可以减小模型的大小,而对准确的影响有限。
谢谢阅读! 与往常一样,我们欢迎您提供反馈,因此,如果有任何问题,请在中创建一个问题[](https://github.com/pytorch/pytorch/issues)
......
......@@ -6,9 +6,9 @@
**由**编辑:[赛斯·魏德曼](https://github.com/SethHWeidman/)
本教程说明了如何进行训练后的静态量化,并说明了两种更先进的技术-每通道量化和量化感知训练-可以进一步提高模型的准确。 请注意,目前仅支持 CPU 量化,因此在本教程中我们将不使用 GPU / CUDA。
本教程说明了如何进行训练后的静态量化,并说明了两种更先进的技术-每通道量化和量化感知训练-可以进一步提高模型的准确。 请注意,目前仅支持 CPU 量化,因此在本教程中我们将不使用 GPU / CUDA。
在本教程结束时,您将看到 PyTorch 中的量化如何导致模型大小显着减小同时提高速度。 此外,您将在此处看到如何轻松应用[中显示的一些高级量化技术,以使您的量化模型受到的准确影响要小得多。](https://arxiv.org/abs/1806.08342)
在本教程结束时,您将看到 PyTorch 中的量化如何导致模型大小显着减小同时提高速度。 此外,您将在此处看到如何轻松应用[中显示的一些高级量化技术,以使您的量化模型受到的准确影响要小得多。](https://arxiv.org/abs/1806.08342)
警告:我们使用了许多其他 PyTorch 仓库中的样板代码,例如,定义了`MobileNetV2`模型架构,定义了数据加载器等等。 我们当然鼓励您阅读它; 但是如果要使用量化功能,请随时跳到“ 4。 训练后静态量化”部分。
......@@ -560,7 +560,7 @@ Size (MB): 3.631847
对于这个量化模型,我们发现在这 300 张相同的图像上,准确率仅低至〜62%。 不过,我们确实将模型的大小减小到了 3.6 MB 以下,几乎减少了 4 倍。
此外,我们可以通过使用不同的量化配置来显着提高准确。 我们使用推荐的配置对 x86 架构进行量化,重复相同的练习。 此配置执行以下操作:
此外,我们可以通过使用不同的量化配置来显着提高准确。 我们使用推荐的配置对 x86 架构进行量化,重复相同的练习。 此配置执行以下操作:
* 量化每个通道的权重
* 使用直方图观察器,该直方图观察器收集激活的直方图,然后以最佳方式选择量化参数。
......@@ -589,11 +589,11 @@ QConfig(activation=functools.partial(<class 'torch.quantization.observer.Histogr
```
仅更改这种量化配置方法,就可以将准确提高到 76% 以上! 尽管如此,这仍比上述 78% 的基准差 1-2%。 因此,让我们尝试量化意识的训练。
仅更改这种量化配置方法,就可以将准确提高到 76% 以上! 尽管如此,这仍比上述 78% 的基准差 1-2%。 因此,让我们尝试量化意识的训练。
## 5.量化意识训练](docs / modern-java-zh /
量化意识训练(QAT)是通常导致最高准确的量化方法。 使用 QAT,在训练的正向和反向过程中,所有权重和激活都被“伪量化”:即,浮点值四舍五入以模拟 int8 值,但所有计算仍使用浮点数完成。 因此,在训练过程中进行所有权重调整,同时“意识到”该模型将最终被量化的事实。 因此,在量化之后,此方法通常会比动态量化或训练后静态量化产生更高的精度。
量化意识训练(QAT)是通常导致最高准确的量化方法。 使用 QAT,在训练的正向和反向过程中,所有权重和激活都被“伪量化”:即,浮点值四舍五入以模拟 int8 值,但所有计算仍使用浮点数完成。 因此,在训练过程中进行所有权重调整,同时“意识到”该模型将最终被量化的事实。 因此,在量化之后,此方法通常会比动态量化或训练后静态量化产生更高的精度。
实际执行 QAT 的总体工作流程与之前非常相似:
......@@ -750,12 +750,12 @@ Training: * Acc@1 63.000 Acc@5 81.333
```
在这里,我们只对少数几个时期执行量化感知训练。 尽管如此,量化意识训练在整个 imagenet 数据集上的准确仍超过 71%,接近浮点精度 71.9%。
在这里,我们只对少数几个时期执行量化感知训练。 尽管如此,量化意识训练在整个 imagenet 数据集上的准确仍超过 71%,接近浮点精度 71.9%。
有关量化意识训练的更多信息:
* QAT 是训练后量化技术的超集,可以进行更多调试。 例如,我们可以分析模型的准确是否受到权重或激活量化的限制。
* 由于我们使用伪量化来对实际量化算术的数值建模,因此我们还可以在浮点中模拟量化模型的准确
* QAT 是训练后量化技术的超集,可以进行更多调试。 例如,我们可以分析模型的准确是否受到权重或激活量化的限制。
* 由于我们使用伪量化来对实际量化算术的数值建模,因此我们还可以在浮点中模拟量化模型的准确
* 我们也可以轻松地模拟训练后量化。
### 量化加速](docs / modern-java-zh /
......
......@@ -355,7 +355,7 @@ plt.tight_layout()
## 第 2 部分。微调可量化模型](docs / modern-java-zh /
在这一部分中,我们将微调用于迁移学习的特征提取器,并对特征提取器进行量化。 请注意,在第 1 部分和第 2 部分中,特征提取器都是量化的。 不同之处在于,在第 1 部分中,我们使用了预训练的量化模型。 在这一部分中,我们将在对感兴趣的数据集进行微调之后创建一个量化的特征提取器,因此这是一种在具有量化优势的同时通过迁移学习获得更好的准确性的方法。 请注意,在我们的特定示例中,训练集非常小(120 张图像),因此微调整个模型的好处并不明显。 但是,此处显示的过程将提高使用较大数据集进行传递学习的准确性
在这一部分中,我们将微调用于迁移学习的特征提取器,并对特征提取器进行量化。 请注意,在第 1 部分和第 2 部分中,特征提取器都是量化的。 不同之处在于,在第 1 部分中,我们使用了预训练的量化模型。 在这一部分中,我们将在对感兴趣的数据集进行微调之后创建一个量化的特征提取器,因此这是一种在具有量化优势的同时通过迁移学习获得更好的准确率的方法。 请注意,在我们的特定示例中,训练集非常小(120 张图像),因此微调整个模型的好处并不明显。 但是,此处显示的过程将提高使用较大数据集进行传递学习的准确率
预训练特征提取器必须是可量化的。 为确保其可量化,请执行以下步骤:
......
......@@ -277,7 +277,7 @@ def run_training_loop(rank, num_gpus, train_loader, test_loader):
```
与传统的本地模型非常相似,下面的内容只是简单地计算了我们训练后模型的准确。 但是,请注意,我们在上面传递给此函数的`net``TrainerNet`的实例,因此,前向传递以透明方式调用 RPC。
与传统的本地模型非常相似,下面的内容只是简单地计算了我们训练后模型的准确。 但是,请注意,我们在上面传递给此函数的`net``TrainerNet`的实例,因此,前向传递以透明方式调用 RPC。
```py
def get_accuracy(test_loader, model):
......
......@@ -65,9 +65,9 @@
当前,该行业主要由前三个部分驱动,但是人工智能的未来取决于第四部分的发展。 沿着机器学习的发展历程,我们可以看到直到现在,这些学习模型都将实数作为输出,例如电影评论(情感评分)和图像分类(类对象)。 但是现在,以及其他类型的输出也正在生成,例如,图像字幕(输入:图像,输出:文本),机器翻译(输入:文本,输出:文本)和语音识别(输入:音频, 输出:文本)。
人类水平的表现是必要的,并且通常应用于深度学习。 在一段时间内收敛到最高点之后,人员水平的准确变得恒定。 这一点称为最佳错误率(也称为贝叶斯错误率,即对于任何随机结果分类器而言,最低的错误率)。
人类水平的表现是必要的,并且通常应用于深度学习。 在一段时间内收敛到最高点之后,人员水平的准确变得恒定。 这一点称为最佳错误率(也称为贝叶斯错误率,即对于任何随机结果分类器而言,最低的错误率)。
其背后的原因是由于数据中的噪声,许多问题在性能上都有理论上的限制。 因此,人员级别的准确是通过进行错误分析来改进模型的好方法。 这是通过合并人为误差,训练集误差和验证集误差来估计偏差方差影响(即欠拟合和过拟合条件)来完成的。
其背后的原因是由于数据中的噪声,许多问题在性能上都有理论上的限制。 因此,人员级别的准确是通过进行错误分析来改进模型的好方法。 这是通过合并人为误差,训练集误差和验证集误差来估计偏差方差影响(即欠拟合和过拟合条件)来完成的。
数据规模,算法类型和性能指标是一组方法,可以帮助我们针对不同的机器学习算法确定改进水平。 因此,决定是否投资深度学习或采用传统机器学习方法的关键决策。
......@@ -81,7 +81,7 @@
* W1,W2 和 W3 是与特征变量关联的相应权重。 当我们谈论神经网络的训练时,我们的意思是说权重的训练。 因此,这些构成了我们小型神经网络的参数。
* 输出层中的功能是应用于从前一层接收的信息的聚合上的激活功能。 此函数创建一个与实际输出相对应的表示状态。 从输入层到输出层的一系列过程导致预测输出,称为正向传播。
* 输出层中的功能是应用于从前一层接收的信息的聚合上的激活函数。 此函数创建一个与实际输出相对应的表示状态。 从输入层到输出层的一系列过程导致预测输出,称为正向传播。
* 通过多次迭代,可以最小化激活函数的输出和实际输出之间的误差值。
......@@ -89,11 +89,11 @@
现在,牢记这些基础知识,让我们进一步使用 Logistic 回归作为神经网络对神经网络进行神秘化,并尝试创建具有一个隐藏层的神经网络。
# 深度学习的激活功能
# 深度学习的激活函数
激活函数是人工神经网络的组成部分。 他们决定特定神经元是否被激活,即神经元接收到的信息是否相关。 激活函数对接收信号(数据)执行非线性变换。
我们将在以下各节中讨论一些流行的激活功能
我们将在以下各节中讨论一些流行的激活函数
# 乙状结肠功能
......@@ -159,7 +159,7 @@ ReLU 函数具有非线性的优势。 因此,反向传播很容易,因此
![](img/a3b9045b-2a4e-4e1f-9414-8b330464d72a.png)
ReLU 功能相对于其他激活功能的主要优势在于,它不会同时激活所有神经元。 这可以从前面的 ReLU 函数图中观察到,在图中我们可以看到,如果输入为负,则输出零,而神经元不会激活。 这导致网络稀疏,并且计算快速简便。
ReLU 功能相对于其他激活函数的主要优势在于,它不会同时激活所有神经元。 这可以从前面的 ReLU 函数图中观察到,在图中我们可以看到,如果输入为负,则输出零,而神经元不会激活。 这导致网络稀疏,并且计算快速简便。
![](img/b6cdb514-2155-4640-a257-7b5a91ad8668.png)
......@@ -173,13 +173,13 @@ ReLU 的导数图,对于 x <=0 and f'(x) = 1 for x> 0 显示 f'(x)= 0
这防止了梯度在负侧变为零,并且由于![](img/f5c373db-725f-4f61-b28b-835eccc7443d.png)的值较低,权重训练持续但缓慢地进行。
# 如何选择正确的激活功能
# 如何选择正确的激活函数
激活功能取决于问题陈述的目的和所关注的属性。 一些推论如下:
激活函数取决于问题陈述的目的和所关注的属性。 一些推论如下:
* Sigmoid 函数在浅层网络和二进制分类器的情况下效果很好。 较深的网络可能会导致梯度消失。
* ReLU 功能是使用最广泛的功能,请尝试使用 Leaky ReLU 以避免神经元死亡的情况。 因此,从 ReLU 开始,如果 ReLU 无法提供良好的结果,则移至另一个激活功能
* ReLU 功能是使用最广泛的功能,请尝试使用 Leaky ReLU 以避免神经元死亡的情况。 因此,从 ReLU 开始,如果 ReLU 无法提供良好的结果,则移至另一个激活函数
* 在外层使用 softmax 进行多类分类。
......@@ -351,9 +351,9 @@ Xavier 初始化是神经网络中权重的初始化,是遵循高斯分布的
以下因素要求应用 xavier 初始化:
* 如果网络中的权重开始很小,则大多数信号将收缩并在随后的层中激活功能处于休眠状态
* 如果网络中的权重开始很小,则大多数信号将收缩并在随后的层中激活函数处于休眠状态
* 如果权重开始很大,则大多数信号将大量增长并通过后面各层的激活功能
* 如果权重开始很大,则大多数信号将大量增长并通过后面各层的激活函数
因此,xavier 初始化有助于产生最佳权重,以使信号在最佳范围内,从而使信号变得既不会太小也不会太大的机会最小。
......@@ -465,7 +465,7 @@ Xavier 初始化是神经网络中权重的初始化,是遵循高斯分布的
* ![](img/2a804f1c-616a-4259-ad96-68538ad3f153.png)和![](img/f08af16f-e2d6-4cc9-8fea-057be7ce996b.png)是随时间共享的权重和偏差。
* ![](img/69bdd200-19d8-4e66-9dbf-0b5c45dfa1bb.png)是激活功能![](img/83763684-e7c3-408a-9d7c-c71e58f2b0f2.png)
* ![](img/69bdd200-19d8-4e66-9dbf-0b5c45dfa1bb.png)是激活函数![](img/83763684-e7c3-408a-9d7c-c71e58f2b0f2.png)
* ![](img/fdae7818-ad9f-4625-a517-9866ab64c7ba.png)指这两个信息的串联。 假设您的输入![](img/fabc1019-14de-464c-9815-31932fc61bd7.png)的形状为![](img/34f9ecdb-a661-464e-827f-d4d3aa3bc4f1.png),即`n`样本/行和 d 尺寸/列,![](img/b826d8a7-d3e8-4bff-bff0-8ee306dfb0fe.png)为![](img/ce5ea938-0957-4fb1-b749-eb5c1dabcd29.png)。 然后,您的串联将得到形状为![](img/98b88230-cb0a-4e47-9196-c1f6a5c25a3b.png)的矩阵。
......@@ -634,7 +634,7 @@ Szegedy 等人从卷积开始深入研究(https://arxiv.org/pdf/1409.4842.pdf
这两个可能的问题可以通过以下方法克服:
* 减少使用 S 型和 tanh 激活功能
* 减少使用 S 型和 tanh 激活函数
* 使用基于动量的随机梯度下降
* 权重和偏差的正确初始化,例如 xavier 初始化
* 正则化(将正则化丢失与数据丢失一起添加并最小化)
......
......@@ -411,7 +411,7 @@ HFFG
input_state = [0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0]
```
通过添加更多隐藏层和不同激活功能的选择,Q 网络绝对比 Q 表具有许多优势。 与 Q 表不同,在 Q 网络中,通过最小化反向传播的损耗来更新 Q 值。 损失函数由下式给出:
通过添加更多隐藏层和不同激活函数的选择,Q 网络绝对比 Q 表具有许多优势。 与 Q 表不同,在 Q 网络中,通过最小化反向传播的损耗来更新 Q 值。 损失函数由下式给出:
![](img/2aa82c3f-b95f-402e-998d-529bfbadff7d.png)
......
......@@ -509,7 +509,7 @@ def __init__(self,learning_rate,gamma,n_features,n_actions,epsilon,parameter_cha
* 这两个参数具有相同的结构,即:
* `w1`:与输入层关联的权重矩阵
* `b1`:与输入层关联的偏置向量
* `ReLU`:信号从输入到隐藏层的激活功能
* `ReLU`:信号从输入到隐藏层的激活函数
* `w2`:与隐藏层关联的权重矩阵
* `b2`:与输入层关联的偏置向量
* 计算主网络输出的 Q 值与目标网络输出的 Q 值之间的损耗
......@@ -1047,7 +1047,7 @@ def conv(self,inputs,w):
* 卷积层 2
* 全连接第 1 层
* 全连接第 2 层
* 使用的激活功能:ReLU
* 使用的激活函数:ReLU
该功能还有助于:
......
......@@ -52,7 +52,7 @@ Brett Sperry 首先使用术语**实时策略**(**RTS**)作为宣传其游
基于案例的推理
在检索步骤中,从案例库中选择与问题相关的案例子集。 在重用步骤中,将根据所选情况调整解决方案。 然后,在修订步骤中,通过在实际环境中进行测试来验证适应的解决方案,并观察到量化预测解决方案准确的反馈。 保留步骤决定是否将此新解决的案例存储在案例库中。 因此,基于案例的推理和计划涉及重用以前的计划,并使它们适应新情况。
在检索步骤中,从案例库中选择与问题相关的案例子集。 在重用步骤中,将根据所选情况调整解决方案。 然后,在修订步骤中,通过在实际环境中进行测试来验证适应的解决方案,并观察到量化预测解决方案准确的反馈。 保留步骤决定是否将此新解决的案例存储在案例库中。 因此,基于案例的推理和计划涉及重用以前的计划,并使它们适应新情况。
基于案例的推理主要应用于静态域,也就是说,代理有时间决定要采取的操作,与此同时,环境的状态也不会改变。 但是现实世界中的问题是动态的,并且有时间限制。 因此,基于案例的推理不适合实际的策略游戏,这导致**在线基于案例的计划**,其中与基于案例的推理不同,实时进行计划和执行。 下图给出了基于案例的在线计划的架构:
......
......@@ -85,7 +85,7 @@
* **规划**是整个过程中最难的部分。 该任务包括将识别和预测的结果集成在一起,以计划将来的动作序列以及下一个驾驶动作集(向左或向右转向,加速等等),以使导航安全且成功。 这是一项艰巨的任务,因为整合和规划需要处理不可避免的情况才能安全到达目的地。 强化学习最适合此类控制计划任务。 我们已经了解了如何成功地部署强化学习来控制 50 场 Atari 游戏中的计划任务,以及 Google DeepMind 提供的最先进的 AlphaGo Zero。 在这些情况下,我们目睹了深度学习在进行表示学习的同时进行强化学习的规划。
由于使用了多种类型的传感器,所有这些信息的集成对于自动驾驶至关重要。 由于数据维数的差异,很难整合来自不同来源的感官输入。 例如,摄像机输入为高维,而 LIDAR 输入为低维。 提取相关信息并忽略不相关信息无疑会提高性能和准确。 它降低了计算和存储能力的利用率。 因此,为了获取相关信息,注意模型适用于此目的,因为使用注意力机制的循环神经网络强化学习已成功应用于图像,从而仅关注相关部分。
由于使用了多种类型的传感器,所有这些信息的集成对于自动驾驶至关重要。 由于数据维数的差异,很难整合来自不同来源的感官输入。 例如,摄像机输入为高维,而 LIDAR 输入为低维。 提取相关信息并忽略不相关信息无疑会提高性能和准确。 它降低了计算和存储能力的利用率。 因此,为了获取相关信息,注意模型适用于此目的,因为使用注意力机制的循环神经网络强化学习已成功应用于图像,从而仅关注相关部分。
# 为什么要加强学习?
......
......@@ -59,7 +59,7 @@
当前,存在用于金融市场交易的深度学习方法,这些方法可以预测价格走势和趋势,但不能在不同的金融产品之间执行自动的资金分配和重新分配。 由于我们拥有所有资产的历史价格,因此我们可以将包含它们的输入数据准备到循环神经网络中,该网络将预测下一时期的资产价格作为输出。 这是机器学习中的监督回归问题。
这些模型的性能完全取决于未来资产价格的预测准确,而不仅是在下一个时期。 但是,未来的市场价格极难预测,因为它们不仅取决于历史价格,而且只能反映波动和流动,不包括也会驱动金融市场的情绪因素。
这些模型的性能完全取决于未来资产价格的预测准确,而不仅是在下一个时期。 但是,未来的市场价格极难预测,因为它们不仅取决于历史价格,而且只能反映波动和流动,不包括也会驱动金融市场的情绪因素。
需要注意的另一个重要点是,预测市场价格并不意味着预测市场行为。 因此,需要领域知识和逻辑将预测价格转换为行动。 结合深度强化学习,可根据最大化回报的目标使此逻辑转换自动化。
......
......@@ -137,7 +137,7 @@ Perkins 和 Barto(2002)提出了一种基于 Lyapunov 函数构造强化学
* 强化学习算法的成功很大程度上取决于奖励函数的质量,其对不同状态表示的覆盖范围以及与之相关的不确定性
* 先验领域知识的重要性是什么?
* 先验知识对于加强学习代理的准确更好。
* 先验知识对于加强学习代理的准确更好。
* 在尽可能少的情节中更好地学习所需的先验知识量尚不确定,并且尚待解决。 因此,重复大量的迭代以确保更好的学习。
* 在某些情况下,由于与环境相关的大量不确定性,先验知识可能无济于事。
* 我们如何根据感知数据仔细学习?
......
......@@ -28,7 +28,7 @@
# 基于区域的卷积神经网络
在较早的对象分类模型中,CNN 非常慢且计算量很大。 此外,作为分类问题的成功完全取决于准确。 通过在每层的所有区域上滑动窗口来完成 CNN 中的运行卷积。 因此,更多的边界框(通过滑动窗口分析的不同区域的总数)意味着更高的计算成本。
在较早的对象分类模型中,CNN 非常慢且计算量很大。 此外,作为分类问题的成功完全取决于准确。 通过在每层的所有区域上滑动窗口来完成 CNN 中的运行卷积。 因此,更多的边界框(通过滑动窗口分析的不同区域的总数)意味着更高的计算成本。
**基于区域的卷积神经网络****R-CNN**)是首次采用选择性搜索方法来减少输入分类器的边界框的数量。 此外,选择性搜索使用纹理,强度,颜色等特征来创建对象的可能盒子位置。 现在,这些盒子可以送入 CNN 模型。
......@@ -64,7 +64,7 @@ Ross Girshick 的 [Fast R-CNN](https://arxiv.org/pdf/1504.08083.pdf)
快速 R-CNN 解决了与 SPP 网络相关的关键问题; 由于空间池化层未进行微调,因此,快速 R-CNN 提供了端到端的学习网络。 快速 R-CNN 使用类似于最大池梯度计算的简单反向传播,但池区域重叠。
此外,与 R-CNN 不同,Fast R-CNN 结合了边界框回归和神经网络训练,而 R-CNN 则使用边界框回归单独进行此区域优化,这有助于更好地定位。 因此,在快速 R-CNN 中,分类和定位不需要单独的网络。 结果,相对于之前开发的任何其他对象检测模型,总的训练时间显着减少,并且由于端到端学习,与 SPP 网络相比,其准确更高。
此外,与 R-CNN 不同,Fast R-CNN 结合了边界框回归和神经网络训练,而 R-CNN 则使用边界框回归单独进行此区域优化,这有助于更好地定位。 因此,在快速 R-CNN 中,分类和定位不需要单独的网络。 结果,相对于之前开发的任何其他对象检测模型,总的训练时间显着减少,并且由于端到端学习,与 SPP 网络相比,其准确更高。
# 更快的 R-CNN
......@@ -81,7 +81,7 @@ Ross Girshick 的 [Fast R-CNN](https://arxiv.org/pdf/1504.08083.pdf)
# 你只看一次
YOLO 通过执行回归学习类概率和边界框的大小,从而对输入图像执行对象检测。 YOLO 将图像划分为 *SxS* 网格,每个网格预测`N`边界框和置信度。 该置信度值量化边界框的准确和对象在边界框中的出现。
YOLO 通过执行回归学习类概率和边界框的大小,从而对输入图像执行对象检测。 YOLO 将图像划分为 *SxS* 网格,每个网格预测`N`边界框和置信度。 该置信度值量化边界框的准确和对象在边界框中的出现。
YOLO 还可以预测训练中所有班级每个盒子的班级得分。 因此,图像中所有框上的类别得分的总和也有助于计算整个图像的类别概率,从而有助于预测对象。 由于将图像划分为 *SxS* 网格,并且针对每个输出 *N 个*边界框,因此,正在预测 *SxSxN* 框。 但是,由于我们具有盒子的置信度得分并使用显着的阈值,因此可以删除所有低置信度(不包含对象)的盒子。
......@@ -89,7 +89,7 @@ YOLO 还可以预测训练中所有班级每个盒子的班级得分。 因此
# 单发探测器
**单发检测器****SSD**)以其在速度和准确之间的平衡而著称。 就像 YOLO 一样,SSD 仅在输入图像上运行一次 CNN 即可学习表示形式。 在此表示形式上运行一个小的 3x3 卷积核,以预测边界框和类概率。 为了处理比例,SSD 会在多个卷积层之后预测边界框。 由于每个卷积层以不同的比例运行,因此它能够检测各种比例的对象。
**单发检测器****SSD**)以其在速度和准确之间的平衡而著称。 就像 YOLO 一样,SSD 仅在输入图像上运行一次 CNN 即可学习表示形式。 在此表示形式上运行一个小的 3x3 卷积核,以预测边界框和类概率。 为了处理比例,SSD 会在多个卷积层之后预测边界框。 由于每个卷积层以不同的比例运行,因此它能够检测各种比例的对象。
下图显示了 Fast R-CNN,Faster R-CNN,YOLO 和 SSD 的性能指标:
......@@ -153,7 +153,7 @@ YOLO 还可以预测训练中所有班级每个盒子的班级得分。 因此
对于 Image-Zooms 模型,每个区域的大小调整为 224x224,并通过 Pool5 层馈入 VGG-16,以获得特征图。 对于 Pool45-Crops 模型,全分辨率的图像通过 Pool5 层输入到 VGG-16。 合并从整个图像中提取的所有**感兴趣区域****ROI**)的特征图。
这两个用于特征提取的模型输出 *7x7* 的特征图,该图被馈送到公共块中(如以下架构所示)。 这些特征图和存储向量(前面讨论过)被馈入由两个全连接层组成的深层 Q 网络,每个层各有 1024 个神经元。 每个全连接层都具有 ReLU 激活功能,并经过辍学训练:
这两个用于特征提取的模型输出 *7x7* 的特征图,该图被馈送到公共块中(如以下架构所示)。 这些特征图和存储向量(前面讨论过)被馈入由两个全连接层组成的深层 Q 网络,每个层各有 1024 个神经元。 每个全连接层都具有 ReLU 激活函数,并经过辍学训练:
![](img/c804ff2f-7264-4eac-99a1-8aeb5a3fd5a7.png)
......
......@@ -48,7 +48,7 @@ TRPO 由 Schulman 等(2017)发布在名为[《信任区域策略优化》](h
* *猫在垫子上*
* *垫子上有只猫*
如果目标只是一个正确的答案,那么准确度的测量很容易,但是如果存在多个同样正确的可能性,那么在这种情况下如何测量准确度? 在本节中,我们将研究 BLEU 分数,BLEU 分数是一种评估指标,用于在出现多个同等正确答案的情况下,测量准确
如果目标只是一个正确的答案,那么准确度的测量很容易,但是如果存在多个同样正确的可能性,那么在这种情况下如何测量准确度? 在本节中,我们将研究 BLEU 分数,BLEU 分数是一种评估指标,用于在出现多个同等正确答案的情况下,测量准确
# 什么是 BLEU 分数,它的作用是什么?
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册