TowardsDataScience 博客中文翻译 2016~2018(一百八十)

原文:TowardsDataScience Blog

协议:CC BY-NC-SA 4.0

学习计算机视觉

原文:https://towardsdatascience.com/learning-computer-vision-41398ad9941f?source=collection_archive---------5-----------------------

最近我读了很多关于计算机视觉的书并做了很多实验,这里介绍了在这个领域中学习和使用什么是有趣的。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Image segmentation for autonomous driving

近年来,计算机视觉取得了很大进步。这些是我将在此提及的主题:

技术:

  • 人脸检测:Haar,HOG,MTCNN,Mobilenet
  • 人脸识别:CNN,Facenet
  • 物体识别:alexnet,inceptionnet,resnet
  • 迁移学习:在一个新的主题上用很少的资源重新训练大的神经网络
  • 图像分割:rcnn
  • 开始
  • 计算机视觉硬件:选什么,GPU 重要
  • 集成视觉的 UI 应用程序:ownphotos

应用:

  • 个人照片组织
  • 自动驾驶汽车
  • 自主无人机
  • 求解验证码/ OCR
  • 为基于图片的网站/应用程序过滤图片
  • 为应用程序自动标记图片
  • 从视频(电视节目、电影)中提取信息
  • 视觉问答
  • 艺术

关注的人:

课程:

  • 深度学习@ coursera
  • 机器学习@ coursera

相关字段:

  • 深度强化学习:参见以 cnn 为输入层的 ppo 和 dqn
  • 与 nlp 的互动:lstm 2 cnn

人脸检测

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Face detection is about placing boxes around faces

人脸检测就是检测人脸的任务。有几种算法可以做到这一点。

【https://github.com/nodefluxio/face-detector-benchmark】提供了这些方法的速度基准,并带有易于重用的实现代码。

哈尔分类器

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

haar features

它们是自 2000 年以来出现在 opencv 中的旧的计算机视觉方法。本文介绍了http://wearables . cc . gatech . edu/paper _ of _ week/viola 01 rapid . pdf

它是一个机器学习模型,具有专门为对象检测选择的特征。Haar 分类器速度快,但准确率低。

https://docs . opencv . org/3 . 4 . 3/D7/d8b/tutorial _ py _ face _ detection . html中查看更长的解释和如何使用它的示例

HOG:方向梯度直方图

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Histogram of oriented gradients

HOG 是一种较新的生成目标检测特征的方法:从 2005 年开始使用。它是基于计算图像像素的梯度。这些特征然后被馈送到机器学习算法,例如 SVM。它比 haar 分类器有更好的精度。

它的一个实现在 dlib 中。它在人脸识别(https://github.com/ageitgey/face_recognition)库中。

MTCNN

一种利用细胞神经网络变异检测图像的新方法。精度更高,但速度稍慢。参见https://KP Zhang 93 . github . io/mt CNN _ face _ detection _ alignment/index . html

MobileNet

目前最好最快的人脸检测方法。基于通用移动网络架构。参见 https://arxiv.org/abs/1704.04861 的

目标检测

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Object detection on many kind of objects

可以使用类似于面部检测的方法来实现对象检测。

这里有两篇文章介绍了实现这一目标的最新方法。这些方法有时甚至还提供对象的类别(实现对象识别) :

卷积神经网络

深度学习的最新进展已经看到新的架构取得了很大的成功。

使用许多卷积层的神经网络就是其中之一。卷积层利用图像的 2D 结构在神经网络的下一层中生成有用的信息。关于什么是卷积的详细解释,请参见https://towards data science . com/intuitive-understanding-convolutions-for-deep-learning-1 F6 f 42 faee 1

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

A convolution layer

物体识别

物体识别是将物体分类的一般问题(如猫、狗等)

基于卷积深度神经网络已经被用于在这个任务上获得很好的结果。

ILSVR 大会已经在 ImageNet(http://www.image-net.org/上举办了比赛,ImageNet 是一个数据库,里面有许多带有诸如猫、狗、…)

越成功的神经网络已经使用越来越多的层。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

ResNet 架构是迄今为止最好的对象分类架构。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Resnet architecture

要对它进行适当的训练,需要使用数百万张图像,即使使用几十块昂贵的 GPU 也要花费大量时间。

这就是为什么在如此大的数据集上不需要每次都重新训练的方法非常有用的原因。迁移学习和嵌入就是这样的方法。

resnet 的预训练模型在https://github . com/tensor flow/tensor 2 tensor # image-class ification中提供

人脸识别

人脸识别就是要弄清楚谁是 T2,谁是 T3。

历史方法

解决该任务的传统方法是应用标准机器学习(例如 svm)的特征工程,或者应用深度学习方法进行对象识别。

这些方法的问题是它们需要每个人的大量数据。实际上,这些数据并不总是可用的。

Facenet

谷歌研究人员于 2015 年在 https://arxiv.org/abs/1503.03832推出了 Facenet。提出了一种不需要为每个人准备大量人脸样本的人脸识别方法。

它的工作方式是通过拍摄大量人脸的照片数据集(比如 http://vis-www.cs.umass.edu/lfw/的照片)。

然后采用现有的计算机视觉架构,如 inception(或 resnet ),然后用计算人脸嵌入的层来替换对象识别 NN 的最后一层。

对于数据集中的每个人,(阴性样本、阳性样本、第二个阳性样本)选择(使用试探法)三个一组的面部,并馈送给神经网络。这产生了 3 个嵌入。在这 3 个嵌入中,计算三元组损失,这最小化正样本和任何其它正样本之间的距离,并且最大化位置样本和任何其它负样本之间的距离。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Triplet loss

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

最终结果是,每个人脸(甚至是不存在于原始训练集中的人脸)现在都可以被表示为一个嵌入(128 个数的向量),它与其他人的人脸的嵌入有很大的距离。

然后,这些嵌入可以用于任何机器学习模型(即使是像 knn 这样简单的模型)来识别人。

关于 facenet 和 face embeddings 非常有趣的一点是,使用它,你可以只通过一些人的照片,甚至是一张照片来识别他们。

查看实现它的库:https://github.com/ageitgey/face_recognition

这是它的张量流实现:https://github.com/davidsandberg/facenet

这是人脸识别管道背后的想法的一个很酷的应用,而不是识别熊的脸:https://hypractive . github . io/2017/01/21/face net-for-bears . html

迁移学习

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Retrain quickly an accurate neural network on a custom dataset

训练像 resnet 这样的非常深度的神经网络是非常耗费资源的,需要大量的数据。

计算机视觉是高度计算密集型的(在多个 gpu 上进行数周的训练),需要大量数据。为了解决这个问题,我们已经讨论过计算人脸的一般嵌入。另一种方法是利用现有网络,在另一个数据集上只重新训练它的几个 it 层。

下面是它的教程: codelab 教程。它建议你重新训练一个初始模型来训练未知的花类。

https://medium . com/@ 14 Prakash/transfer-learning-using-keras-d 804 b 2e 04 ef 8提出了在进行迁移学习时,应该重新训练哪一层的良好指南。

图象分割法

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Image segmentation for autonomous driving

图像分割是一个令人印象深刻的新任务,近年来已经成为可能。它包括识别图像的每个像素。

该任务与目标检测相关。实现它的一种算法是 mask r-cnn,更多详情参见本文https://medium . com/@ Jonathan _ hui/image-segmentation-with-mask-r-CNN-ebe6d 793272

开始

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Large scale GAN

由 ian goodfellow 介绍的生成式广告网络是一个由两部分组成的神经网络体系结构:一个鉴别器和一个生成器。

  • 鉴别器检测一张图片是否是一个类,它通常已经在一个对象分类数据集上进行过预训练。
  • 生成器为给定的类生成图像

生成器的权重在学习期间被调整,以便产生鉴别器不能从该类的真实图像中区分的图像。

这是迄今为止最大的氮化镓制作的图像的例子https://arxiv.org/abs/1809.11096

参见https://github.com/eriklindernoren/Keras-GAN的 keras 中 GAN 的实现

计算机视觉硬件

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

训练大模型,需要大量的资源。有两种方法可以实现这一点。首先是使用云服务,比如 google cloud 或者 aws。第二种方式是自己搭建一台带 GPU 的电脑。

只要 1000 美元,就有可能建造一台像样的机器来训练深度学习模型。

https://hypractive . github . io/2017/02/13/dl-computer-build . html中阅读更多详细信息

UI 中的视觉

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Face dashboard of ownphotos

Ownphotos 是一个令人惊叹的用户界面,允许你导入照片,自动计算人脸嵌入,进行物体识别和人脸识别。

它使用:

应用程序

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Visual question answering

计算机视觉有许多应用:

  • 个人照片组织
  • 自动驾驶汽车
  • 自主无人机
  • 求解验证码/ OCR
  • 为基于图片的网站/应用程序过滤图片
  • 为应用程序自动标记图片
  • 从视频(电视节目、电影)中提取信息
  • 视觉问答:结合自然语言处理和计算机视觉
  • 艺术:甘

结论

正如我们在这里看到的,有许多新的有趣的方法和应用的成功。

我认为人工智能中最有趣的是学习可以重复使用的算法,能够将这些方法应用到越来越多的任务中,而不需要太多的处理能力和数据:

  • 迁移学习:它使得重新利用预先训练好的大型神经网络成为可能
  • 嵌入(例如 facenet):无需对这些类进行训练就可以识别许多类

在通用数据集上学习数据科学是没有用的

原文:https://towardsdatascience.com/learning-data-science-on-generic-datasets-is-useless-163e9015041c?source=collection_archive---------26-----------------------

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

好吧,这绝对不是没用的。但它的用处远远超过了实际需要。本文将概述数据在学习数据科学中扮演的一些潜在角色,并反对使用通用(以及静态数据集)数据集。我们经常看到在可用的通用数据集上教授机器学习主题,如 mtcarsiris 。让我澄清一下,我们使用这些数据集是因为它们经过了惊人的清理、准备和强健,可以用来教授数据科学中的各种概念。不是每个人都有大量的数据…或者他们有吗?或许现在时机已经成熟,可以自动管理学习者自己的网上数据,帮助他们回答关于自己的问题,同时学习数据科学。随着我们继续发展数据科学教育,我建议我们转向使用可变和个人数据集进行学习。我的目标是将数据科学教育转变为一项技能培养活动,而不是自我探索和发现活动。其中一个想法围绕着使用已经可用的相关数据(你自己的!),另一个更深层次的观点直指数据甚至在学习过程中扮演的角色。本文将探讨一下为什么数据很重要

我们学数据科学不是无缘无故的。

最近我一直在纠结为什么我们应该学习数据科学。有时,冲进资本主义的监狱似乎是一种耸人听闻的恐慌。“T16 要是你有数据科学技能就好了!”“这架飞机上有机器学习的博士吗?!"这肯定是另一篇博文,但现在我将继续宣扬学习数据科学是自我发现的一种形式,如果培养得当,可以带来巨大的快乐。所以,让我们假设你正在学习成为一名数据科学家,不管是出于什么原因。当您真正处理数据时:

  • 你通常有一个实际的问题要解决,甚至可能有一个特定的结果。
  • 您将数据与您所拥有领域知识联系起来;无论是体育、医药、利润、游戏等等。
  • 你对正在处理的数据有预测和直觉。有时候这可以让你指出自己犯的错误(心率 9000?那不可能是对的!)。其他时候,你被你的直觉所迷惑,试图寻找根本不存在的意义。

处理数据的所有这些方面都与您拥有的数据密切相关。某些问题需要某些测试,这些测试需要某些数据配置。这些数据与你对自己领域的了解密切相关,通常用于支持对该领域真理的追求。你的直觉很重要!每次我们将经验 转化为数据,我们都在做决策。** 我一直在用下面的例子来说明这一点:在测量美国的平均身高时,我们会把婴儿包括在内吗?我们如何定义我们处理的数据很重要,对使用什么数据有某种直觉也很重要。我不知道你,但是我对植物学和萼片长度完全没有直觉。

算法是一个过程,数据改变了这个过程。

  • 理解机器学习算法的部分核心是理解*数据驱动的过程。*这意味着您的流程与输入到系统中的数据密切相关。我并不是说算法会根据它拥有的数据从根本上改变它的步骤,而是说这个过程对于每个数据场景(算法在其中移动的空间)来说看起来是不同的。
  • 观察数据量很少或非常多的模型会发生什么,可以让您了解算法实际上是如何工作的。想想下面这个例子:你得知一只狗的名字是 Sparky,但却意外地假设这只狗的名字实际上是 Barky(一个错误,但是一个聪明的错误)。有一次你听到有人叫这只狗“斯巴基”,也许会认为他们搞错了,因为这只狗的名字真的叫巴克利。现在想象一下,你听到每个人都称这只狗为“Sparky”超过 1000 次。也许是你认识到自己错误的时候了!这是一个数据量如何改变结果甚至过程的例子。算法也是如此。能够处理我们看到的大量数据对于学习算法如何运行非常重要。
  • 如果我们的数据没有边缘情况,我们如何考虑它们?我们拥有的数据允许我们对涉及的算法的某些部分进行推理。如果您的数据不需要担心局部最小值,那么了解全局最小值可能就没有什么启发性了。我们掌握的数据实际上决定了我们可以探索的案例。我并不是说我们可以自动筛选出包含完美边缘案例的完美数据集,也可能是当前通用数据集包含边缘案例的情况。但我要说的是,这是我们必须承认的数据所扮演的重要角色。

您选择的数据和模型是一种委托关系。

数据不仅改变了算法过程,还决定了适合使用哪种算法。这并不是说你应该仅仅因为数据允许就使用一种算法。但是需要注意的是,数据的作用是限制你实际使用的算法。用于教授某些概念的通用数据集当然有合适的数据来解决手头的问题,但如果您的问题发生了变化(在处理真实数据时经常发生这种情况),该怎么办呢?我们能让我们的数据集自动适应我们提出的问题吗?除了拥有关于数据本身的领域知识,我建议我们需要更多自动适应的数据集,帮助我们学习帮助我们回答问题的概念。我知道,有点拗口。我们选择的数据和模型有着深厚的关系,这种关系不是一刀切的。我们用来学习数据科学的数据需要像数据和我们选择的模型之间的关系一样具有适应性、错综复杂、杂乱和微妙。

学习数据科学—第 1 部分:MOOC、Youtube、Ted

原文:https://towardsdatascience.com/learning-data-science-part-1-mooc-youtube-ted-20617dbb7f4b?source=collection_archive---------5-----------------------

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Photo by Clint Patterson on Unsplash

我最近开始学习数据科学,大约两个月前。我没有统计学、数学、数据科学、工程学、经济学或任何类似的学位。说实话,学生时代数学和统计学不是我的强项。我更擅长语言。说有些人语言能力强于数学能力可能是一个神话,反之亦然,但这就是我的感受。

我在文学院学的是管理,在文学院学的是策展。我写了我的论文,但它更侧重于文献综述,而不是应用定量研究方法。我在时尚界做过跟单员和采购员。所以在我的整个教育和经历中,我对数学和统计并不是那么了解。

那我为什么还要学习数据科学呢?我对“从数据中获得洞察力”的概念很感兴趣。如此感兴趣,以至于我甚至决定克服我对数学和统计的长期恐惧。考虑到我们仅用两天(到目前为止甚至可能需要 10 分钟)就创建了与 2003 年相同数量的数据,而只有 1%的数据被分析,这个领域充满了各种可能性。“我需要成为它的一部分”,这就是我当时的想法,并且仍然相信它。

MOOC (Coursera 课程)

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Coursera founders Andrew Ng and Daphne Koller

微积分一(我在数学课上没怎么注意,我确实需要复习。)
基础统计学(我听说过一两次,但不能说我什么都知道)
机器学习(这是吴恩达的著名课程,但在第 6 周左右,我意识到我真的需要更多关于编程、数学、统计的基础知识,所以我把它搁置了)
Python 适合所有人(这是一个强烈推荐的专业(5 门课程),如果你和我一样,来自非技术背景

Youtube 频道

有不同的类别,你可能会发现有用的。

第一种是“教程”型。
机器学习

  • Siraj Raval (众说纷纭,但我仍然认为这是一道不错的开胃菜)
  • Harrison Kinsley (也可能是褒贬不一)
    总的来说,它们对于起步来说是不错的,但我觉得这类 Youtube 教程可能在他们如何解决问题、如何处理问题上有点偏见。
  • 韦尔奇实验室(他们有很好的教程关于“学习看”、“神经网络揭秘”。教程是针对初学者的,所以我发现这些视频对掌握概念的基本原理非常有帮助。即使他们没有很多可用的视频,也绝对值得一去)

统计

数学

  • mathbff (当你遇到不熟悉的数学术语,或者记不住的数学规则时,这是一个很好的来源。三角测量法、导数、链式法则等…)

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

I find her videos strangely therapeutic

巨蟒巨蟒
巨蟒查克为大家遣散巨蟒

第二种是“会议”型。对于初学者来说,有些材料可能不容易消化,但看看即将出现的东西、最近的发展以及数据科学中的主题也无妨。

第三个是数据科学学校/训练营自己的 Youtube 频道

最后是 Ted 演讲。我太喜欢 Ted 演讲了。所以我把它和普通的会议类型分开。
各种主题的伟大演讲者,我总能发现新的东西,认识到我不知道的东西,受到鼓舞,受到激励,这让我想成为一个更好的人。它可能不会教你如何构建一个算法,但它可以告诉你为什么和为了什么。
顺便说一下,Ted Talks 有两个不同的名字。“TED Talks”和“Tedx Talks”。我谷歌了一下才知道区别。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Ted’s programs and initiatives

TED 和 TEDx 活动的不同之处在于,前者更多地采用全球化的方式,而后者通常专注于关注本地声音的本地社区。“官方上,TEDx 中的‘x’代表独立组织的 TED 活动——但它更多的是一个 TED 倍增。是这股力量带着 TED 穿越了这个星球,播种了所有这些社区。

如果你在 Youtube 上搜索“ted”,你会得到的第一个条目是“TED Talks”Youtube 页面。 https://www.youtube.com/user/TEDtalksDirector
拥有 790 万订阅用户,2488 个视频(01/10/2017)
在搜索结果的第 17 个条目上,有“TEDx Talks”页面。
https://www.youtube.com/user/TEDxTalks
拥有 890 万用户和 99031 个视频(2017 年 1 月 10 日)

无论如何,下面是一些我非常喜欢的演讲。

我计划更新这个列表,因为我找到了更多有用的资源。我希望它能对任何一个和我处境相似的人有所帮助。对于第 2 部分,我将列出播客和博客作为学习数据科学的来源。

学习数据科学—第 2 部分:播客、博客

原文:https://towardsdatascience.com/learning-data-science-part-2-podcasts-blogs-8bed327eb1b5?source=collection_archive---------7-----------------------

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Photo by fabio on Unsplash

这是“学习数据科学”的第二部分,是我在尝试沉浸于数据科学时收集的链接和资源。我开始这样做是为了跟踪所有我觉得有用的学习资源,但如果它也能对任何人有所帮助,那就是“一举两得”。在第一部分“学习数据科学——第一部分:MOOC、Youtube、Ted ”中,我列出了大部分视频资源。尽管视觉辅助工具在学习时很有帮助,但我想有效地利用我的通勤时间,我经常在地铁里收不到信号,或者流式视频对我的移动数据使用来说有点太重。

播客

partial Derivative 的 Chris Albon 在 Metis 举办的现场演讲中总结了听播客如何帮助你,“揭开数据科学的神秘面纱”(现场演讲于 2017 年 9 月 27 日举行,但你仍然可以通过在他们的网站上注册来获得录音。我不确定是否会有录音,所以我在英国时间下午 3 点到凌晨 3 点看了 12 个小时的演讲…)。播客是关于“让你的大脑一遍又一遍地听到这些术语”。当然,30 分钟的播客不会让你成为专家,但你会听到实际的数据科学家如何谈论一个主题,他们如何将其应用于实际问题。在播客的一集之后,你会比以前更好地了解这个话题。

  • 数据怀疑论者(特别喜欢迷你剧集,主持人 Kyle Polich 向联合主持人 Linh Da 非常直观地解释了各种数据科学概念,没有数学或计算)
  • 偏导数(很难过看到 2017 年 9 月 5 日最后一集之后就停了。听着听着,我感觉就像在听数据科学家们在酒吧里就该领域最近的话题聊天。我在非常有趣和轻松的方式中学习如何在各种情况下应用特定的 ML 算法,有什么限制。再次,悲伤地看到它停止了)

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

The hosts of Partially Derivative: from left, Jonathon Morgan, Vidya Spandana, Chris Albon

  • 线性题外话(两位主持人之间的对话,凯蒂·马龙是数据科学家,本·贾菲是 UI 工程师。很好地结合了对数据科学的不同观点,如果您是精通技术的数据科学家新手,即使没有某个主题的专业知识,您也可以关注他们的谈话)
  • 学习机器 101 (这是一个非常有教育意义的播客,专注于机器学习,如果你感兴趣,我建议你从第一集开始听,因为它建立了你对该领域历史发展和理论的基本理解)
  • 统计+故事(这更像是一个统计和新闻播客。考虑到许多数据科学概念来自统计学,学习如何像统计学家一样思考是非常有用的)
  • 或多或少 (BBC 关于我们身边的数字和统计的播客。同样,我不是专门研究数据科学的,但看到统计数据和我们日常生活之间的联系非常有帮助。凭借一点自己的创造力,您可能会为您的数据科学项目找到一个好主题)

博客

有这么多好的博客,要跟上你感兴趣的每一个博客并不容易。这就是 RSS feeder 派上用场的地方。我最近发现了 Feedly ,它让我不用翻找书签,也不用查看是否有博客更新。您只需复制并粘贴博客地址,然后点击“关注”。然后你可以去 Feedly 查看你关注的所有博客的更新。(我是免费会员,我可以添加的来源仅限于 100 个)

出版商的博客

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

the O’Reilly tarsier

组织的博客

  • 脸书研究博客(他们有关于数据科学的博客,你可以访问各种主题的研究论文;自然语言处理,计算机视觉等。)
  • AWS AI 博客(作为新手,我还没机会用 AWS 跑模型。供我个人以后参考)
  • Tableau 博客(还是那句话,我没用过 Tableau,但是很感兴趣)
  • 彭博——图形(数据可视化非常酷的经济新闻故事。有时他们会分享方法,并展示他们是如何得出这些指标的)
  • GDS 博客(英国政府数字服务的数据博客)的数据。了解政府如何组织和使用数据的良好来源)

数据社区/门户

  • fivethirtyeeight(美国著名统计学家内特·西尔弗的网站。擅长政治和体育。有时他们在 Github 页面中有用于分析的数据集。)

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Fiverthirtyeight styled graph is very famous, there’s even a style sheet replicating this style in Matplotlib

  • 分析 Vidhya (专注于数据科学的业务分析方面。可以找到教程、技巧和窍门。关于各种数据科学应用的分步教程非常有用)
  • 数据经济(本网站更关注数据科学的总体环境,将数据放在上下文中,而不是特定主题的教程)
  • KDnuggets (著名的数据门户网站,涵盖广泛的话题。新闻、教程等)
  • Dataquest 博客(这来自一个在线数据科学课程。擅长教程类型的文章。)

个人

  • Jer Thorp: blprnt.blg (数据艺术家,我在之前的帖子里已经介绍过了。最先进的数据可视化)

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

A map of hotels in Western Europe, showing the density in capital cities like Paris, London, Madrid and Rome (Image courtesy Jer Thorp; flickr.com/photos/blprnt/)

  • 数据科学 101 (“揭开数据科学的神秘面纱”的演讲者之一,Ryan Swanstrom。关于如何学习数据科学的良好资源)
  • 兰德尔·s·奥尔森博士(我第一次知道他是在他写的一篇 538 年的文章中。在他的个人博客中,他分享了数据科学的思维过程,以及他如何将数据科学应用于现实生活中的问题)

个人兴趣(时尚和零售领域的数据科学)

我很快就要在伦敦大会上开始一个新兵训练营课程,我想我会很忙来跟上所有的课程工作和项目,但如果可能的话,我会试着分享我的学习之旅。

学习奖励分配导致 RL 的艺术状态

原文:https://towardsdatascience.com/learning-distributions-over-rewards-leads-to-state-of-the-art-in-rl-5afbf70672e?source=collection_archive---------11-----------------------

最近在 DeepMind 中完成的工作“强化学习的分布式视角”展示了许多 Atari 游戏中具有特殊技巧的最新成果。他们训练了一个神经网络来提供可能的奖励分布,而不是单一的价值。

基本上这是一个很好的老深度 Q 网络。但是,它并没有逼近预期的未来回报值,而是生成了可能结果的整体分布。这种变化背后的主要动机是分布可能有几个峰值。仅仅将它们平均为一个期望值可能是不合适的,并导致不充分的结果。

他们用代表不同奖励值范围的分类变量的概率代替了 DQN 的输出。他们测试了不同数量的区间,分割了可能的值范围:5、11、21、51 和 51 个区间的表现远远优于其他区间。超出此范围的值被剪切到最后一个容器中。对学习算法进行了第二次修改,以处理分布贝尔曼方程。

与普通 DQN 相比,TensorFlow 实施所需的计算时间增加了约 25 %,但只需要一小部分训练步骤就可以实现卓越的性能。与 DQN 相比,在没有其他现代 RL 技术的情况下,这种方法几乎将具有超人性能的游戏数量增加了一倍:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

您可以在原始论文中找到所有的数学和实现细节。虽然研究人员使用 DQN 作为基础,但更先进的模型可能会提供更好的性能。

它看起来像什么

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

行动中:

最初发表于 认知混乱

学习工程:融合科学和数据设计强大的学习体验

原文:https://towardsdatascience.com/learning-engineering-merging-science-and-data-to-design-powerful-learning-experiences-e3c5ddb477f5?source=collection_archive---------20-----------------------

学习是一个有机的过程,在这个过程中,知识的种子被缓慢而稳定地植入并铭刻在头脑中。这种知识的种子最终会在付诸行动时结出果实。正如本杰明·富兰克林所说:“告诉我,我会忘记;教我,我会记住;让我参与,我会学到。”。

工程包括应用实用的、科学的、经济的和社会的知识,这将有助于设计、建造、维护和各种形式的创造。工程学科兼收并蓄,有专门的工程流派领域。每一个都特别强调技术的独特领域及其用途。

自过去十年以来,不同领域的各种专家一直在努力将“学习”的艺术和“工程”的本质以教学培训模块的形式结合起来。这已经形成了一股强大的推动力,促使来自学习和工程领域的团队创建在线课程。

这种不断努力让不同的人拥有良好的专业知识,并尝试制作一些最好的在线培训课程,我们愿意称之为学习工程师。也就是说,创建一个稳定的学习工程学科是一项艰巨的任务。

那么,我们如何用通俗的语言描述一个学习型工程师在做什么呢?学习工程师是一群熟练的个人,他们通过人类行为和行动从基于证据的信息中得出结论。这种导致行动的证据然后被公式化,以基于各种工程环境场景创建准确、可靠并且更重要的是数据丰富的学习数据。

在宣布学习工程成为主流职业的紧迫性和必要性下,IEEE-SA(【http://standards.ieee.org/】)标准委员会 ICCom 强烈建议开展一项新的为期两年的行业联系()活动,为迅速发展的学习工程领域提供描述和支持。

虽然联盟已经成立,但现实情况是很难找到具备这种技能的人。但是在适当的时候,随着对这一学科的认识在市场上变得可用,将会有专家诞生。到目前为止,唯一的解决方案是让一个人拥有技术和科学工作背景,并与一位在教学设计方面有坚实基础的专家合作,帮助创建一个有弹性的在线课程材料。

这又带来了对工程设计和教学设计是否相同的进一步分析。让我们得到一些澄清。首先,学习工程师不属于支持角色。相反,他是一个学习工程师,一个成熟的贡献者,一个开发在线内容的积极分子。学习型工程师的角色是“学习”学习。另一方面,教学设计者是被赋予创建在线课程任务的专家。现在,基于发给他们的技术,教学设计者想出如何成功地写作业。

整个学工程的过程听起来很迷人。但是一个人如何进入这个领域呢?ICICLE 现在已经建立了特别兴趣小组(SIGs)来跟踪与人工智能以及自适应学习技术有关的项目。除此之外,SIG 还跟踪 xAPI &学习分析、学习数据标准、能力框架、LX(学习体验)设计和学习数据治理。这将有助于团队侦察学习工程在未来将如何塑造行业智慧和学术智慧。

学习工程师倾向于广泛参与包括学习 CMS(内容管理系统)和学习管理在内的技术。移动电子学习应用程序和创作工具是市场趋势的一些变体。除了上面提到的这些,学习工程师在准备独一无二的在线内容时,还会使用仪表盘来处理分析、视频和其他类似的流媒体内容。

在过去的五年中,有一个惊人的进步帮助维持了学习技术标准的过程。利用学习工程机制改变了我们使用学习技术的传统方式,并促使其进入数字化领域。因此,学习工程的项目标志着迎合市场变化的独特技能。据预测,到下一个十年,学习工程将成为教育部门(即教育技术公司、学校和大学)的一项成熟工作。

在所有方面,随着这些进步和技术被付诸实践以创造适应性学习体验,新手和教育工作者将需要某些参数,如透明度、公正性和经证明的效率。需要记住的是,为了学习工程的发展和可持续性,需要大量精通理论和环境的工程师,这将为有效的教学和学习过程增加更多的意义。

现在正在不断努力将这种独特的综合运用到工作中。麻省理工学院的在线教育政策倡议小组发布了一份报告(https://oepi.mit.edu/),陈述了各种学习科学如何应用于高等院校。弗吉尼亚大学也做出了类似的努力,他们将这一过程命名为杰弗逊教育加速器(【http://www.jeauva.com/】T2)。这项倡议的宗旨是通过帮助中型初创企业与学习科学研究人员建立联系,帮助他们吸收功效数据。

麦格劳希尔(McGraw Hill)等大型出版社创造了“学习科学公司”(Learning Science Company)这个名称,其主要关注点是深入研究数据集。反过来,这些数据集通过其 LearnSmart 技术开始积累。McGraw Hill 还渴望将更好的设计实践融入到产品设计流程中。皮尔逊也不落后,他专注于不同产品的功效,包括对不同产品和服务的一系列评估。

一个由 30 个教育学院院长组成的核心小组,有着相似的兴趣,他们聚集在一起,致力于在他们的员工进步到即兴发挥他们的计划后,利用实体化来表现他们的员工。除此之外,他们打算教他们的老师如何在课堂上应用学习科学,作为他们课程的一部分。

Kaplan 是一个令人敬畏的专业教育机构,它不仅仅参与了前面提到的努力。事实上,首席学习官 Bror Saxberg 一直在努力大规模地推行循证学习。Kaplan 的座右铭是详细说明学习策略和计划,以在学习者和学习组织之间获得适当的平衡。投入更多的时间和响应来验证学习证据收集方法的可靠性。在一个组织的不同部分实施受控跟踪,只关注了解对个人的成功有影响的过程。最后,努力在这个领域做出“学习工程”决策,面对现实世界给我们带来的所有限制和挑战。

希望,给你提供这些关于学习工程学的有价值的见解,可能会改变你对与工程科学合作学习这一概念的看法。因此,我们可以强烈地期望,在不久的将来,将适应过程和教育方法的发展和改进,这将通过利用工程科学始终如一地导致可重复的发展和随机应变的学习情况。所有这些都应与应对教学挑战相称。

向机器学习:关于数据产品,传统制造业能教给我们什么

原文:https://towardsdatascience.com/learning-from-machines-what-traditional-manufacturing-can-teach-us-about-data-products-e661f92c3594?source=collection_archive---------20-----------------------

从航空工程师转型为数据科学家的见解

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Photo by Chris Leipelt on Unsplash

这是一个两部分系列探索机器学习(ML)产品的 第一部分 。在第一部分中,我将实物产品和 ML 产品的生产进行了比较。在 第二部分 中,我讨论了为什么这些相似之处应该告知数据科学家如何进行产品开发。

作为一个领域,数据科学非常新,管理该领域的规范仍在建立中。有大量的资源解释机器学习中涉及的数学、统计学和迭代逻辑。还有更多研究如何将机器学习作为一种工具 来指导决策和解决业务问题——例如 A/B 测试和预测客户流失——或者作为一种功能来优化用户体验——想想推荐系统和个性化的策划内容。但是,因为它在商业中不太常见,所以关于机器学习作为一种产品* 的讨论要少得多,因为它的主要目的是解决市场问题并直接产生收入,例如自动驾驶汽车、客户支持聊天机器人服务和自动化保险服务等。*

在这一系列文章中,我以一种新的方式构建了机器学习产品概念,利用我在航空航天制造领域的背景来进行对比,以告知数据科学家和产品经理应该如何处理 ML 产品的开发和维护。

工厂类比

虽然这似乎违反直觉,但开发和维护机器学习产品的过程与构建物理产品比开发软件应用程序有更多的共同点。软件开发生命周期中通常缺少的是一个关键组件:数据供应链。这种缺失使得软件开发在某些方面变得更简单,因为拥有对产品不可或缺的数据意味着需要在产品的整个生命周期中考虑它。

那是什么意思?让我们从一个简单的类比开始,我发现这个类比有助于我的非技术朋友理解机器学习产品和物理产品之间的联系。

当你想要生产一个实体产品时——让我们使用飞机无线电,因为我曾经在一家制造这些产品的公司工作过——你需要设计和建造工厂,培训员工如何组装无线电,管理制造无线电所需的零件供应,整合任何客户定制,制造无线电并将其交付给你的客户。同样,在构建 ML 产品时,您需要训练模型(即设计/构建工厂并培训工人),收集客户输入(定制)并丰富这些输入(管理零件供应)以生成预测(即收音机)。

因为有如此多高度相互依赖的活动部件,一个功能的故障会导致其他功能的故障。你可以拥有拥有高端设备和顶级劳动力技能的最先进工厂,但不可靠或不充分的供应链(即数据缺失或数据不正确)最终会让你的产品沉没。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Building a custom aircraft radio versus providing customer predictions

相比之下,开发软件产品的过程要复杂得多。这类似于设计和构建一种体验。以一个销售服装的网站为例。一旦建成,有一个维护方面涉及到保持其运作。您可能希望定期更换内容或添加新功能来增强用户体验,但您通常不会依赖外部来源的数据流来维持网站的运行。虽然会有实物库存的供应链,但这与网站运营是分开的;网站本身根本不需要专门的供应链。因此,供应管理方面在软件开发生命周期框架中并不存在。一旦数据产品依赖于持续的输入数据,框架就需要遵循物理产品的供应管理实践,否则您将被迫进行被动管理。

深入观察

回到实物产品的类比,让我们来看几个现实生活中的场景,说明为什么实物产品的比较如此有用,特别是在涉及供应链管理时。

有一段时间,我在一家生产无线电的航空公司做采购员。有一天,我们发现有一批坏的开关集成电路(一种电子芯片)。大部分产品都没有通过测试,我们需要购买更多的产品来生产一台不太受欢迎的收音机。当我与我们的供应商核实时,我发现他们不再销售这种芯片。更糟糕的是,其他供应商已经将其列为过时产品。制造商两年前就已经停止生产了,我们对此一无所知。我们已经做了 12 年的收音机。我们需要尽快更换芯片!

我们能够在一个子组件上做一个小的重新设计,以包含一个更新、更小的芯片。这需要暂停生产,直到新的设计到位,在重新开始生产之前重新测试产品,并加班加点完成订单,以兑现客户的承诺。对于一个更保守的行业,同样的产品销售几十年,这种情况并不少见。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Photo by Nicolas Thomas on Unsplash

虽然这可能不会立即显而易见,但这种情况实际上与数据科学家可能遇到的情况非常相似。最近,我在检查一个原型模型的数据更新。我想验证我们使用的所有外部上下文数据都是新鲜的,所以测试预测将是准确的。在检查中,我注意到有一个资源已经过时了,更糟糕的是,我们再也无法访问那个资源了。我们需要尽快替换数据集!

虽然我们能够找到新的可比数据来源,但这些数据并不完全匹配。就像前面的飞机无线电示例一样,替换需要重新培训和重新测试新的 ML 模型,并重新运行我们的所有评估指标来检查影响。幸运的是,这不是在真实环境中托管的;我只能想象不得不将生产模型离线以修复数据质量或数据检索紧急情况的噩梦。这将是难以置信的破坏性。有一些最佳实践和检查可以帮助防止这些问题,但是我将把这个讨论留到以后。

从这些例子中,物理和 ML 产品开发之间的一些更深层次的相似之处应该是显而易见的。两者:

  • 要求持续供应高质量的投入(或零件),以便持续生产/交付;
  • 受到供应链的摆布(特别是在产品依赖非内部生成的数据的情况下);
  • 随着时间的推移,要求根据需要重新设计,以满足可持续性和/或性能需求。在这两种情况下,这通常严重依赖于供应链。

更重要的是,这些例子暗示了管理开发的需要,要意识到供应链如何影响产品生命周期的各个阶段。就像在制造业中一样,依赖于数据供应的数据产品需要从一开始就考虑到这些数据来进行管理。这是我将在这个由两部分组成的系列的下一篇文章中讨论的内容,在这篇文章中,我将探索用于最小化风险的传统供应链管理方法,并将其转化为数据科学产品。

总之,机器学习和数据依赖系统的性质使你面临其他软件应用程序中通常看不到的独特风险,但这些风险不是该行业独有的。它们在制造业中以类似的形式存在,供应链战略的概念可以直接应用于数据科学。管理好数据风险就是确保你的 ML 产品持续成功。这就是数据供应策略的存在或缺乏能够成就或摧毁你的产品的地方。

嗨,我是 凯蒂·拉泽尔-费尔曼 。我是纽约市geo phy的数据科学家。对这个帖子有疑问或者对这个话题很好奇?欢迎在下面评论或者 联系我

人工智能学习金拉米,第一部分

原文:https://towardsdatascience.com/learning-gin-rummy-part-i-75aef02c94ba?source=collection_archive---------5-----------------------

在我关于主题的上一篇文章中,我描述并包含了一个手工构建的玩金拉米的系统的代码,该系统只考虑当前可见的牌,而不考虑对手已经捡起或埋在弃牌堆中的先前可见的牌的记忆。我的直觉是,如果你在策略中包含已知牌的历史,你应该可以玩得更好,并且可靠地击败我手工构建的策略。

理解手牌构建策略的关键首先是手牌和游戏状态的表示,其次是手牌评估函数。

表现

金拉米世界的表示是一个 4 x 13 的矩阵,对应于一副牌中的四种花色,以及花色中牌的值,从 a 到 k。例如,拿这手(赢的)十张牌来说:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

这将由矩阵表示(其中 1 表示您有该卡):

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

游戏状态也是 4×13 矩阵,然而代替 0/1,有九种状态对应于哪个玩家持有哪些牌,哪些牌已经被放在弃牌堆中,哪些牌留在库存中(面朝下的牌堆)。这些状态是:

## Card states:          
## 0 Stock         
## 1 Player 0 card that was stock      
## 2 Player 0 card that was discard      
## 3 Player 1 card that was stock      
## 4 Player 1 card that was discard      
## 5 Player 0 top-discard       
## 6 Player 0 discard       
## 7 Player 1 top-discard       
## 8 Player 1 discard 

一个游戏状态的例子,玩家 0 刚刚用上面说明的那手牌赢了游戏:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

最后,还有另一种表示方法,那就是股票牌的顺序(stockOrder),它表示为一副牌中 52 张牌的列表,这是一个 4 x 13 矩阵的简化版本。游戏开始时,洗牌相当于:

stockOrder = np.arange(52)

手动评估

手牌评估功能为手牌中的每张牌赋值,值越高的牌越有价值,有助于组成得分牌。价值较低的牌是你可以弃掉的牌。

手动构建的手牌评估函数背后的思想是,如果一张牌在花色中具有水平最近邻,以构成顺子得分(例如,上面手牌中的红心 4 到 7),则该牌获得更高的值。此外,如果一张牌有垂直的相邻牌(例如三个皇后),它的价值也更高。

手动构建的手牌评估函数使用卷积矩阵来评估手牌中的每张牌。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

这意味着,根据水平相邻的牌,增加的价值最大,而相同价值不同花色的牌也很有价值。

战略

每回合,玩家必须做出两个决定:

  1. 取货:你是要正面朝上的丢弃,还是正面朝下的股票卡?
  2. 弃牌:你手里的 11 张牌你会弃哪张?

手工构建策略是拾取步骤的一个简单规则:

  1. 用最大弃牌评估当前手牌
  2. 如果最上面的弃牌是你手中价值最低的牌,则取牌。否则拾取丢弃。

更简单的规则是弃牌步骤:评估你手中的 11 张牌,弃掉价值最低的牌。

手工打造的策略有什么好的吗?

在我和我的两个孩子艾娃和卢卡参加的一场非正式锦标赛中,手工打造的策略极具竞争力。这是玩金拉米游戏的最佳策略吗?大概不会。手工构建的策略有点愚蠢,因为它忽略或“忘记”了以前玩过的牌。我知道如果我的对手在收集 a,我会尽量避免丢弃 a。手工构建的策略不会这样做。

我可以认真考虑一下,自己构建一个考虑历史牌的手牌评估函数的扩展,但我想开发一个自动学习这种手牌评估的系统。是时候学习人工智能技术了。下一篇将会讲述我是如何接近这个的。

用机器的方式学习人类。

原文:https://towardsdatascience.com/learning-humans-the-machine-way-26bb2137e1ec?source=collection_archive---------5-----------------------

我们到底是什么,在我们自己的大脑里发生了什么?仅仅是化学反应让人思考吗?还是不止如此。我们,人类,创造了这么多的指标来解决很多问题来生存和互相帮助。但是我们仍然会犯一些错误,比如迷失、失控和忽视。我们把随机时刻联系起来,让事情变得更复杂。背后的方程式是什么?是你周围的环境或人,还是你自己?在思考了所有这些之后,我开始分析机器是如何工作的,它们是如何进行繁重的计算的。它们是如何处理的?他们现在是如何获得思考“人工智能”的能力的当你能理解机器的时候,它会让你很高兴去关注上面提到的人类的问题。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

source : MIT Technology Review

这个世界上的一切都可以局限在 0 和 1。这些 0 和 1 是这项技术背后的计算单位。当谈到我们人类的大脑时,我们将这些计算单元命名为神经元。那么这个计算单位是做什么的呢?这些能被削减成更多的子部分吗?答案是肯定的;我们甚至可以将这些计算单元分成更小的部分。而是你对理解事物的感知。让我们举一个计算机解一个简单的数学方程 a +b 的例子。计算机从来不识别实数,它唯一能理解的是二进制数 a 0 或 1。如果是 1,那么功率通过电路,如果是 0,那么通俗地说就不行了。但是,它能够理解所有复杂方程的媒介是“编程语言”

同样,神经元也从来不会体验到我们生活的情绪或环境。他们表现得像问题的解决者,有时是问题的创造者。他们在一瞬间把所有的事情和情况联系起来。我们能控制它吗?答案是否定的。因为它将在神经元控制中,让你循环通过事物。你解决问题的能力将与神经元之间的相互作用,以及它们连接的速度有关。就看你从小怎么培养他们了。“你是怎么训练他们的?”我们能训练他们吗?不,它们只是会适应你做事的方式,你通过它传递的等式。

即使对计算机来说,我们也不知道二进制在里面是如何工作的,我们传入方程。幸运的是,我们的大脑不是由铜层或玻璃纤维制成的。虽然我们可以训练它快速计算,但这需要几年的时间。机器擅长存储和速度,但大脑保持效率领先。

写这篇文章的原因是,有时候,我不明白为什么我在思考一个问题时会把事情变得更复杂,然后我意识到,不是我在思考这个问题。这是因为有很多化学反应和计算是我无法控制的。然后,当我试图理解计算机/机器时,我知道我可以验证我的一个鼓舞人心的人物所说的话。《人工智能的局限性》涉及到在计算机科学和生物学之间架起一座桥梁。"

我是一名充满激情的工程师,试图理解机器和人类。这篇文章可以帮助你更简单、更容易地解决你的问题。你所需要做的就是深入思考。为了让你把事情联系起来,我留下了这篇不完整的文章。敬请关注下一篇文章。

为机器学习和深度学习学习数学

原文:https://towardsdatascience.com/learning-maths-for-machine-learning-and-deep-learning-5509c097ee83?source=collection_archive---------2-----------------------

虽然我在攻读工程学位时确实学了很多数学,但当我想进入机器学习领域时,我已经忘记了大部分。毕业后,我从未真正需要过任何数学。我做了很多依赖逻辑的 web 编程,我可以诚实地说,每一个标题中带有“管理”一词的系统都让我损失了三分之一的数学知识!我已经为学习管理系统、内容管理系统和客户关系管理系统编写了扩展程序——我将让您来计算我在使用这些系统后获得了多少数学应用。目前,我已经掌握了很好的数据科学技能,可以使用各种 ML 和 DL 算法。我已经成功完成了许多 MOOCs 课程(例如,Udacity 的深度学习基础课程和吴恩达的新 Coursera 课程)。我会用 Scikit Learn,TensorFlow,Kera 的。….但是我对创造新的算法变种有粗略的想法。目前,我真的想创建一种新的交互式主题建模算法。由于缺乏数学知识,我感到进退两难。在我试图重新学习一些基础数学的旅行中,我遇到了几本由具有解释艺术的人写的书。这些书产生了巨大的不同,因为它们能够以非常简单的方式传达复杂的概念。我写这篇博客是为了分享这些伟大的资源,尤其是对程序员而言。这些书涵盖了微积分和线性代数。我还没有找到一本等效的概率和统计书籍——如果你知道一本,请留下评论或发推文。

汤普森使微积分变得简单

从一本 1914 年写的书里学微积分!书的 pdf 是免费的。这本书简直太棒了。英语是有点老的风格,但解释是永恒的。汤普森让微积分变得超级简单。成本函数的优化是 ML 和 DL 的核心,这本书将帮助你理解最小化的基础。那些渐变体面的更新规则将不再看起来像魔术。看看序言就知道了——它为这本书的其余部分定下了基调……

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

The Prologue from Calculus Made Easy by S. Thompson

P. N .克莱因的矩阵编码

大多数线性代数书从简单开始,但是像图像、基、维数、正交化、特征向量这样的概念是以完全抽象的方式介绍的。大多数线性代数书籍甚至没有介绍真实世界的应用,并且很难看出你在哪里或者为什么要使用数学。矩阵乘法是一个很好的例子,我学到了一些东西,但从来没有真正理解(即,为什么它不是一个元素一个元素地执行)。编码矩阵不一样!您实际上可以在提高 Python 编程技能的同时构建自己的线性代数库!这本书充满了实际的计算机科学应用(例如,固定白板照片的角度)。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Coding the Matrix — the best Linear Algebra book ever!

学习神经网络架构

原文:https://towardsdatascience.com/learning-neural-network-architectures-6109cb133caf?source=collection_archive---------12-----------------------

如何自动创建神经网络

上次我们谈到了学习的限制,以及消除对神经网络架构设计的需求将如何导致更好的结果和深度神经网络的使用。

在这里,我们将分析所有最近的学习神经网络架构的方法,并揭示利弊。这篇文章会随着时间的推移而发展,所以一定要不时登录以获取更新。

首先…

学习一个神经网络架构意味着什么?这意味着尝试以最佳方式组合所有的神经网络构建模块,以在某些任务中获得最高性能,比如说:对 ImageNet 图像进行分类。

这里你可以看到过去 10 年左右所有最近的神经网络架构。所有这些建筑都是人类凭直觉和原始脑力精心打造的。这是人类最大的智慧,但是正如你所想象的,它并不总是导致最好的解决方案。正如我们在这里提到的,这不是进步的方式,因为我们将受到人类思维所能想到的限制,并且永远不会完全搜索神经架构的大空间。想想最近象棋围棋的游戏发生了什么!人类被搜索最佳行动和策略的神经网络算法打得落花流水。

神经网络算法将在神经结构搜索领域击败人类,就像他们在围棋和国际象棋中击败人类一样!

所以要走的路真的是使用神经网络来寻找越来越好的神经架构。实际上,我们将使用相同的梯度下降技术来引导神经结构的巨大搜索。

但是正如你所看到的,有许多可能的神经构建模块,搜索空间是巨大的。想象我们已经尝试了所有可能的卷积层:不同数量的输入输出平面、膨胀、深度、池化、非线性等…搜索空间可以从 10 个⁴到 10 个⁸or 更多选项!这是一个巨大的空间。想象一下,我们花 1 个小时来训练和测试一个架构……那么我们将需要 10 个⁴小时,或者永恒!

梯度方法

基于控制器的方法,如 Zoph,Le (2017 )使用递归神经网络来创建新的架构,然后用强化学习来测试它们。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

An overview of Neural Architecture Search

他们将神经网络的连接和结构编码成可变长度的字符串,并使用 RNN 控制器来生成新的架构。“子网络”是在数据集上训练的,以产生训练和验证精度。验证准确度被用作训练控制器的奖励信号。随着控制器随着时间的推移在搜索中改进,这又在接下来的迭代中产生更好的神经网络。

刘看着艾尔通。(2017) 使用启发式搜索,从简单的神经网络结构开始,逐步增加复杂度。本文基于Zoph et al(2018)的工作。在后一篇论文中,他们再次使用相同的 RNN 控制器来搜索架构:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Controller model architecture for recursively constructing one block of a convolutional cell.

该控制器产生一系列输出,这些输出对上图顶部的每个元素进行编码,基本上包括:使用前两层,对两个输入中的每一个应用哪种操作,以及用哪种方法将它们的两个输出合并成一个输出。

为了减少可能的参数组合数量,他们使用下图所示的固定构造块架构。该区块可以实现类残差层和类 Google net层。它们允许 RNN 控制器为每层找到多个块,通常是 5 个,这是有效性和搜索空间之间的一个很好的折衷。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Example constructed block

在这项工作中,他们还将可能的基本构建模块的数量限制在以下列表中:

  • 身份;1x7 然后 7x1 卷积;1×3 然后 3×1 卷积;3x3 平均池化;3x3 或 5x5 或 7x7 最大池化;1x1 或 3x3 卷积;3×3 或 5×5 或 7×7 深度方向可分离卷积;3x3 扩展卷积

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Scalable architectures for image classification consist of two repeated motifs termed Normal Cell and Reduction Cell.

他们创造了如左图所示的架构。基于以前的架构历史,他们决定整体架构应由两种类型的单元组成:(1)返回相同维度的特征图的卷积单元或正常单元;以及(2)返回高度、宽度或缩减单元 l 缩减两次的特征图的卷积单元。注意,在这些架构中,每当空间激活大小减小时,它们还会将输出中的滤波器数量增加一倍,以保持大致恒定的隐藏状态维度。还要注意的是,左图中的这个架构有点类似于 ResNet 中的模块,包括普通和简化单元的选择。

为了训练控制器 RNN,他们使用强化学习。一旦 RNN 建造了一个建筑,它就被训练了。利用验证数据集中的准确性,产生奖励信号,并用于向 RNN 控制器提供反馈,最终训练它在建筑搜索方面越来越好。由于奖励信号是不可微分的,他们使用策略梯度方法,如加强,并通过使用以前验证奖励的移动平均值减去当前验证值。这有效地充当了验证准确性的增量改进度量。

有趣的是,在下图中你可以看到算法找到的最佳细胞。它们似乎是更复杂版本的 Inception-ResNet 层。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Architecture of the best convolutional cells (NASNet-A) with B = 5 blocks identified with CIFAR-10

结果很好!他们发现,与人类手工制作相比,大型和小型神经网络都非常高效和高性能。下面我们报告一个小模型的表格。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Performance on ImageNet classification on a subset of models operating in a constrained computational setting, i.e., < 1.5 B multiply-accumulate operations per image

最后,本文对强化学习搜索相对于随机搜索的性能做了一些有益的评论。在过去的努力中,击败随机搜索出人意料地困难。RL 搜索更好,可以找到很多更好的模型,但随机搜索的效果也令人惊讶。毕竟这就是创造我们人类大脑的东西,但在此之前只花了几十万年和 50 亿年…

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Comparing the efficiency of random search (RS) to re- inforcement learning (RL) for learning neural architectures

总的来说,这是一个很有指导意义的模型搜索,但方法和结果可以用于许多不同类型的神经网络。我们希望在接下来的几年里看到这项技术得到更多的应用。一个缺点是所使用的模型架构非常类似于 ResNet 块架构。此外,构造的块仅捕获可能集合的子集。这当然都是为了减少搜索空间并使问题更易处理,但是它并没有例如推广到编码器-解码器架构或更小的应用。为此,人们将不得不创建新的构造块和基础网络。

此外,对体系结构的搜索计算量非常大,并且花费大量时间。你需要 500 个 GPU(贵的像英伟达 P100!)而且你需要在 4 天内测试 20,000 个神经网络才能找到结果

遗传搜索

遗传搜索是穷举搜索方法,创建不同的神经架构,然后逐一尝试。因此,它们经常受到无向导搜索的缓慢过程的限制。例如 Wierstra 等人(2005 年)、Floreano 等人(2008 年)、Stanley 等人(2009 年)。这些方法使用进化算法来搜索新的架构。

神经进化是一种最近在强化学习算法中获得成功的方法。它最近在强化学习任务中取得了成功,而其他算法(DQN、A2C 等)却没有取得成功。)失败了。

作为网络架构搜索进行修剪

最近,神经网络的修剪作为一种神经网络结构搜索技术被重新审视。本文展示了两个主要的见解:1)可以从修剪过的神经网络开始,并从头开始训练它;2)修剪因此可以被视为类似于网络结构搜索的优化神经网络结构的技术。

注意,修剪产生的结果不如上面讨论的基于梯度的搜索技术好。

关于作者

我在硬件和软件方面都有将近 20 年的神经网络经验(一个罕见的组合)。在这里看关于我:媒介网页学者LinkedIn 等等…

[学习笔记]循环网络中的辍学—第 2 部分

原文:https://towardsdatascience.com/learning-note-dropout-in-recurrent-networks-part-2-f209222481f8?source=collection_archive---------1-----------------------

喀拉斯和 PyTorch 的经常性辍学实施

在进行实验之前,我想详细检查一下实现,以便更好地理解和将来参考。由于篇幅限制,我用#...省略了对当前讨论不重要的行。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

https://keras.io/img/keras-logo-small.jpg

克拉斯

这里我用的是 Tensorflow 1.3.0 自带的 Keras。

实现主要驻留在LSTM类中。我们从LSTM.get_constants类方法开始。为Recurrent.call方法中的每个批处理调用它,以提供丢弃掩码。(输入辍学率和经常性辍学率已作为实例属性存储在__init__。)

输入以 (样本,时间(用零填充),input_dim) 的形式排列。上面的代码块创建形状为 (samples,input_dim) 的输入掩码,然后随机将元素设置为零。因此,对于每个序列/样本,新的掩码被采样,与论文【1】中描述的一致。

注意创建了四个不同的掩模,对应于 LSTM 的四个门。只有 LSTM 支持这个设置。(更多细节见下文)。

同样,上面创建了四个形状为 (samples,hidden_units) 的循环遮罩。

接下来我们转向LSTM.step方法,该方法在每个时间步依次执行:

Keras 有 3 个 LSTM 实现,默认为实现 0:

实现:{0、1 或 2}之一。如果设置为 0,RNN 将使用使用更少、更大矩阵乘积的实现,从而在 CPU 上运行更快,但消耗更多内存。如果设置为 1,RNN 将使用更多的矩阵产品,但较小的,因此运行速度较慢(实际上可能在 GPU 上更快),同时消耗较少的内存。如果设置为 2(仅适用于 LSTM/GRU),RNN 会将输入门、忽略门和输出门组合成一个矩阵,从而在 GPU 上实现更省时的并行化。注意:RNN 辍学必须为所有门共享,导致稍微减少正规化。

实现 2 对应于捆绑权重 LSTM。上面的代码块实现了 dropout,就像这个公式[1]一样:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Dropout in Tied-weight LSTM

请注意它是如何只获取第一个遮罩并丢弃其余的(三个遮罩)的。这是因为这个公式要求所有门共享 RNN 辍学。

看来实施 01 在如何应用输入压差方面有所不同。在实现 0 中,转换后的输入在step 方法之外预计算,而在实现 1 中,输入被丢弃并在step内转换。

(注意每个门如何使用它自己的下降掩码,以及如何为每个门组合转换的输入和隐藏状态。)

就是这样。实现没有任何惊喜,所以你可以放心使用 [dropout](https://keras.io/layers/recurrent/#lstm) [recurrent_dropout](https://keras.io/layers/recurrent/#lstm) 参数。你唯一需要考虑的可能是是否使用实现 2 而不是 0 来加快速度。

(目前 Keras 似乎不提供[1]中描述的嵌入丢失。不过,我认为你绝对可以为此编写一个自定义层。)

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

http://pytorch.org/tutorials/_images/pytorch-logo-flat.png

PyTorch

正如在第 1 部分中提到的,PyTorch 不提供对变化的辍学的本地支持。我们将使用来自sales force/awd-lstm-lm项目的实现。(此部分针对 PyTorch 0.2.0 版本)

锁定输出 可用于对每个时间步长应用相同的下降掩码(如输入下降):

PyTorch 一般支持两种序列张量排列: (样本,时间,输入 _ dim)(时间,样本,输入 _dim)* 。上述代码块是为后一种安排而设计的。您可以很容易地修改它来支持这两种安排。m被创建为一个单一时间步长的下降遮罩,形状为 (1,样本,输入 _ 尺寸) 。因此,每个序列都要采样一个新的掩码,与 Keras 中的一样。*

接下来是 WeightDrop 类。在[2]中提出的这种压差形式更简单,性能更好,即使在捆绑权重设置中,每个门也允许不同的压差。相比之下,要实现传统的变分丢失,可能需要在 For 循环中将 LSTM/RNN 分解成单独的时间步长。

_setupweight drop中禁用参数展平(否则无法与 CUDA 配合使用),并将目标权重矩阵(通常为weight_hh_l0)重命名为带有_raw 后缀的矩阵。在forward中,目标权重被应用了一个删除遮罩,被复制并重命名为原始属性名(weight_hh_l0)。注意注册的参数是带有_raw后缀的权重矩阵(删除操作不会影响该权重矩阵)。

有两种类型的重量下降,由variational参数控制。在我们能够理解代码之前,我们首先需要知道权重矩阵是如何工作的:对于 LSTM nn.LSTM,有四个相关联的参数:weight_ih_l0weight_hh_l0bias_ih_l0bias_hh_l0。命名要足够明显:ih表示输入要隐藏;hh意为隐来隐去;l0表示第一层。如果以nn.LSTM(2, 8, num_layers=1) 为例,weight_hh_l0 (U) 会有一个 (32,8) 的形状,对应四个门和八个隐藏单元(32 = 8 * 4)。你应该能认出这是一只负重 LSTM。这暗示了隐藏状态矩阵 (h) 被整形 (8,batch_size) 。矩阵乘法 Uh 将产生一个 32 x batch_size 矩阵。每列代表一个单个序列的八个隐藏单元及其四个内部门的转换后的循环输入(注意 PyTorch 使用 Uh 而不是 hU ):

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Internal Definition of LSTM

对于variational=True,创建形状为 (4 * hidden_units,1) 的遮罩。将任何一个元素设置为零意味着切断隐藏单元中一个门的所有循环连接。这似乎有点不可思议。如果我们希望 dropout out 与 Keras 绑定权重实现(下面的公式)一致,我们需要使用形状为 (1,hidden_units) 的遮罩。将任何一个元素设置为零意味着切断所有源自隐藏单元的循环连接。(记住,Keras 中的单个循环漏失遮罩是成形的(示例,hidden_units)。)有可能是我弄错了,或者是 bug,或者是作者故意这样做的。我还不确定。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

(Reprise) Dropout in Tied-weight LSTM

对于variational=False,创建形状 (4 * hidden_units,hidden_units) 的遮罩。因此,不同的隐藏单元和不同的门使用不同的掩模。

WeightDropKeras 实现的一个重要区别是权重矩阵的丢弃掩码只能在每小批量采样一次。如果您试图对每个序列采样一次,那么它实际上是使用大小为 1 的小批量,失去了使用小批量的目的。根据小批量的大小,这种限制导致每个小批量内不同程度的变化减少。(记住,在 Keras 中,对每个序列采样新的缺失掩码。)因此,总是从variational=False配置开始似乎是个好主意。

最后,嵌入漏失:

这应该很简单。漏音遮罩的形状为 (num_words,1) ,漏音应用于字级。如[1]中所述,当字数和嵌入维数很大时,这种实现可能会有一些性能问题。但是我猜作者认为这是代码简单性和性能之间的一个适当的折衷。

把它放在一起

使用所有三个讨论过的辍学的示例模型:

(第 11–15 行)虽然 WeightDrop 不需要分割时间步,但是它需要分割 RNN 层。这是我们可以在图层之间应用locked roup的唯一方法。

(第 30 行)此处forward应用了嵌入 dropout。

(第 31,35 行)locked rout通过简单地传递张量和辍学率来应用。

待续

这个帖子很乱,很抱歉。用简单的英语从技术上写作很难…无论如何,在最后一部分,我将记录一些实验结果。所得结果与文献[1]的结果有些不同。我也会试着对此做一些解释。

* [## [学习笔记]循环网络中的辍学—第 1 部分

理论基础

becominghuman.ai](https://becominghuman.ai/learning-note-dropout-in-recurrent-networks-part-1-57a9c19a2307) [## [学习笔记]循环网络中的辍学—第 3 部分

一些实证结果比较

medium.com](https://medium.com/@ceshine/learning-note-dropout-in-recurrent-networks-part-3-1b161d030cd4)

参考

  1. y . gal 和 z . Ghahramani(2015 年)。在递归神经网络中基于理论的辍学应用。
  2. 梅里蒂,s .,凯斯卡尔,N. S .,&索彻,R. (2017)。规范和优化 LSTM 语言模型。*

[学习笔记]循环网络中的辍学—第 3 部分

原文:https://towardsdatascience.com/learning-note-dropout-in-recurrent-networks-part-3-1b161d030cd4?source=collection_archive---------5-----------------------

一些实证结果比较

在第一部分中,我们介绍了循环网络中变分丢失的理论基础。第二部分研究了 Keras 和 PyTorch 中的实现细节。现在是最后一部分,我们在公共数据集上比较不同的模型。

MC 辍学实施

Keras 没有一个参数或函数来启用测试时间的丢失。虽然你可以使用一个总是活跃的 lambda 层,我们不容易比较标准漏失近似和蒙特卡罗漏失的结果。

撰写核心论文[1],的 Yarin Gal 提供了一个 2017 年 2 月在 Github 上实现 MC dropout 的例子。这也是 Keras 开始为经常性辍学提供内置支持的时候。仅仅过了几个月,它就很快过时了。我挖了一下 似乎 已经让它与 Kera s 的最新版本 Tensorflow 1.3.0 一起工作了。

对于 PyTorch 来说,事情就简单多了。在前馈前使用model.eval()使能标准压差近似值,使用model.train()使能蒙特卡洛压差。

请注意,一些超参数是根据框架经验调整的。例如,在 Keras 中,学习率被设置为 1e-3,但在 PyTorch 中,它被设置为 1e-4。目的是避免模型永远收敛。因此,建议将重点放在同一框架中实现的模型之间的比较上。

康奈尔电影评论数据集

该数据集在论文[1]中用于评估不同的模型。有 10,620 个训练样本和 2,655 个测试/验证样本。这是一个回归问题。给定一个单词序列,模型需要预测用户给这部电影的分数。将分数归一化,使其以零为中心,单位方差为。在下面的讨论中,**【原始 MSE】**将对应于归一化分数的均方误差,将对应于原始分数的均方根误差(文中使用 RMSE)。

批量大小设置为 128,序列长度为 200(填充),与论文中相同。所有模型中隐藏单元的数量保持不变。唯一的区别是如何应用辍学。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Fig 3(b) in [1]: Naive Dropout LSTM over-fits eventually

论文中使用的退出概率似乎大多是 0.5 。正如你在上图中看到的,这可能与缓慢的收敛速度有关。变分 LSTM 需要数百个历元才能胜过其他两个模型。我没有太多的时间来训练这么多的纪元,所以在允许一些过度拟合的同时,降低了退出概率以提高速度。关于确切的概率,请参考本节末尾的电子表格。

克拉斯

评估了三种模型:

  1. **变量:使用输入压差、循环压差和输出压差。
  2. **无脱落:只有极低的重量衰减。
  3. **朴素漏失:使用时间步长独立输入漏失,输出漏失。

所有三种模型都没有嵌入丢失。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

(向右修正图表的坐标轴标签:X 轴:" 原始 MSE 差异 “,Y 轴:” 计数"】**

图表“(MC —近似值)直方图”是每个样本的 MC 差值的原始 MSE 减去标准差值近似值的直方图。注:在变分和简单的 LSTM 模型中,MC 下降通常产生较低的原始 MSE。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

天真的辍学者似乎是最好的执行者,并且不会随着时间的推移而过度适应。

PyTorch

测试了五个模型:

  1. 重量下降 [ 2 ]:使用输入下降、重量下降、输出下降、嵌入下降。
  2. 无脱落:香草单层 LSTM,无重量衰减。
  3. 朴素漏失:使用时间步长独立输入漏失,输出漏失。
  4. 变重量下降:与 变重量下降 相同,但参数设置为真。**
  5. 无经常性脱落的变化 ( 变量-2v w/o r-drop ):与重量脱落相同,但重量脱落概率设置为零。(无经常性辍学)

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

对于重量下降的 LSTM,MC 压差低于标准压差近似值。这也适用于没有经常性辍学的变分 LSTM。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

在这种情况下,“无辍学”模型严重过度拟合。与 Keras 的结果相比,我们也许可以把 RMSE 的陡峭上升归因于没有重量衰减。然而,PyTorch 的“天真辍学”模式在 RMSE 也有缓慢上升的趋势。“重量下降变化”模型似乎有一些不合适的问题。

摘要

以下是实验及其结果的详细记录:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Spreadsheet Link

(似乎没有办法把谷歌电子表格嵌入到一个中等的帖子里。请使用表格下方的链接获取表格的网页版本。)

(尽管 MC dropout 在减重模型中的性能较差,但为了简单起见,我坚持使用 MC dropout:所有预测(除了“无脱落”模型)都是使用 10 轮 MC dropout 创建的。

IMDB 电影评论数据集

这个数据集是一个二元分类问题。有 25000 个训练样本和 25000 个测试样本。目标是从给定的单词序列中预测用户是否喜欢这部电影。

批量大小为 128,序列长度为 80(填充)。

模型结构和之前差不多,这里就不赘述了。

克拉斯

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

和以前一样,MC 丢失通常产生较低的对数损失。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

(epoch 17 后有一些数值问题,生成 NaNs 为 log loss。图表中省略了这些数据点。)

在这个数据集中,所有模型都随着时间的推移而过度拟合。

PyTorch

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

和以前一样,权重下降模型在 MC 丢失时表现更差,就像变分模型在经常性丢失时一样(不在直方图中)。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

在这种情况下,“天真辍学”模型明显过度拟合。其他三个辍学模型都得到了类似的表现。

摘要

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Spreadsheet Link

“变权重下降”在这个数据集中表现得令人惊讶,具有体面的验证损失,并且相当抗过拟合。

总体评论

  1. 我们可以从减肥模特身上得到一些不错的表现。然而,退出概率需要仔细调整。
  2. 我怀疑 MC dropout 性能的下降与嵌入 dropout 的使用有关。我会尝试使用更多的采样轮或只是在测试时间禁用嵌入丢失。
  3. 从 IMDB 数据集的结果来看,嵌入丢失似乎在防止过拟合方面有适度的贡献。
  4. 在 Jupyter notebook 中进行实验(链接到下面的代码)需要大量的手工劳动,并且只能在一定程度上进行管理。如果需要更全面的评估,我会使用类似于神圣的来自动化这个过程。

** [## ces hine/经常性辍学实验

通过在 GitHub 上创建一个帐户,为经常辍学实验的发展做出贡献。

github.com](https://github.com/ceshine/recurrent-dropout-experiments)**

参考资料:

  1. Gal,y .,& Ghahramani,Z. (2016)。作为贝叶斯近似的辍学:表示深度学习中的模型不确定性
  2. 梅里蒂,s .,凯斯卡尔,N. S .,&索彻,R. (2017)。规范和优化 LSTM 语言模型

以前的零件

** [## [学习笔记]循环网络中的辍学—第 1 部分

理论基础

becominghuman.ai](https://becominghuman.ai/learning-note-dropout-in-recurrent-networks-part-1-57a9c19a2307) [## [学习笔记]循环网络中的辍学—第 2 部分

喀拉斯和 PyTorch 的经常性辍学实施情况

medium.com](https://medium.com/towards-data-science/learning-note-dropout-in-recurrent-networks-part-2-f209222481f8)**

[学习笔记]带 Pytorch 的单次多盒检测器—第 1 部分

原文:https://towardsdatascience.com/learning-note-single-shot-multibox-detector-with-pytorch-part-1-38185e84bd79?source=collection_archive---------1-----------------------

最近我在尝试学习 Pytorch 以及一些物体检测深度学习算法。因此,为了一举两得,我决定阅读由 Max deGroot 撰写的单次多盒检测器论文以及其中一篇 Pytorch 实现。

诚然,我在理解论文中的一些观点时有些困难。看了实现,挠了一会儿头,我想我至少弄明白了其中的一部分。所以下面是我在第一遍和第二遍阅读后对一些混淆概念的笔记。

网络结构

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

SSD Architecture taken from the original paper

首先,单次多盒检测器(SSD)使用在 ILSVRC CLS-LOC 数据集上预训练的 VGG-16 结构,并增加一些额外的卷积层。相关代码位于 ssd.py :

base = {
    '300': [64, 64, 'M', 128, 128, 'M', 256, 256, 256, 
            'C', 512, 512, 512, 'M', 512, 512, 512],
    '512': [],
}
extras = {
    '300': [256, 'S', 512, 128, 'S', 256, 128, 256, 128, 256],
    '512': [],
}

“m”表示内核大小为 2、步幅为 2 的最大池。“c”表示相同的最大池化,但带有在原始结构中没有出现的ceil_mode=True。我的理解是ceil_mode=True处理输入高度或宽度不能被 2 整除的情况,所以在输出中会有一些单元格来自 1x2,2x1,1x1 max 池。不知道为什么会在那里,但应该没什么区别。

“S”表示一个stride=2padding=1卷积层,过滤器的数量在列表中紧随其后(例如,第一个“S”有 512 个过滤器)。

def vgg(cfg, i, batch_norm=False):
    layers = []
    in_channels = i
    for v in cfg:
        if v == 'M':
            layers += [nn.MaxPool2d(kernel_size=2, stride=2)]
        elif v == 'C':
            layers += [nn.MaxPool2d(
                kernel_size=2, stride=2, ceil_mode=True)]
        else:
            conv2d = nn.Conv2d(
                in_channels, v, kernel_size=3, padding=1)
            if batch_norm:
                layers += [
                    conv2d, nn.BatchNorm2d(v), 
                    nn.ReLU(inplace=True)]
            else:
                layers += [conv2d, nn.ReLU(inplace=True)]
            in_channels = v
    pool5 = nn.MaxPool2d(kernel_size=3, stride=1, padding=1)
    conv6 = nn.Conv2d(
                512, 1024, kernel_size=3, padding=6, dilation=6)
    conv7 = nn.Conv2d(1024, 1024, kernel_size=1)
    layers += [pool5, conv6,
               nn.ReLU(inplace=True), conv7,
               nn.ReLU(inplace=True)]
    return layers

请注意,它向原始 VGG 结构添加了一个 conv6 (1024 个 3×3 卷积滤波器,膨胀=6,填充=6)和一个 conv7 (1024 个 1×1 卷积滤波器)层。

def add_extras(cfg, i, batch_norm=False):
    # Extra layers added to VGG for feature scaling
    layers = []
    in_channels = i
    flag = False
    for k, v in enumerate(cfg):
        if in_channels != 'S':
            if v == 'S':
                layers += [
                    nn.Conv2d(in_channels, cfg[k + 1],
                        kernel_size=(1, 3)[flag], stride=2,
                        padding=1)]
            else:
                layers += [
                   nn.Conv2d(
                     in_channels, v, kernel_size=(1, 3)[flag])]
            flag = not flag
        in_channels = v
    return layer

额外层的构建使用一个旋转的 3x3 和 1x1 内核大小,可选的“S”标志表示stride=2padding=1,正如我们已经提到的。

我们已经讨论了网络结构。现在是时候继续实际预测/检测物体的类别和位置了。

预测方案

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Figure taken from the original paper

SSD 的一个关键概念是将神经网络中的中间层作为特征图。然后,它对要素地图运行 3x3 卷积过滤器,对默认框(Python 代码中的先前框)进行分类和预测偏移。每个位置有 4 或 6 个相应的默认框。自然地,较低层中的默认框较小,因为较低层捕获了输入图像的更精细的细节。

对于每个默认框,我们预测:

  1. 它属于某一类的概率
  2. 默认框中心的 x 和 y 偏移量
  3. 宽度和高度缩放到默认框的宽度和高度

中的默认框设置 ssd.py :

mbox = {
    # number of boxes per feature map location    
    '300': [4, 6, 6, 6, 4, 4],  
    '512': [],
} def multibox(vgg, extra_layers, cfg, num_classes):
    loc_layers = []
    conf_layers = []
    vgg_source = [24, -2]
    for k, v in enumerate(vgg_source):
        loc_layers += [
            nn.Conv2d(vgg[v].out_channels,
                      cfg[k] * 4, kernel_size=3, padding=1)]
        conf_layers += [
            nn.Conv2d(vgg[v].out_channels,
                      cfg[k] * num_classes, kernel_size=3,
                      padding=1)]
    for k, v in enumerate(extra_layers[1::2], 2):
        loc_layers += [
            nn.Conv2d(v.out_channels, cfg[k]
                      * 4, kernel_size=3, padding=1)]
        conf_layers += [
            nn.Conv2d(v.out_channels, cfg[k]
                      * num_classes, kernel_size=3, padding=1)]
    return vgg, extra_layers, (loc_layers, conf_layers) def build_ssd(phase, size=300, num_classes=21):
    if phase != "test" and phase != "train":
        print("Error: Phase not recognized")
        return
    if size != 300:
        print("Error: Sorry only SSD300 is supported currently!")
        return
    return SSD(
        phase, *multibox(vgg(base[str(size)], 3),
                         add_extras(extras[str(size)], 1024),
                         mbox[str(size)], num_classes),     
        num_classes
    )

SSD 使用 VGG 模型中的两个层— Conv4_3 和 Conv7/FC7,它们对应于层索引 24 和-2(即 relu 激活之前)。这种获得层次的方式有点不靠谱。如果我们决定在 VGG 构造中使用 use batch_norm=True,多框构造将会得到错误的层。额外的层也应该如此,但事实上batch_norm=True甚至还没有在add_extras()中实现。

对于额外的图层,我们在每两层中使用第二层作为特征地图。一个奇怪的部分是,因为最后一层 Conv11_2 具有形状(256,1,1),所以 3x3 卷积不是真正必要的。我猜这只是为了代码结构的简单。

注意,每个默认盒子应该有num_class + 4 (x,y,w,h)个输出。

锻炼

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Table taken from the original paper

尝试验证 SSD300 中默认盒子的数量(实现的那个)。

解决办法

  1. Conv4_3: 38 * 38 * 4 = 5776
  2. Conv7: 19 * 19 * 6 = 2166
  3. Conv8_2: 10 * 10 * 6 = 600
  4. Conv9_2: 5 * 5 * 6 = 150
  5. Conv10_2: 3 * 3 * 4 = 36
  6. Conv11_2: 4

总计:5776+ 2166 + 600 + 150 + 36 + 4 = 8732

请注意,此计算包括填充单元格中的默认框,这些默认框将始终为零,因此基本上是无用的框。

附加练习:计算 SSD300 中有效默认框的数量。

待续

我们仍然没有讨论如何将这些默认框映射回输入图像中的实际位置,如何挑选与地面事实相匹配的正确默认框,以及如何构造损失函数来训练网络。这些问题将在下一篇文章中讨论。

(2017/07/28 更新:以下是该系列第二部的和第三部的链接。)

(2018/07/12 更新:有人私下问了我一个有趣的问题。在此人的允许下,该问答被转贴于此:

问:我试图阅读纸质 VGG-16 和固态硬盘,到处都提到固态硬盘使用 VGG-16 架构,但原始纸张中的固态硬盘架构图像从尺寸(38x38x512)开始,但 VGG-16 架构中唯一可用的尺寸是(224x224x64)、(112x112x128)、(56x56x256)等等,但没有它的(38 X 38 X 512)。

答:注意 VGG16 的(官方)输入图像尺寸是 224,SSD 的是 300。对于 224,特征映射如你所说演化为(224,224,64),(112,112,128),(56,56,256)和(28,28,512)。但如果将(300,300,3)图像输入放入 VGG16 架构。特征映射演变为(300,300,64),(150,150,128),(75,75,256),(38,38,512)。)

[学习笔记]带 Pytorch 的单次多盒检测器—第 2 部分

原文:https://towardsdatascience.com/learning-note-single-shot-multibox-detector-with-pytorch-part-2-dd96bdf4f434?source=collection_archive---------1-----------------------

平铺和匹配策略

在上一篇中,我们讨论了 SSD 的网络结构和预测方案。现在,我们继续将默认框和基本事实结合起来,这样就可以确定预测的质量(并通过训练进行改进)。

(提醒:本文使用的 SSD 纸py torch 实现

将默认框映射到输入图像上的坐标

data/config.py 中预先计算并硬编码了每个特征映射的默认框的参数:

#SSD300 CONFIGS                      
# newer version: use additional conv11_2 layer as last layer before multibox layers                       
v2 = {                           
    'feature_maps' : [38, 19, 10, 5, 3, 1],
    'min_dim' : 300,                                                    
    'steps' : [8, 16, 32, 64, 100, 300],                                                   
    'min_sizes' : [30, 60, 111, 162, 213, 264],                                                   
    'max_sizes' : [60, 111, 162, 213, 264, 315],                                                   
    'aspect_ratios' : [[2], [2, 3], [2, 3], [2, 3], [2], [2]],                                                   
    'variance' : [0.1, 0.2],                                                   
    'clip' : True,                                                   
    'name' : 'v2',                       
}

实际的映射发生在层/函数/prior_box.py (P.S .默认框在实现中称为 prior boxed):

from itertools import product as productclass PriorBox(object):
    def __init__(self, cfg):
        super(PriorBox, self).__init__()
        # self.type = cfg.name
        self.image_size = cfg['min_dim']
        self.variance = cfg['variance'] or [0.1] […] for v in self.variance:
            if v <= 0:
                raise ValueError(
                    'Variances must be greater than 0') def forward(self):
        mean = []
        if self.version == 'v2':
            for k, f in enumerate(self.feature_maps):
                for i, j in product(range(f), repeat=2):
                    f_k = self.image_size / self.steps[k]
                    # unit center x,y
                    cx = (j + 0.5) / f_k
                    cy = (i + 0.5) / f_k # aspect_ratio: 1
                    # rel size: min_size
                    s_k = self.min_sizes[k]/self.image_size
                    mean += [cx, cy, s_k, s_k] # aspect_ratio: 1
                    # rel size: sqrt(s_k * s_(k+1))
                    s_k_prime = sqrt(
                        s_k * (self.max_sizes[k]/self.image_size))
                    mean += [cx, cy, s_k_prime, s_k_prime] # rest of aspect ratios
                    for ar in self.aspect_ratios[k]:
                        mean += [
                            cx, cy, s_k*sqrt(ar), s_k/sqrt(ar)]
                        mean += [
                            cx, cy, s_k/sqrt(ar), s_k*sqrt(ar)]

        […]        # back to torch land
        output = torch.Tensor(mean).view(-1, 4)
        if self.clip:
            output.clamp_(max=1, min=0)
        return output

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Layout of the four default boxes (from original paper)

(ITER tools . product创建输入可迭代对象的笛卡尔积。所以 product(range(4),repeat=2)得出(0,1,2,3)和(0,1,2,3)之间的所有组合,即(0,0),(0,1) …,(3,2),(3,3)。)

以第一张特征图(38x38)为例。f_k=300/8=37.5i+0.5j+0.5的范围从 0.537.5 。所以中心点坐标 cxcy 转化为(0.0133,0.0133),(0.0133,0.04) …,(1,0.9733),(1,1)。请注意,代码将坐标归一化为(0,1),并且记住大多数特征图都是零填充的(最外面的单元总是零)。可以自己验证一下倒数第二个(未填充)要素图中最外面的中心点离 0 和 1 有一点距离。并且最后的特征图只有一个中心点正好位于(0.5,0.5)。

现在我们有了每个默认框的中心点。接下来我们要计算宽度和高度。有六种默认的方框布局:

  1. 尺寸 (s_k,s_k) 的小方块
  2. 大小为 (sqrt(s_k * s_(k+1))、sqrt(s_k * s_(k+1))) 的大正方形
  3. 尺寸为 1:2 的矩形 (s_k * 0.7071,s_k * 1.414)
  4. 2:1 矩形尺寸 (s_k * 1.414,s_k * 0.7071)
  5. 尺寸为 (s_k * 0.5774,s_k * 1.7321) 的 1:3 矩形
  6. 3:1 大小的矩形 (s_k * 1.7321,s_k * 0.5774)

对于具有 4 个默认框的要素地图,仅使用前四种布局。矩形的面积与小正方形的面积相同。这和上图不一样,上图面积好像和大正方形一样。

s_k 来自以下公式,第一个特征图除外:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Formula (4) from the original paper

默认框实际上是根据经验设计的,如论文中所述:

在实践中,还可以设计默认框的分布,以最适合特定的数据集。如何设计最优的镶嵌也是一个公开的问题。

因此,您可以根据自己的需要自由修改 prior_box.py

找到最符合实际情况的默认框

这就是所谓的“文中匹配策略”。这个想法非常简单——如果任何一对基础真值框和默认框的 Jaccard overlap 大于一个阈值(0.5),那么它们就被认为是匹配的。在(希望)简单的英语中,如果重叠区域大于两个盒子覆盖区域的一半,这就是匹配。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

The intersection need to be larger than half of the union. (Image from Wikipedia)

相关代码位于 layers/box_utils.py :

def intersect(box_a, box_b):
    """ We resize both tensors to [A,B,2] without new malloc:
    [A,2] -> [A,1,2] -> [A,B,2]
    [B,2] -> [1,B,2] -> [A,B,2]
    Then we compute the area of intersect between box_a and box_b.
    Args:
      box_a: (tensor) bounding boxes, Shape: [A,4].
      box_b: (tensor) bounding boxes, Shape: [B,4].
    Return:
      (tensor) intersection area, Shape: [A,B].
    """
    A = box_a.size(0)
    B = box_b.size(0)
    max_xy = torch.min(box_a[:, 2:].unsqueeze(1).expand(A, B, 2),
                       box_b[:, 2:].unsqueeze(0).expand(A, B, 2))
    min_xy = torch.max(box_a[:, :2].unsqueeze(1).expand(A, B, 2),
                       box_b[:, :2].unsqueeze(0).expand(A, B, 2))
    inter = torch.clamp((max_xy - min_xy), min=0)
    return inter[:, :, 0] * inter[:, :, 1]

(tensor . unsqueeze在指定位置插入一个尺寸为 1 的新尺寸。应该相当于numpy . expand _ dimstensor . expand以记忆高效的方式扩展大小 1 维。当组合 时,它们在功能上等同于张量。重复 ,但是 张量。重复 创建一个新的张量。)

( )张量钳位 限制一个张量的最大值和最小值。应该相当于numpy . clip。)

作者巧妙的计算了交集。通过展开张量,我们现在能够在没有任何 for 循环的情况下,在一次运行中计算 box_a(基本事实)和 box_b(默认盒子)的每个组合的交集。

def jaccard(box_a, box_b):
    """Compute the jaccard overlap of two sets of boxes.  
       The jaccard overlap is simply the intersection over 
       union of two boxes.  Here we operate on ground truth 
       boxes and default boxes.
       E.g.:
          A ∩ B / A ∪ B = A ∩ B / (area(A) + area(B) - A ∩ B)
       Args:
          box_a: (tensor) Ground truth bounding boxes, 
                 Shape:    [num_objects,4]
          box_b: (tensor) Prior boxes from priorbox layers, 
                 Shape: [num_priors,4]
       Return:
          jaccard overlap: (tensor) 
                           Shape: [box_a.size(0), box_b.size(0)]
    """
    inter = intersect(box_a, box_b)
    area_a = ((box_a[:, 2] - box_a[:, 0]) *
              (box_a[:, 3] - 
               box_a[:, 1])).unsqueeze(1).expand_as(inter)
    area_b = ((box_b[:, 2] - box_b[:, 0]) *
              (box_b[:, 3] - 
               box_b[:, 1])).unsqueeze(0).expand_as(inter)  
    union = area_a + area_b - inter
    return inter / union  # [A,B]

在这里,作者使用同样的技巧来计算每个盒子的面积,然后得到并集。

def match(threshold, truths, priors, variances, 
          labels, loc_t, conf_t, idx):
    """Match each prior box with the ground truth box of 
       the highest jaccard overlap, encode the bounding boxes,
       then return the matched indices corresponding to both 
       confidence and location preds.

       Args:
         threshold: (float) The overlap threshold 
                    used when mathing boxes.
         truths: (tensor) Ground truth boxes, 
                 Shape: [num_obj, num_priors].
         priors: (tensor) Prior boxes from priorbox layers, 
                 Shape: [n_priors,4].
         variances: (tensor) Variances corresponding 
                    to each prior coord,
                    Shape: [num_priors, 4].
         labels: (tensor) All the class labels for the image,
                 Shape: [num_obj].
         loc_t: (tensor) Tensor to be filled w/ endcoded 
                location targets.
         conf_t: (tensor) Tensor to be filled w/ matched 
                 indices for conf preds.
         idx: (int) current batch index
       Return:
         The matched indices corresponding to 
         1)location and 2)confidence preds.
    """
    # jaccard index
    overlaps = jaccard(
        truths,
        point_form(priors)
    )
    # (Bipartite Matching)
    # [num_objects, 1] best prior for each ground truth
    best_prior_overlap, best_prior_idx = overlaps.max(1)
    # [1, num_priors] best ground truth for each prior
    best_truth_overlap, best_truth_idx = overlaps.max(0)
    best_truth_idx.squeeze_(0)
    best_truth_overlap.squeeze_(0)
    best_prior_idx.squeeze_(1)
    best_prior_overlap.squeeze_(1)
    # ensure best prior    
    best_truth_overlap.index_fill_(0, best_prior_idx, 2)     
    for j in range(best_prior_idx.size(0)):
        best_truth_idx[best_prior_idx[j]] = j
    # Shape: [num_priors,4]
    matches = truths[best_truth_idx] 
    # Shape: [num_priors]         
    conf = labels[best_truth_idx] + 1
    # label as background
    conf[best_truth_overlap < threshold] = 0  
    loc = encode(matches, priors, variances)
    # [num_priors,4] encoded offsets to learn
    loc_t[idx] = loc    
    # [num_priors] top class label for each prior
    conf_t[idx] = conf

(tensor . max和 Tensor.min 在传递一个 *dim* 参数时返回两个张量:1。沿指定轴的实际最大/最小值。2.沿该轴的最大/最小值的索引)

(Tensor.squeeze _是 tensor . squeeze 的就地版本,返回一个去掉了所有尺寸为 1 的维度的张量。)

(tensor . index _ fill _用传递的索引值填充原始张量的元素)

还记得我们从那里得到的 prior_box.py 是(cx,cy,w,h)格式吗?这里我们用point_from将其转换成(xmin,ymin,xmax,ymax)格式。为了节省空间,代码没有公布(在这里找到)。

这部分代码可能是最令人困惑的:

# ensure best prior    
best_truth_overlap.index_fill_(0, best_prior_idx, 2)     
for j in range(best_prior_idx.size(0)):
    best_truth_idx[best_prior_idx[j]] = j

张量best _ prior _ idx包含每个基础事实框的最佳匹配默认框的索引。所以第一行代码要做的是确保每个基本事实框至少有一个默认框通过了阈值。

for 循环将变化从第一行传播回张量 best_truth_idx ,,该张量包含每个默认框的最佳匹配基础真值框的索引。这种循环的效果是,当存在更需要它的另一个基本事实时,迫使先前的框放弃原始的最佳匹配基本事实(否则没有用于该基本事实的默认框)。

请注意,我们将每个默认框与一个真实背景相匹配,并为所有最大 Jaccard 重叠小于阈值(即背景)的默认框分配一个特殊的标签/类别零*。***

有一个encode函数将匹配的真实和默认框对转换成损失函数理解的格式。损失函数将在下一篇文章中讨论。

待续

我们讨论了如何将缺省框映射到实际坐标,以及如何匹配基础真值框和缺省框。这比我预期的要长,所以将会有第 3 部分讨论目标函数,最后是如何在测试阶段预测/检测。

(2017/07/28 更新:这里是该系列第三部的链接)

[学习笔记]带 Pytorch 的单次多盒检测器—第 3 部分

原文:https://towardsdatascience.com/learning-note-single-shot-multibox-detector-with-pytorch-part-3-f0711caa65ad?source=collection_archive---------3-----------------------

训练目标和推理

(提醒:本文使用的 SSD 论文py torch 实现。还有,第系列的第一和第系列的第二部分。)

训练目标/损失函数

每个深度学习/神经网络都需要一个可微分的目标函数来学习。在将基础事实和默认框配对,并将剩余的默认框标记为背景之后,我们准备好制定 SSD 的目标函数:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Overall Objective — Formula (1) from the original paper

这个目标函数有两个部分:

  1. 置信度损失:模型预测每个对象的类别有多准确
  2. 局部化损失:模型创建的边界框离地面真实框有多近。

信心丧失

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Confidence Loss — formula (3) from the original paper

这是实际标签和预测标签之间的简单的 softmax 损失函数。当第 i 个默认框与第 j 个类别 p 的第 1 匹配时。注意,有一个特殊的类别对应于背景框(没有地面真相匹配)。背景框被视为 ,并且如我们稍后将看到的,被下采样以避免高度不平衡的训练数据集。

本地化损失

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Localization Loss— Formula (2) from the original paper

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Smooth L1 loss function from Fast R-CNN paper

定位损失仅在 盒上计算(具有匹配接地真值的盒)。它计算相对于中心点坐标的正确偏移和预测偏移之间的差异,以及相对于宽度和高度的正确比例和预测比例。消除绝对差异。

偏移和比例的差异根据默认框的宽度和高度进行归一化,并且比例在进行差异计算之前进行对数缩放。

代码

来自层/模块/multibox_loss.py :

def forward(self, predictions, targets):
    """Multibox Loss
       Args:
         predictions (tuple): A tuple containing loc 
                              preds, conf preds,
                              and prior boxes from SSD net.
           conf shape:
               torch.size(batch_size,num_priors,num_classes)
           loc shape: torch.size(batch_size,num_priors,4)
               priors shape: torch.size(num_priors,4) ground_truth (tensor): Ground truth boxes and 
                                labels for a batch,
             shape: [batch_size,num_objs,5] 
                    (last idx is the label).
    """
    loc_data, conf_data, priors = predictions
    num = loc_data.size(0)
    priors = priors[:loc_data.size(1), :]
    num_priors = (priors.size(0))
    num_classes = self.num_classes # match priors (default boxes) and ground truth boxes
    loc_t = torch.Tensor(num, num_priors, 4)
    conf_t = torch.LongTensor(num, num_priors)
    for idx in range(num):
        truths = targets[idx][:,:-1].data
        labels = targets[idx][:,-1].data
        defaults = priors.data
        match(self.threshold,truths,defaults,
              self.variance,labels,loc_t,conf_t,idx)
    if self.use_gpu:
        loc_t = loc_t.cuda()
        conf_t = conf_t.cuda()
    # wrap targets
    loc_t = Variable(loc_t, requires_grad=False)
    conf_t = Variable(conf_t,requires_grad=False) pos = conf_t > 0
    num_pos = pos.sum() # Localization Loss (Smooth L1)
    # Shape: [batch,num_priors,4]
    pos_idx = pos.unsqueeze(pos.dim()).expand_as(loc_data)
    loc_p = loc_data[pos_idx].view(-1,4)
    loc_t = loc_t[pos_idx].view(-1,4)
    loss_l = F.smooth_l1_loss(loc_p, loc_t, size_average=False) # Compute max conf across batch for hard negative mining
    batch_conf = conf_data.view(-1,self.num_classes)
    loss_c = log_sum_exp(batch_conf) - batch_conf.gather(
                 1,   conf_t.view(-1,1)) # Hard Negative Mining
    loss_c[pos] = 0 # filter out pos boxes for now
    loss_c = loss_c.view(num, -1)
    _,loss_idx = loss_c.sort(1, descending=True)
    _,idx_rank = loss_idx.sort(1)
    num_pos = pos.long().sum(1)
    num_neg = torch.clamp(
        self.negpos_ratio*num_pos, max=pos.size(1)-1)
    neg = idx_rank < num_neg.expand_as(idx_rank) # Confidence Loss Including Positive and Negative Examples
    pos_idx = pos.unsqueeze(2).expand_as(conf_data)
    neg_idx = neg.unsqueeze(2).expand_as(conf_data)
    conf_p =  conf_data[
       (pos_idx+neg_idx).gt(0)].view(-1,self.num_classes)
    targets_weighted = conf_t[(pos+neg).gt(0)]
    loss_c = F.cross_entropy(
        conf_p, targets_weighted, size_average=False) # Sum of losses: L(x,c,l,g) = (Lconf(x, c) + αLloc(x,l,g)) / N
    N = num_pos.data.sum()
    loss_l/=N
    loss_c/=N
    return loss_l,loss_c

挺长的,我们来分解一下:

# match priors (default boxes) and ground truth boxes
loc_t = torch.Tensor(num, num_priors, 4)
conf_t = torch.LongTensor(num, num_priors)
for idx in range(num):
    truths = targets[idx][:,:-1].data
    labels = targets[idx][:,-1].data
    defaults = priors.data
    match(self.threshold,truths,defaults,
          self.variance,labels,loc_t,conf_t,idx)
[...]
# wrap targets
loc_t = Variable(loc_t, requires_grad=False)
conf_t = Variable(conf_t,requires_grad=False)

num对应批量大小。idx参数被传递给match()以让match知道要写哪一行。

(设置 requires_grad=False 表示我们不需要在反向过程中计算这些变量的梯度。) 参考

*pos = conf_t > 0
num_pos = pos.sum()# Localization Loss (Smooth L1)
# Shape: [batch,num_priors,4]
pos_idx = pos.unsqueeze(pos.dim()).expand_as(loc_data)
loc_p = loc_data[pos_idx].view(-1,4)
loc_t = loc_t[pos_idx].view(-1,4)
loss_l = F.smooth_l1_loss(loc_p, loc_t, size_average=False)*

(tensor . view等价于numpy . shape,返回一个数据相同但大小不同的新张量。Tensor.view_as 的工作方式相同,但会自动将目标形状设置为传递的张量的形状。)

这部分计算本地化损失。

记住类标签 0 对应背景(负框),我们可以用> 0找到正框。pos扩展为(num,num_priors,4)用于选择阳性框。.view(-1, 4)做的是将张量从(num,num_priors,4)展平到(num * num_priors,4)。F出自import torch.nn.functional as F

*# Compute max conf across batch for hard negative mining
batch_conf = conf_data.view(-1,self.num_classes)
loss_c = log_sum_exp(batch_conf) - batch_conf.gather(
                 1, conf_t.view(-1,1))# Hard Negative Mining
loss_c[pos] = 0 # filter out pos boxes for now
loss_c = loss_c.view(num, -1)
_, loss_idx = loss_c.sort(1, descending=True)
_, idx_rank = loss_idx.sort(1)
num_pos = pos.long().sum(1)
num_neg = torch.clamp(
    self.negpos_ratio*num_pos, max=pos.size(1)-1)
neg = idx_rank < num_neg.expand_as(idx_rank)*

*(*tensor . gather沿 dim 指定的轴收集值。)

*(*tensor . sort类似于 Tensor.min 和 Tensor.max,它返回两个张量:1。已排序的值。2.排序值的原始索引)

对于置信损失 SSD 使用一种称为 硬负挖掘 的技术,即选择最困难的负框(它们具有更高的置信损失),因此负对正比率最多为 3:1。

log_sum_exp来自 layers/box_utils.py 。它计算log(c)的分母部分。batch_conf.gather计算分子部分,其中只有真实标签的预测概率是重要的。

该代码使用两种排序来查找每个盒子的等级。首先获取排序索引,然后获取排序索引的排序索引作为秩。num_negnum_priors — 1夹住,看起来怪怪的。实际的负数num_prior — num_pos似乎更合理。

*# Confidence Loss Including Positive and Negative Examples
pos_idx = pos.unsqueeze(2).expand_as(conf_data)
neg_idx = neg.unsqueeze(2).expand_as(conf_data)
conf_p =  conf_data[
      (pos_idx+neg_idx).gt(0)].view(-1,self.num_classes)
targets_weighted = conf_t[(pos+neg).gt(0)]
loss_c = F.cross_entropy(
          conf_p, targets_weighted, size_average=False)*

这部分应该很简单。收集预测和真实标签,然后传递给 cross_entropy 函数,得到总损失(还没有平均)。

*# Sum of losses: L(x,c,l,g) = (Lconf(x, c) + αLloc(x,l,g)) / N
N = num_pos.data.sum()
loss_l /= N
loss_c /= N
return loss_l, loss_c*

最后,计算两次损失的平均值,然后返还。现在我们有了训练网络所需的一切。

推理

训练完网络后,是时候使用我们的检测器了。SSD 设计的一个特殊问题是,如果超过阈值,我们可以将多个默认框匹配到一个真实框。因此,在预测时,我们可能会预测一个对象周围的多个高度重叠的框。这通常不是目标检测算法的期望输出。我们需要做一些后期处理。

SSD 使用的技术被称为非最大抑制(nms) 。基本思想是迭代地将最有把握的盒子添加到最终输出中。如果候选框与最终输出中同类的任何框高度重叠(Jaccard 重叠高于 0.45),则该框将被忽略。它还将每个图像的总预测盒数限制在 200 个。

实现(nms 函数)位于 layers/box_utils.py 。它有一些新的东西,如 Tensor.numeltorch.index_selectout 参数。但是您现在应该对工作流程相当熟悉了,所以我不会在这里详细分析代码。

谢谢大家!

就是这样!非常感谢您通读整个系列。有段时间没写过这么长的学习笔记/教程了,再来一遍感觉棒极了!

这个系列的目的真的是强迫自己钻到乱七八糟的细节里去,去理解到底是怎么回事。如果能对你有所帮助,我会很高兴。另外,如果我做错了什么或者错过了什么重要的事情,请随时告诉我。

[学习笔记]用于多标签文本分类的 StarSpace

原文:https://towardsdatascience.com/learning-note-starspace-for-multi-label-text-classification-81de0e8fca53?source=collection_archive---------1-----------------------

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

StarSpace 是一个雄心勃勃的模型,试图解决一系列与实体嵌入相关的问题。它由脸书人工智能研究所(FAIR)创建并开源。我还没有在论文中读到模型的细节,但是很容易假设它扩展了 FAIR 之前的文本嵌入库 fastText 。StarSpace 旨在成为一个直接有效的强基线,也就是说,你为新数据集或新问题训练的第一个模型。

在这篇文章中,我将写下我是如何(试图)让 StarSpace 处理来自 Kaggle 的有毒评论分类挑战的数据集的。该数据集表示多标签文本分类问题,即,可以将多个标签分配给单个评论。由于 fastText 不完全支持多标签分类,我认为 StarSpace 可能是一个不错的选择。

剧透/TL;博士;医生

我发现 StarSpace 在当前状态下存在两个主要问题,使其无法作为该数据集的基线:

  1. 没有predict命令:目前只提供test,给出描述性的模型评估。额外的工作需要你自己完成,以获得每个评论的标签概率的清晰输出。
  2. 评估度量是不可定制的:由于缺乏清晰的预测输出,我们依赖于来自test命令的模型评估。但是我看不出有什么方法可以让它显示我们关心的这个数据集的列级平均日志损失。

另外,StarSpace 的文档也不是很全面。这也是为什么我会写这篇文章的原因。

安装 StarSpace

Starspace 是用 C++写的,要自己搭建。在我的 Linux Mint 18.3 环境中,这非常简单。只需克隆 Git repo 并运行make:

git clone https://github.com/facebookresearch/Starspace.git
cd Starspace
make

将编译好的可执行文件starspace复制到你的路径中的某个地方(我个人使用~/bin/

在其他环境中,你可能需要跳过额外的关卡来满足需求。请查看链接以获取进一步的说明。

Python 环境

  • Python 3.6
  • pandas 0.22.0,joblib 0.11,tqdm 4.19.5(使用了非常基础的 API,所以确切的版本应该无关紧要。如果你遇到任何问题,请在这篇文章发表后检查是否有任何重大更新。)
  • 空间 2.0.5
  • sci kit-学习 0.19.1

准备数据集

不言而喻,您需要首先将数据集下载到您的计算机上。我通常将数据集放在项目根目录下的data子文件夹中,并将从原始数据集派生的所有内容放在cache子文件夹中。我们将在下面使用相同的设置。

下一步是清理和标记注释。在这里,我使用了来自 spacy,的英文分词器,删除换行符和一些其他标点符号,并将注释精简到 20,000 个字符。(清洗方案通常依赖于数据集。对于这个数据集,肯定有比这篇文章中简单的方案更好的方案。例如,你可以过滤掉停用词。)

在注释被标记化之后,我们将这些标记与它们相关联的标签结合起来,并以 StarSpace 可以识别的格式保存它们(这里我们使用 fastText 格式)。

我们使用 25%的训练数据集作为验证。结果分别保存到cache/train.txtcache/val.txt。注意因为我还没有找到一种容易提取预测的方法,所以这里不处理测试数据集。

快速文本格式非常简单。在连续的标记之间放置一个空格,每行一个注释/实例,并在末尾放置标签。标签用数字编码,并为无毒的评论创建一个虚拟标签(StarSpace 不接受空标签列表)。

例如,这是训练数据集中的第一条注释:

22256635,"Nonsense?  kiss off, geek. what I said is true.  I'll have your account terminated.",1,0,0,0,0,0

处理后,它变成:

Nonsense ? kiss off , geek . what I said is true . I 'll have your account terminated . __label__0

训练和评估模型

要训练模型,请在命令行中运行以下命令:

starspace train -ngrams 2 -minCount 10 -thread 4 -trainFile cache/train.txt -model cache/starspace.model

该模型使用 unigram 和 bigram,要求一个令牌至少出现 10 次才被考虑,并使用 4 个线程。更多参数可通过starspace -h找到。

StarSpace 将模型保存到cache/starspace.model,将文字嵌入和标签嵌入向量保存到cache/starspace.model.tsv。您可以分析或可视化这些嵌入向量,以获得进一步的见解。

要使用验证数据集评估模型,请运行以下命令:

starspace test -testFile cache/val.txt -model cache/starspace.model -predictionFile cache/starspace.pred

除了命令行输出之外,它还将逐例评估写入cache/starspace.pred。一个例子:

Example 68:
LHS:
IT 'S HER QUOTE . WHAT CAN'T YOU UNDERSTAND ? Here is the official press release Now , please , can we stop this nonsense ? 
RHS: 
__label__0 
Predictions: 
(--) [0.542934] __label__6 
(--) [0.055087] __label__4 
(--) [0.0467122]        __label__2 
(++) [-0.0127831]       __label__0 
(--) [-0.23463] __label__1

另一个例子:

Example 116:
LHS:
STOP , you had better stop putting all that stupid junk on my IP page . read it . you 'll see what i 'll do if you do it again . 
RHS: 
__label__0 
Predictions: 
(++) [0.529969] __label__0 
(--) [0.416814] __label__2 
(--) [0.388696] __label__4 
(--) [0.34913]  __label__3 
(--) [0.240833] __label__1

注意,数据集中的大多数评论都是没有毒性的( __label__6 ),所以我在这里真的是精挑细选了一些例子。

分配给每个标签的值的含义不清楚。我想答案可以在报纸上找到。

包扎

不幸的是,StarSpace 还没有准备好作为有毒评论数据集的基线。这篇文章尽我们所能记录了所需的步骤,以供将来参考。希望星际空间将继续发展,并真正为生产做好准备。我们会回来买更多的。

空腹学习:加州奥兰治县学校免费餐计划的数据研究

原文:https://towardsdatascience.com/learning-on-an-empty-stomach-data-study-on-school-free-meal-programs-in-orange-county-california-bd61c6ea3db3?source=collection_archive---------9-----------------------

夹在洛杉矶和圣地亚哥县之间的加利福尼亚州奥兰治县,可能是以美丽的海滩、职业运动队和几个电视节目的所在地而闻名。作为一个终身居民,很容易看到某些迷人的看法可能会推广到整个县,但整个画面远远超出了电视上看到的。

老实说,我是带着一种扭曲的世界观长大的,我的整个童年都是在尔湾度过的,那里被联邦调查局称为美国最安全的大城市,也被当地人称为泡沫。直到我在加州大学富勒顿分校上大学期间,开始在各种学校、施粥场和无家可归者收容所做志愿者,我的观点才发生转变。在此期间,我在大学附近的多所小学做志愿者。离我崭新的、最先进的商学院仅一英里的地方是一所小学,学生们在教室里上课,教室里没有空调,地板是泥土的,而不是地毯。我志愿参加的大多数教室几乎都有每个学生参加免费早餐计划,低收入家庭的学生排队领取他们早上分配的水果、蔬菜和牛奶(装在塑料袋里,必须用吸管戳)。这不是我从小到大习惯的事情,但很明显这是这里的例行公事,几个孩子贪婪地吃着他们的食物,好像他们从前一天就没有吃过东西。

这些经历与我自己的小学经历大相径庭。由于我在我访问过的少数几所学校中看到了如此巨大的差异,我想看看一些数据,看看所有 OC 学校的小学经历有多大的差异。在这份报告中,我把重点放在有资格享受免费餐计划的学生的百分比(T2)上作为我的变量,因为学生的资格是由他们家庭相对于贫困线的收入决定的。

为了设置场景,让我们来看看奥兰治县与加州其他县相比的情况:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

在 58 个加州县中,奥兰治县公立学校学生享受免费餐的比例排在倒数第 18 位(仍为 39.9%)。虽然奥兰治县公立学校有资格享受免费餐的学生比例低于平均水平,但 OC 各学区之间的标准偏差很高(见下文)。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

当查看每个加州县的标准偏差时,每个县的个别学校之间的免费餐计划合格比率的可变性,奥兰治县的可变性是显而易见的。奥兰治县的标准差为 28.8%,是加州所有县中标准差第二高的县。关于标准差,奥兰治县夹在阿拉米达县和康特拉科斯塔县之间,这两个县都是硅谷北部的相邻县。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

看一下上面的图,其中三角形代表每个县的每个公立学校区,您可以看到 Orange County 在中线(两个蓝色阴影框之间的黑线)和第 75 百分位标记(由浅蓝色框右侧的黑线表示)之间存在明显的差距。当你看看其他人口稠密的地区,如洛杉矶和圣地亚哥,学校在整个范围内的分布相对均匀,不像奥兰治县。对于奥兰治县学区来说,对免费餐的依赖程度高和低的学区之间,几乎就像有一条想象中的边界。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

泡沫的大小:学生注册的规模

泡泡的颜色:橙色越深=有资格享受免费餐的学生比例越高

列出的百分比:有资格享受免费餐的学生百分比

在 OC 最大的学区中,圣安娜拥有压倒性的高比率,80.3%的学生有资格享受免费餐。另一方面,右下方可以看到我的家乡尔湾市的失业率非常低,只有 10.3%。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

这张图表显示,即使是最富裕的地区也有高度依赖免费和优惠膳食计划的学校。查看上图中的圆点,它们代表每个 OC 学区中有资格享受免费餐的学生比例最高的学校,您会发现圣安娜统一学校是享受免费餐计划的公立学校比例最高的学区(95.8%)。然而,最高值仅次于最高值的地区是 Placentia-yor ba Linda Unified(89.4%),Capistrano Unified (87.9%)紧随其后,位居第四。Placentia-Yorba Linda 和 Capistrano 的一些学校最依赖免费餐计划,尽管整个地区符合条件的学生比例中位数分别排名第 9 和第 6。这两个城市都是相对富裕的地区,约巴林达的家庭收入中值为 117,855 美元,T2 最近的一项研究将它列为全国第六富裕的城市,然而它仍然有一所对免费餐计划依赖程度最高的学校。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

这个问题也没有减少,看看每个 OC 学区,自 2012 年以来,免费餐有了大量增加。正如你在上面看到的,许多 OC 学区看到有资格享受免费餐的学生增加了,一些学区看到超过 75%的学校注册了免费餐资格的增加。

在研究和撰写这篇文章后,我的主要收获是,即使在一些看起来最迷人的地区,也有许多人需要帮助。任何地区都不能被忽视。这是我第一篇关于食品不稳定和贫困的数据文章,但我计划写更多。如果你有任何意见,额外的数据,或者想要合作,请随时联系我。这里有一份对抗饥饿的顶级慈善机构名单(我目前通过第二丰收食物银行橘子郡志愿参与“供养美国”)。

感谢您阅读我最新的数据帖子。作为一名产品营销和数据分析专业人士,我对数据支持的讲故事充满热情。这些数据新闻帖子是我将真实数据与我个人的不同兴趣整合起来的方式,这些兴趣包括从旅行和娱乐到经济和社会问题的任何事情。
如果您有任何评论、故事想法或预期的数据项目,请随时发送电子邮件至 dwpwriting <至> gmail < dot > com 或通过
LinkedIn 联系我。

为什么以及如何开展数据科学学习项目

原文:https://towardsdatascience.com/learning-projects-e831fa94f09f?source=collection_archive---------9-----------------------

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Stefan Steinbauer on Unsplash

有很多关于如何创建项目以建立数据科学组合的博客帖子。我推荐迈克尔·加拉尼克这首康纳·杜威的这首。不幸的是,这种方法现在对我不起作用,因为我的日常工作非常耗时。我需要根据不断变化的需求,在更小的副主题上更快地迭代。

我测试了许多不同的方法来实现这一点。我完成了几个 Udacity 纳米学位,完成了 Coursera 和 Udemy 的课程,参加了网络研讨会,读了一堆 O’Reilly 的书。需要明确的是:所有这些资源都可以为您提供支持,具体取决于您在数据科学之旅中的位置。然而,对我来说最有效的是学习项目。

学习项目是我为填补技能组合中的特定缺口而做的小型数据科学项目。它们不是为了给招聘人员或潜在雇主留下深刻印象。相反,他们为我提供了量身定制的挑战来提高我的能力。

在这篇博文中,我与你分享了我现在从想法选择到评估的过程。每次迭代之后,我都会不断地改进它,但是总的模式是成立的。我也给你一个我最近的学习项目作为一个切实的例子。

第一步:找到一个你关心的想法

学习项目的灵感到处都在等着。一位同事提到一个你不知道的概念。或者,你听播客,偶然发现一些东西。或者你第 1000 次谷歌某样东西,想把它记在脑子里。长话短说:想法是你的环境提供给你的,如果你有开放的心态

一旦你开始接触这些想法,你所需要的只是一个写下它们的地方。为此,我搭建了一个 Trello 板。我不认为有一个系统适合所有人,所以你可能需要做一些实验。但是,您的系统需要提供两件事情:

  1. 它必须随时可以被访问。
  2. 获得一个概述必须是简单的。

每当你有一个新的想法,添加一两句话作为一个新的项目来描述它。

当你准备好下一个项目时,检查你的清单。根据两个标准来标记想法:内在动机专业价值。如果你目前的工作需要掌握一些东西,那么这就是你的最高优先级。

这里有一点很重要:现在还不要考虑可行性或实际细节。总有办法调整一个想法。数据科学是创造解决方案,而不是过分强调问题。

我最近的一个学习项目开始于我路过一家电影院时,看到了最后的绝地的电影海报:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

当我看着这张海报的风格时,我想知道这部系列电影的前几部给了它多少设计灵感。由于我是一名数据科学家,所以没过多久,我就决定训练一个 CNN 对一张电影海报的十年进行分类。

第二步:做一个快速的可行性检查

数据可用性是所有数据科学的瓶颈。学习项目在这里也不例外。当你决定了你的想法,检查通常的数据来源,看看是否有足够的数据可用。有三种可能的结果:

  1. 你需要的确切数据已经准备好了。如果是这样的话,对让它变得容易理解的人说声谢谢。享受这一刻。
  2. 您找到了与您需要的相似但不完全符合您想法的数据。在这种情况下,考虑一下你是否能在保持核心动机不变的情况下调整你的计划。
  3. **没有有用的数据源。**一般来说,回到你的清单,选择另一个项目。不要删除你的想法。它可能会激发你新的想法,你可能会发现一个新的角度,或者新的数据可能会在某个时候变得可用。

就我而言,我已经知道 Kaggle 上的电影数据集,所以我开始在那里搜索。幸运的是,这个数据集包含了一段时间内成千上万部电影海报的链接。

第三步:明确你的学习目标

import pandas as pd等等很容易让人马上开始,但是等等!你有一个想法,你知道有数据可以解决它。但是,你确定你想从中带走什么吗?换句话说:**退一步想想自己的学习目标。**要不要在 Pytorch 建立自己的第一个神经网络?您想了解特定类型数据的缺陷吗?要不要测试一下不同种类的超参数优化(不要脸的自我推销)?

如果你的想法与许多不同的学习目标有关,那就专注于对你来说最重要的那一部分。我在攻读博士学位期间学到了一条规则:要么专注于一个新论点、一个新数据集,要么专注于一种新方法。太多的活动部件使得很难得出正确的结论。同样的道理也适用于学习项目。

我的电影海报项目的目标是测试我建立一个从图片输入到预测输出的基本管道有多容易。换句话说,我的主要目标是进行自我评估,找出我需要克服的弱点。

第四步:专注于你的学习目标

从现在开始,没有明确的指导方针。然而,记住你的学习目标。例如,当你想比较你的神经网络的两个不同的激活函数时(另一个无耻的自我推销,不要在数据探索上花太多时间。

实事求是地说:把必要的和关键的任务分开。尽可能做好前面的工作,但不要在这里研究或尝试新事物。相反,把你的大部分时间集中在后面的任务上。再说一次,学习项目并不意味着成为你的正式投资组合的一部分。他们的工作是推动你在学习曲线上走得更远。

例子:电影海报按年代分类

我的重点是建立一个基本的 CNN 管道,所以我没有花太多时间准备数据。相反,我删除了所有缺少值的行,而没有考虑是否有系统的原因。我还删除了所有具有非唯一链接的行,没有进一步检查。

从剩余的 24,812 部电影中,我选择了 800 部电影用于训练,200 部电影用于测试,这是从 20 世纪 50 年代开始的 60 年间的事情。随后,我写了一些代码,将相关的电影海报下载到traintest文件夹中,每个十年都有子文件夹。我意识到有些文件是空的,就额外写了代码删除 0 KB 的文件。完成这些步骤后,我的模型只剩下不到 800/200 个文件:

Images in train-folder:
00s: 788
50s: 768
60s: 754
70s: 771
80s: 760
90s: 779
Images in test-folder:
00s: 198
50s: 194
60s: 187
70s: 192
80s: 199
90s: 197

为了准备模型构建的文件,我使用了来自keras.preprocessing.imageImageDataGenerator及其flow_from_directory方法。要了解更多细节,请看维贾雅布哈斯卡尔 J的这篇优秀的博客文章或 Keras 博客上的一个例子

接下来,我用 Tensorflow 后端在 Keras 构建了一个标准的 CNN 架构。唯一的变化是我使用了 SELUs 作为激活函数,而不是 ReLUs 来反映我当前的知识。

然后,我花足够的时间进行微调,以获得大约 44%的验证准确率:

Epoch 1/7
145/144 [==============================] - 134s - loss: 2.6112 - acc: 0.2073 - val_loss: 2.3751 - val_acc: 0.2202
Epoch 2/7
145/144 [==============================] - 127s - loss: 1.6243 - acc: 0.3422 - val_loss: 1.6827 - val_acc: 0.3393
Epoch 3/7
145/144 [==============================] - 126s - loss: 1.2459 - acc: 0.5397 - val_loss: 1.8159 - val_acc: 0.3102
Epoch 4/7
145/144 [==============================] - 125s - loss: 0.8281 - acc: 0.7190 - val_loss: 1.7473 - val_acc: 0.4087
Epoch 5/7
145/144 [==============================] - 125s - loss: 0.4775 - acc: 0.8527 - val_loss: 2.0787 - val_acc: 0.4233
Epoch 6/7
145/144 [==============================] - 127s - loss: 0.2678 - acc: 0.9153 - val_loss: 2.6315 - val_acc: 0.4105
Epoch 7/7
145/144 [==============================] - 129s - loss: 0.1877 - acc: 0.9412 - val_loss: 2.7076 - val_acc: 0.4430

这个模型将上面的海报归类为 100%来自 60 年代。

这是一个非常简短的总结,但我相信您已经看到了为什么这不是一个包含在数据科学产品组合中的好选择的许多原因。同样,这不是学习项目的目的!我实现了我的学习目标,因为我意识到了这样一个管道的哪些部分是我最需要做的(图像预处理和生成器方法)。现在我可以开始另一个学习项目,这个项目是为在下一次迭代中解决这些弱点而定制的。

你完成了一个学习项目——现在呢?

**首先恭喜自己!**您进一步拓展了数据科学知识的范围。更重要的是,你培养了一种不断学习和成长的态度。

第二,确保充分利用你的工作:

  1. 写下你可以毫无困难地做的事情。它将帮助你评估你现在作为一名数据科学家的地位。它也显示了当你开始时,你已经从后面走了多远。
  2. 在追求你的学习目标的同时,写下你学到的东西。你买了多少?你应用的核心概念和技能是什么?特别注意你完成了多少学习目标,以及它是否符合你的期望。调整你即将到来的项目。
  3. 写下你在这个学习项目中注意到的弱点。它将帮助你决定哪个想法是下一个学习项目的最佳选择。
  4. 重复。

你的学习方法是什么?请在评论和 Twitter 上告诉我什么对你有用,或者在LinkedIn上联系我。

感谢阅读!如果你喜欢这篇文章,留下一些吧👏🏻并在 LinkedIn 或 Twitter 上分享。再次感谢,让我们继续学习!

关于如何优化深度神经网络学习速率的初级读本

原文:https://towardsdatascience.com/learning-rate-a6e7b84f1658?source=collection_archive---------6-----------------------

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Victoire Joncheray on Unsplash

训练深度神经网络时的一个主要挑战是平衡最终解决方案的质量和达到最终解决方案所需的训练时间。学习率是优化这种平衡的最重要的超参数。

你可以认为小学习率和大学习率具有不同的个性:

  • 小学习率谨慎。也就是说,它使网络缓慢而小心地调整。
  • 学习率大就是浮躁。也就是说,它调整得很快,但可能会超调。

当你做深度学习时,你想让网络同时快速而精确地学习。在这篇文章中,我向你展示了三种不同的选择,在谨慎和浮躁之间找到平衡:

  1. 决定一个既不太低也不太高的学习率,即找到最佳的折衷。
  2. 一旦你接近一个最佳解决方案,在训练期间从高到低调整学习速率以减慢速度。
  3. 在高学习率和低学习率之间摇摆,创造一个混合体。

这篇文章是作为一个引子,并不涵盖细节。如果你想了解更多,我推荐 Pavel Surmenok 的这篇文章:

[## 估计深度神经网络的最佳学习速率

学习率是用于训练深度神经网络的最重要的超参数之一。

towardsdatascience.com](/estimating-optimal-learning-rate-for-a-deep-neural-network-ce32f2556ce0)

选择 1:折衷——固定学习率

最基本的方法是坚持默认值,并希望最好的结果。

第一个选项的更好实现是测试各种可能的值。根据损失的变化,你可以选择更高或更低的学习率。目标是找到仍能减少损失的最快速度。

鉴于这种选择的简单性,固定的学习率会让你走得比你预期的更远。然而,还有更好的选择。

选项 2:顺序——随着时间的推移,学习率降低

第二种选择是以高学习速率开始,以利用速度优势,然后切换到低学习速率,以优化结果。有两种主要的变化。

首先,你可以根据损失函数的变化来调整学习速率。也就是说,每当损失函数停止改进时,你就降低学习速率以进一步优化。

第二,您可以应用更平滑的函数形式,并根据训练时间调整学习速率。也就是说,学习率的降低与损失函数没有直接关系。

与固定学习率相比,这两种方法及其变体都是改进,因为它们结合了小学习率和大学习率的优点。然而,还有更大的改进余地。

选项 3:混合式学习率——走走停停

主要的想法是,由快转慢非常有帮助,我们应该在训练中不止一次地这样做。还有两个额外的优势:

  1. 跳回到高学习率有助于避免局部最优。
  2. 高学习率在穿过损失函数的平坦区域时更快。

综上所述,第三种选择是将第二种选择重复几次。

但是我们没有优化算法吗?

是的,因为最先进的优化算法,如亚当根据训练过程改变每个人体重的学习率。如果你想更多地了解亚当,我推荐这篇博文:

[## 深度学习的 Adam 优化算法简介

你的深度学习模型的优化算法的选择可能意味着良好结果之间的差异…

machinelearningmastery.com](https://machinelearningmastery.com/adam-optimization-algorithm-for-deep-learning/)

没有,因为即使是 Adam 也有两个与学习率相关的参数,分别是lr用于学习率和decay ( 参见 Keras 实现)。也就是说, Adam 需要一个学习速率来开始,以及它是否应该包括衰减函数的信息。如果你想使用这些参数,你需要考虑如何应用选项 1 和 2。

还有一种算法实现了选项 3。它被称为重启的随机梯度下降,并由马克·霍夫曼进行了精彩的解释:

[## 探索重新开始的随机梯度下降(SGDR)

这是我第一篇深度学习的博文。我在 2017 年 1 月左右开始了我的深度学习之旅,在我听说了…

medium.com](https://medium.com/38th-street-studios/exploring-stochastic-gradient-descent-with-restarts-sgdr-fa206c38a74e) 外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Jens Johnsson on Unsplash

你下一步应该做什么

我所知道的关于深度学习的最好的课程是由 fast.ai 公开提供的课程。还有同一个团队写的刚到 1.0 版本的 Python 包,如果你关心深度学习,到这里上第一堂课

总体来说,你对学习率和训练深度学习有什么看法?请在评论中或在 Twitter 上告诉我。我也很乐意在 LinkedIn 上联系。感谢阅读,留点👏🏻如果这对你有帮助,让我们继续学习吧!

学习率调度程序

原文:https://towardsdatascience.com/learning-rate-scheduler-d8a55747dd90?source=collection_archive---------10-----------------------

适应性学习率

在训练深度网络时,随着训练时期数量的增加,降低学习速率是有帮助的。这是基于直觉,即在高学习率的情况下,深度学习模型将拥有高动能。因此,它的参数向量会乱跳。因此,它不能停留在损失函数的更深和更窄的部分(局部最小值)。另一方面,如果学习速率非常小,那么系统的动能就会很低。因此,它会停留在损失函数的较浅和较窄的部分(假最小值)。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

上图描述了高学习率将导致向量在局部最小值附近的随机往复运动,而低学习率将导致陷入错误的最小值。因此,知道何时降低学习速度可能很难找到答案。

我们的实验基于**阶跃衰减的原理。**这里,我们每隔几个历元就用一个常数因子降低学习率。典型值可能是每 5 个时期将学习速率减少一半,或者每 20 个时期减少 0.1。这些数字很大程度上取决于问题的类型和模型。你在实践中可能看到的一个启发是,在以固定的学习速率训练时观察验证误差,并且每当验证误差停止改善时,以一个常数(例如 0.5)降低学习速率。

在实践中,步长衰减是首选,因为它更容易解释超参数,如衰减分数和以历元为单位的步长计时。此外,还发现它提供了学习率值的稳定性,这反过来有助于随机梯度下降显示出快速收敛和高成功率。

实验步骤

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

实验结果

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

源代码

[## shree 6791/深度学习

深度学习——这个知识库由 Shreenidhi Sudhakar 实施的深度学习项目组成。

github.com](https://github.com/shree6791/Deep-Learning/blob/master/CNN/Cats%20and%20Dogs/keras/src/Intern%20Task%203.ipynb)

深度学习的学习速率表和自适应学习速率方法

原文:https://towardsdatascience.com/learning-rate-schedules-and-adaptive-learning-rate-methods-for-deep-learning-2c8f433990d1?source=collection_archive---------0-----------------------

当训练深度神经网络时,随着训练的进行降低学习速率通常是有用的。这可以通过使用预定义的学习率计划自适应学习率方法来完成。在本文中,我在 CIFAR-10 上训练了一个卷积神经网络,使用不同的学习速率计划和自适应学习速率方法来比较它们的模型性能。

学习费率表

学习率时间表旨在通过根据预定义的时间表降低学习率来调整训练期间的学习率。常见的学习率时间表包括基于时间的衰减阶跃衰减指数衰减。为了说明的目的,我构建了一个在 CIFAR-10 上训练的卷积神经网络,使用具有不同学习速率调度的随机梯度下降(SGD)优化算法来比较性能。

恒定学习率

在 Keras 的 SGD optimizer 中,恒定学习率是默认的学习率计划。默认情况下,动量和衰减率都设置为零。选择正确的学习速度是很棘手的。在我们的例子中,通过实验学习率的范围,lr=0.1显示了相对较好的开始性能。这可以作为我们试验不同学习速度策略的基准。

keras.optimizers.SGD(lr=0.1, momentum=0.0, decay=0.0, nesterov=**False**)

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Fig 1 : Constant Learning Rate

基于时间的衰变

基于时间的衰减的数学形式是lr = lr0/(1+kt),其中lrk是超参数,t是迭代次数。查看 Keras 的源代码,SGD 优化器采用decaylr参数,并在每个时期以递减因子更新学习率。

lr *= (1\. / (1\. + self.decay * self.iterations))

动量是 SGD 优化器中的另一个参数,我们可以调整它以获得更快的收敛。与经典的 SGD 不同,动量法帮助参数向量以恒定的梯度下降在任何方向上建立速度,以防止振荡。动量的典型选择在 0.5 到 0.9 之间。

SGD optimizer 还有一个名为nesterov的参数,默认设置为 false。内斯特罗夫动量法是动量法的一个不同版本,它对凸函数有更强的理论收敛保证。在实践中,它比标准动量法稍微好一点。

在 Keras 中,我们可以通过在 SGD 优化器中设置初始学习率、衰减率和动量来实现基于时间的衰减。

learning_rate = 0.1
decay_rate = learning_rate / epochs
momentum = 0.8
sgd = SGD(lr=learning_rate, momentum=momentum, decay=decay_rate, nesterov=False)

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Fig 2 : Time-based Decay Schedule

阶跃衰减

步长衰减计划每隔几个历元就将学习速率降低一个因子。阶跃衰减的数学形式为:

lr = lr0 * drop^floor(epoch / epochs_drop) 

一个典型的方法是每 10 个时期将学习率降低一半。为了在 Keras 中实现这一点,我们可以定义一个步长衰减函数,并使用 LearningRateScheduler 回调将步长衰减函数作为参数,并返回更新后的学习速率,以供 SGD optimizer 使用。

def step_decay(epoch):
   initial_lrate = 0.1
   drop = 0.5
   epochs_drop = 10.0
   lrate = initial_lrate * math.pow(drop,  
           math.floor((1+epoch)/epochs_drop))
   return lratelrate = LearningRateScheduler(step_decay)

题外话,回调是在训练程序的给定阶段应用的一组函数。在训练期间,我们可以使用回调来查看模型的内部状态和统计数据。在我们的示例中,我们通过扩展基类keras.callbacks.Callback来创建一个定制回调,以记录培训过程中的损失历史和学习率。

class LossHistory(keras.callbacks.Callback):
    def on_train_begin(self, logs={}):
       self.losses = []
       self.lr = []

    def on_epoch_end(self, batch, logs={}):
       self.losses.append(logs.get(‘loss’))
       self.lr.append(step_decay(len(self.losses)))

将所有东西放在一起,我们可以传递一个回调列表,该列表由LearningRateScheduler回调和我们的定制回调组成,以适应模型。然后,我们可以通过访问loss_history.lrloss_history.losses来可视化学习率时间表和损失历史。

loss_history = LossHistory()
lrate = LearningRateScheduler(step_decay)
callbacks_list = [loss_history, lrate]history = model.fit(X_train, y_train, 
   validation_data=(X_test, y_test), 
   epochs=epochs, 
   batch_size=batch_size, 
   callbacks=callbacks_list, 
   verbose=2)

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Fig 3a : Step Decay Schedule

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Fig 3b : Step Decay Schedule

指数衰减

另一个常见的时间表是指数衰减。其数学形式为lr = lr0 * e^(−kt),其中lrk为超参数,t为迭代次数。类似地,我们可以通过定义指数衰减函数并将其传递给LearningRateScheduler来实现这一点。事实上,使用这种方法可以在 Keras 中实现任何定制的衰减计划。唯一的区别是定义了不同的自定义衰减函数。

def exp_decay(epoch):
   initial_lrate = 0.1
   k = 0.1
   lrate = initial_lrate * exp(-k*t)
   return lratelrate = LearningRateScheduler(exp_decay)

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Fig 4a : Exponential Decay Schedule

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Fig 4b : Exponential Decay Schedule

现在让我们在我们的例子中使用不同的学习率时间表来比较模型的准确性。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Fig 5 : Comparing Performances of Different Learning Rate Schedules

自适应学习率方法

使用学习率时间表的挑战在于它们的超参数必须预先定义,并且它们严重依赖于模型和问题的类型。另一个问题是相同的学习速率被应用于所有的参数更新。如果我们有稀疏的数据,我们可能希望在不同程度上更新参数。

自适应梯度下降算法,如**、** Adadelta、 RMSprop Adam ,提供了经典 SGD 的替代方案。这些每参数学习率方法提供了启发式方法,而不需要为学习率调度手动调整超参数的昂贵工作。

简而言之, Adagrad 对更稀疏的参数执行较大的更新,对不太稀疏的参数执行较小的更新。它在稀疏数据和训练大规模神经网络方面具有良好的性能。然而,当训练深度神经网络时,它的单调学习速率通常被证明过于激进并且过早停止学习。 Adadelta 是 Adagrad 的扩展,旨在降低其激进的、单调递减的学习速率。 RMSprop 以非常简单的方式调整 Adagrad 方法,试图降低其激进的、单调递减的学习速率。 Adam 是对 RMSProp 优化器的更新,它类似于带有 momentum 的 RMSprop。

在 Keras 中,我们可以使用相应的优化器轻松实现这些自适应学习算法。通常建议将这些优化器的超参数保留为默认值(有时lr除外)。

keras.optimizers.Adagrad(lr=0.01, epsilon=1e-08, decay=0.0)keras.optimizers.Adadelta(lr=1.0, rho=0.95, epsilon=1e-08, decay=0.0)keras.optimizers.RMSprop(lr=0.001, rho=0.9, epsilon=1e-08, decay=0.0)keras.optimizers.Adam(lr=0.001, beta_1=0.9, beta_2=0.999, epsilon=1e-08, decay=0.0)

现在让我们看看使用不同的自适应学习率方法的模型性能。在我们的例子中,在其他自适应学习率方法中,Adadelta 给出了最好的模型精度。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Fig 6 : Comparing Performances of Different Adaptive Learning Algorithms

最后,我们比较了我们讨论过的所有学习速率表和自适应学习速率方法的性能。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Fig 7: Comparing Performances of Different Learning Rate Schedules and Adaptive Learning Algorithms

结论

在我研究的许多例子中,自适应学习率方法比学习率计划表现更好,并且在超参数设置中需要更少的努力。我们还可以使用 Keras 中的LearningRateScheduler来创建针对我们的数据问题的定制学习率计划。

作为进一步的阅读,Yoshua Bengio 的论文为深度学习的学习速率调优提供了非常好的实用建议,例如如何设置初始学习速率、小批量大小、纪元数量以及使用早期停止和动量。

源代码

参考资料:

数据科学家的学习资源

原文:https://towardsdatascience.com/learning-resources-for-data-scientists-2a48d9168625?source=collection_archive---------10-----------------------

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Learning, learning and more learning!

我被问了很多次,为了学习更多关于数据科学或人工智能的知识,我去了哪些学习资源。这篇博文让我可以轻松地与他人分享我学习所依赖的资源,以及我是如何使用这些学习资源的。我将从我去的网站开始。

Arxiv.Org

期刊曾经是一个非常封闭的领域,每个学者都在竭尽全力让他们的研究发表在最负盛名的期刊上(或被称为学术界的第一梯队)。与现在相比,这些杂志的存在使在大学工作对我来说更有吸引力。但是这些期刊的受众非常有限,鉴于目前的情况,研究不再局限于大学,为了人类的进步,研究论文需要更广泛地分享。

这就是 Arxiv.Org 的的用武之地。它收藏在康奈尔大学图书馆,是许多学者和非学者研究的宝库。你会发现那里有很多研究,你可以从 Arxiv 学到很多关于数据科学、算法、计算机科学等的知识。使用它的关键是能够使用相关的关键字进行搜索。否则,另一种选择可能是 FB 集团或 Reddit,人们“推荐”某些研究论文,你可以根据推荐阅读。

我承认这些论文读起来很有挑战性,但是你必须告诉自己,这些论文不是要在一次阅读中完成的。你必须多读几遍,才能体会到你在之前的阅读中学到的东西,并与之前获得的其他相关知识联系起来。

所以,如果你想从事数据科学和人工智能,请做好准备。Arxiv.Org 将是你学习旅程中的好伙伴。

StackOverflow

鉴于开源运动如此之大,你不能逃避编程,尤其是大型科技公司开放了他们的机器学习框架,如 Tensorflow、PyTorch、Keras 等。

既然你不能逃避编程,你也不能逃避程序员最常见和最令人沮丧的任务,那就是调试!对于任何编写代码的人来说, StackOverflow 是一个可以去的地方,可以寻找那些曾经陷入相同错误的同事,并寻求解决方案。我确实经常去 StackOverflow(是的,我是一个糟糕的程序员。)来寻找可能的调试方法,通常我会从中获得一些关于如何调试的想法。最大的挑战是试图根据问题的“标题”来解读,你正在寻找的解决方案是否就在那里。所以很多时候,你要先浏览几个 Q & A 线程,才能找到可能的解决方案。

中型

博客自诞生以来已经走过了漫长的道路(大约 10 年前?).博客不仅仅是一个供人们写观点的地方,现在还有一些“产品”,如出版物,它整合了相似主题的博客,这样像我这样的新博客就很容易有现成的受众。准备好的观众鼓励更多的人贡献他们的观点和想法。

说回来,像 Medium(尤其是 Medium)这样的博客网站是一个学习的好地方。除了技术博客,他们展示了如何使用机器学习解决业务问题,代码和思维过程也显示了出来,在我看来,这是非常有价值的,因为数据科学家是解决方案的提供者,加强我们自己的思维过程并能够从不同角度看待挑战是非常重要的。所以我在 Medium 上订阅了一些出版物,并让 Medium“推荐”我喜欢阅读的博客。

我订阅的刊物有走向数据科学 e、黑客帝国成为人类数据驱动投资者

慕课

我从 MOOC 网站上捡了很多知识,比如 Coursera 、(特别) UdacityEdx 。鉴于世界各地的大学提供了大量的知识和材料,我喜欢这些网站。

目前,我正在学习 Udacity 上的强化学习模块。想象一下,在过去,这种高级模块在网上是没有的,如果我想了解它,我必须四处打听一本推荐的教科书,然后吃大约一个月的面包(便宜的),才能攒够买教科书的钱。现在,由于 MOOCs 网站,我可以很容易地获得这些策划材料。

需要注意的一点是,大多数模块都有非常简洁的视频,所以不要期望在完成模块后成为专家。它可以给你一个关键词列表,你需要进一步研究,以掌握这个主题。

YouTube

又一个生命救星,非常感谢大学和科技聚会/会议把讲座和谈话放在 YouTube 上!我喜欢它!现在 YouTube 上有很多大学讲座,如果我需要对某些主题的快速解释,我会去 YouTube 上寻找一个简短的视频,并以 1.5-2 倍的速度播放(另一个很棒的功能!).

世界知名的大学,如麻省理工学院和斯坦福大学,将他们的讲座放在网上,并允许任何可以上网的人“旁听”讲座,一起学习!多棒啊。所以我保留了一个播放列表的列表,希望可以浏览一下,了解更多关于计算机科学/数据科学/人工智能的知识。

播客

最近,我偶然看到几个关于数据科学和人工智能的播客。它们让我能够听取专家的不同意见,并让我有可能在漫长的会议旅途中学习。伴随着路过的风景,聆听其他相关领域专家的知识分享,是一种极大的放松。在这些巴士旅程中,我学到了很多知识,也让我接触到了新的概念。我相信这些曝光是由于小组成员/发言者的自发性。

结论

这些是我去学习和获取更多数据科学和人工智能知识的网站。毫无疑问,这些网站你可能听说过,但我在这里的分享更多的是创造一种意识,即你习惯的这些网站是你可以用来学习的网站,可以了解更多关于数据科学和人工智能的信息。

我希望这个博客对你有用。如果有,一定要分享。祝您的数据科学学习之旅愉快,请务必访问我的其他博客文章LinkedIn 个人资料

通过自然语言推理学习句子嵌入

原文:https://towardsdatascience.com/learning-sentence-embeddings-by-natural-language-inference-a50b4661a0b8?source=collection_archive---------1-----------------------

无监督学习方法看起来像是构建单词、句子或文档嵌入的正常方式,因为它更一般化,使得预训练的嵌入结果可以转移到其他 NLP 下游问题。例如,单词嵌入中的 skip-gram 和句子嵌入中的 skip-through 以及段落嵌入中的分布式词袋。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

“closeup photo of person carrying professional video recorder” by Laura Lee Moreau on Unsplash

Conneau 等人指出,ImageNet(图像分类)中的监督学习在将结果转移到下游问题方面做得很好。有些特征可以以某种方式转移到下游。因此,Conneau 等人使用文本蕴涵数据来训练一个句子嵌入层,称为 InferSent。

看完这篇文章,你会明白:

  • 完美的设计
  • 体系结构
  • 履行
  • 拿走

完美的设计

该团队使用 SNLI(斯坦福自然语言推理)数据来训练自然语言推理(NLI)问题的模型。NLI 的目标是找出句子 1(前提)和句子 2(假设)之间的关系。有三个范畴,即蕴涵、矛盾和中性。下面是一个非常简单的例子:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

“two apples and walnuts on white towel” by Alex Kotomanov on Unsplash

  1. 我吃水果。
  2. 我吃苹果。

直觉上,这种关系是隐含的。作者认为,NLI 是理解句子中语义关系的合适任务,因此它有助于为下游 NLP 问题的句子嵌入建立良好的嵌入。

体系结构

总体思路是,两个句子(前提输入和假设输入)将通过句子编码器(权重相同)进行转换。然后利用 3 种匹配方法来识别前提输入和假设输入之间的关系。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Conneau et al. (2017)

  1. 两个向量的连接
  2. 两个向量的逐元素乘积
  3. 两个向量的绝对元素差

在概述之后,可能会进入句子编码器的架构。Conneau 等人评估了 7 种不同的架构:

  1. 标准 LSTM
  2. 标准 GRU
  3. 前向和后向 GRU 的最后隐藏状态的串联
  4. 具有平均轮询的双向 LSTM
  5. 具有最大轮询的双向 LSTM
  6. 自我关注网络(用 BiLSTM 关注)
  7. 分层卷积网络

在首先得出最佳方法之前,我们可以认为用 BiLSTM 注意应该是最佳方法,因为注意机制有助于识别重要权重。实际上,在迁移学习中使用它可能是有害的。另一方面,采用平均轮询的 BiLSTM 可能由于无法定位重要部分而性能不佳。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

#5 Bi-directional LSTM with max polling (Conneau et al., 2017)

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

#6 Self-attentive Network Architecture (Conneau et al., 2017)

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Hierarchical convolutional networks (Conneau et al., 2017)

从实验结果来看,最大轮询的双向 LSTM 是最好的方法。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

Conneau et al. (2017)

履行

有两种方法可以使用 InferSent。首先是在你的 NLP 问题中使用一个预先训练好的嵌入层。另一个是你自己发出的建筑噪音。

加载预训练嵌入

脸书研究小组提供了两个预训练模型,即版本 1(基于手套)和版本 2(基于快速文本)。

加载推断预训练模型和 GloVe(或 fastText)模型,然后您可以将句子编码为向量。

# Init InferSent Model
infer_sent_model = InferSent()
infer_sent_model.load_state_dict(torch.load(dest_dir + dest_file))# Setup Word Embedding Model
infer_sent_model.set_w2v_path(word_embs_model_path)# Build Vocab for InferSent model
model.build_vocab(sentences, tokenize=True)# Encode sentence to vectors
model.encode(sentences, tokenize=True)

列车嵌入

另一种方法是自己训练嵌入。你可以使用你自己的数据或原始数据集。因为这个推理器使用监督学习方法来生成句子嵌入,所以您首先需要有一个带注释的(带标签的)数据。

这是第一种方法的步骤。克隆人将原始的回购发送到本地。然后在控制台中执行“get_data.bash ”,以便下载和处理 SNLI(斯坦福自然语言推理)和 multi nli(NLI)语料库。确保您必须在当前文件夹而不是其他相对路径中执行以下 shell 脚本

./get_data.bash

之后,下载手套(和/或快速文本)

mkdir dataset/GloVe
curl -Lo dataset/GloVe/glove.840B.300d.zip http://nlp.stanford.edu/data/glove.840B.300d.zip
unzip dataset/GloVe/glove.840B.300d.zip -d dataset/GloVe/
mkdir dataset/fastText
curl -Lo dataset/fastText/crawl-300d-2M.vec.zip https://s3-us-west-1.amazonaws.com/fasttext-vectors/crawl-300d-2M.vec.zip
unzip dataset/fastText/crawl-300d-2M.vec.zip -d dataset/fastText/

正在下载预先训练好的模型。版本 1 通过使用 GloVe 来训练,而版本 2 利用了 fastText。

curl -Lo encoder/infersent1.pkl https://s3.amazonaws.com/senteval/infersent/infersent1.pkl
curl -Lo encoder/infersent2.pkl https://s3.amazonaws.com/senteval/infersent/infersent2.pkl

最后,您可以执行下面的命令来训练嵌入层。

python train_nli.py --word_emb_path ./glove.42B.300d.txt

对于我的单个 GPU 虚拟机,完成培训大约需要 1 天时间。

拿走

要访问所有代码,可以访问我的 github repo。

  • 与其他嵌入方法相比, InferSent 使用监督学习来计算单词向量。
  • InferSent 利用单词嵌入 (GloVe/ fastText)构建句子嵌入。
  • 预训练模型支持 GloVe(版本 1)和 fasttext(版本 2)

关于我

我是湾区的数据科学家。专注于数据科学、人工智能,尤其是 NLP 和平台相关领域的最新发展。你可以通过媒体博客LinkedInGithub 联系我。

参考

Conneau,D. Kiela,H. Schwenk,L. Barrault,A. Bordes, 从自然语言推理数据中监督学习通用语句表示

在 Pytorch 中感染

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值