TowardsDataScience-博客中文翻译-2016-2018-二十一-

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

原文:TowardsDataScience Blog

协议:CC BY-NC-SA 4.0

深入探究深层网络背后的数学

原文:https://towardsdatascience.com/https-medium-com-piotr-skalski92-deep-dive-into-deep-networks-math-17660bc376ba?source=collection_archive---------1-----------------------

神经网络之谜第一部分

如今,有了许多高级的、专门的库和框架供我们使用,如 KerasTensorFlowPyTorch ,我们不需要经常担心我们的权重矩阵的大小或记住我们决定使用的激活函数的导数公式。通常我们创建一个神经网络所需要的,即使是一个非常复杂的结构,也只是一些导入和几行代码。这节省了我们搜索 bug 的时间,并简化了我们的工作。然而,关于神经网络内部正在发生什么的知识对诸如架构选择、超参数调整或优化等任务有很大帮助。

注:承蒙荣格林逸的礼遇,你也可以用中文阅读这篇文章。多亏了达维·坎迪多的帮助,你还可以查看文本的葡萄牙语版本。在我的 GitHub 上可以找到用于创建本文中使用的可视化效果的源代码。

介绍

为了进一步了解神经网络是如何工作的,我决定今年夏天花些时间来看看隐藏在表面下的数学。我还决定写一篇文章,一篇给我自己——整理新学到的信息,一篇给别人——帮助他们理解这些有时很难的概念。对于那些对代数和微分学感觉不太舒服的人,我会尽量温和,但正如标题所示,这将是一篇有很多数学的文章。

Figure 1. Visualization of the training set.

作为的一个例子,我们将解决数据集的二元分类问题,如图 1 所示。以上。属于两个类别的点形成圆——这种排列对于许多传统的 ML 算法来说是不方便的,但是一个小的神经网络应该工作得很好。为了解决这个问题,我们将使用图 2 所示结构的神经网络。—五个完全连接的层,具有不同数量的单元。对于隐藏层,我们将使用 ReLU 作为激活函数,Sigmoid 作为输出层。这是一个非常简单的架构,但足够复杂,可以作为我们讨论的有用示例。

Figure 2. Neural network architecture

克拉斯溶液

首先,我将介绍一个使用最流行的机器学习库之一——KERAS 的解决方案。

就这样。正如我在介绍中提到的,几个导入和几行代码就足以创建和训练一个模型,然后该模型能够以几乎 100%的准确率对来自我们测试集的条目进行分类。我们的任务归结为根据所选择的架构提供超参数(层数、层中神经元的数量、激活函数或时期的数量)。现在让我们看看幕后发生了什么。哦…还有我在学习过程中创造的一个很酷的视觉效果,希望它能让你不至于睡着。

Figure 3. Visualization of areas qualified for appropriate classes during training

什么是神经网络?

L 让我们从回答这个关键问题开始:什么是神经网络?这是一种受生物启发的构建计算机程序的方法,能够学习并独立发现数据中的联系。如图 2 所示。如图所示,网络是分层排列的软件“神经元”的集合,以允许通信的方式连接在一起。

单个神经元

E 每个神经元接收一组 x 值(从 1 到 n 编号)作为输入,并计算预测的 y-hat 值。向量 x 实际上包含来自训练集的 m 个示例之一中的特征值。此外,每个单元都有自己的一组参数,通常称为 w (权重的列向量)和 b(偏差),它们在学习过程中会发生变化。在每次迭代中,神经元基于其当前权重向量 w 计算向量 x 的值的加权平均值,并添加偏差。最后,这个计算的结果通过一个非线性的激活函数 g 传递。我将在文章的下一部分提到一些最流行的激活函数。

Figure 4. Single neuron

单层

现在让我们缩小一点,考虑如何对神经网络的整个层进行计算。我们将利用我们对单个单元内发生的事情的了解,并跨整个层进行矢量化,以将这些计算合并到矩阵方程中。为了统一符号,将为所选层【l】编写方程。顺便说一下,下标 i 标记了该层中一个神经元的索引。

Figure5. Single layer

还有一个重要的备注:我们写单个单元的方程时,用的是 x 和 y-hat,分别是特征的列向量和预测值。当切换到层的一般符号时,我们使用向量a——表示相应层的激活。因此, x 矢量是层 0——输入层的激活。该层中的每个神经元根据以下等式执行类似的计算:

为了清楚起见,让我们以第 2 层为例写下方程式:

正如你所看到的,对于每一层,我们必须执行一些非常相似的操作。为此使用 for-loop 不是很有效,所以为了加快计算速度,我们将使用矢量化。首先,通过将权重的水平向量 w (转置)堆叠在一起,我们将构建矩阵 W 。类似地,我们将叠加层中每个神经元的偏差,创建垂直向量 b 。现在,没有什么可以阻止我们建立一个单一的矩阵方程,允许我们一次对该层的所有神经元进行计算。让我们也写下我们用过的矩阵和向量的维数。

跨多个示例进行矢量化

到目前为止,我们所拟定的方程式只涉及一个例子。在神经网络的学习过程中,您通常会处理大量的数据,多达数百万个条目。因此,下一步将是跨多个示例的矢量化。假设我们的数据集有 m 个条目,每个条目有 nx 个特征。首先,我们将把每层的垂直向量 xaz 放在一起,分别创建 XAZ 矩阵。然后,我们重写之前的布局方程,考虑新创建的矩阵。

什么是激活功能,我们为什么需要它?

激活函数是神经网络的关键元素之一。没有它们,我们的神经网络就会变成线性函数的组合,所以它本身就只是一个线性函数。我们的模型具有有限的扩展性,不超过逻辑回归。非线性元件允许在学习过程中更大的灵活性和复杂函数的创建。激活函数对学习速度也有显著影响,这是选择它们的主要标准之一。图 6 显示了一些常用的激活功能。目前,最流行的隐藏层可能是 ReLU。当我们处理二元分类并且希望从模型返回的值在 0 到 1 的范围内时,我们有时仍会使用 sigmoid,尤其是在输出层。

Figure 6. Diagrams of the most popular activation functions together with their derivatives.

损失函数

T 学习过程进度的基本信息来源是损失函数值。一般来说,损失函数旨在显示我们离“理想”解决方案有多远。在我们的例子中,我们使用了二元交叉熵,但是根据我们处理的问题,可以使用不同的函数。我们使用的函数由以下公式描述,其值在学习过程中的变化如图 7 所示。它显示了随着每一次迭代,损失函数值是如何降低的,而精度是如何提高的。

Figure 7. Change of accuracy and loss values during learning process

神经网络是如何学习的?

T 学习过程是关于改变参数 Wb 的值,从而使损失函数最小化。为了实现这一目标,我们将求助于微积分和使用梯度下降法找到一个函数最小值。在每次迭代中,我们将计算损失函数相对于神经网络每个参数的偏导数的值。对于那些不太熟悉这类计算的人,我只想说导数有一种神奇的能力来描述函数的斜率。由于这一点,我们知道如何操纵变量,以便在图表中向下移动。为了直观地了解梯度下降是如何工作的(并阻止你再次入睡),我准备了一个小的可视化。你可以看到每一个连续的时代我们是如何走向最小值的。在我们的神经网络中,它以同样的方式工作——每次迭代计算的梯度向我们显示我们应该移动的方向。主要的区别在于,在我们的示例性神经网络中,我们有更多的参数要处理。正是…怎么计算这么复杂的导数?

Figure 8. Gradient descent in action

反向传播

ackpropagation 是一种允许我们计算非常复杂的梯度的算法,就像我们需要的那样。根据以下公式调整神经网络的参数。

在上面的等式中,α代表学习率——一个超参数,它允许你控制执行调整的值。选择一个学习率是至关重要的——我们设置得太低,我们的神经网络将学习得非常慢,我们设置得太高,我们将无法达到最小值。 dWdb 使用链式法则计算,损失函数相对于 Wb 的偏导数。 dWdb 的尺寸分别与 Wb 的尺寸相同。图 9。显示了神经网络中的操作序列。我们清楚地看到前向和后向传播是如何一起优化损失函数的。

Figure 9. Forward and Backward Propagation

结论

我已经成功地向你们解释了发生在神经网络内部的数学。在使用神经网络时,至少了解这个过程的基本知识会很有帮助。我认为我提到的事情是最重要的,但它们只是冰山一角。我强烈推荐尝试自己编程这么小的神经网络,不使用高级框架,只用 Numpy。

如果你设法来到这里,恭喜你。这当然不是最容易的阅读。如果你喜欢这篇文章,请在 TwitterMedium 上关注我,并在 GitHubKaggle 上查看我正在进行的其他项目。本文是“神经网络的奥秘”系列的第二部分,如果你还没有机会,请阅读其他文章。保持好奇!

自动驾驶汽车的自动车道检测

原文:https://towardsdatascience.com/https-medium-com-priya-dwivedi-automatic-lane-detection-for-self-driving-cars-4f8b3dc0fb65?source=collection_archive---------2-----------------------

第 1 章:用数据做酷事!

我们可以使用汽车中的前置摄像头来自动检测车道线吗?

原来我们可以做得很好!这是一个视频,当汽车行驶时,车道线被“画”出来。你也可以看到曲率半径被计算出来以帮助汽车转向。

Lane Lines detected for self driving car

我们为什么要这么做?因为给汽车配备前置摄像头很便宜。比雷达或激光雷达便宜多了。自动驾驶汽车即将问世!

链接到我的 GitHub 用 Python 写的完整代码。

我们是这样做的。一旦我们从自动驾驶汽车的前置摄像头获得了摄像头图像,我们就会对其进行一些“修改”。我遵循的步骤详述如下:

  1. 失真校正

当相机观察真实世界中的 3D 对象并将它们转换为 2D 图像时,会发生图像失真。这种转换并不总是完美的,扭曲会导致物体的外观尺寸、形状或位置发生变化。因此,我们需要纠正这种失真,以使相机能够准确地看到图像。这是通过拍摄相机的几张棋盘图片并使用 cv2.calibrateCamera() 函数计算相机校准矩阵来完成的。

请参见下面的失真校正图像示例。请注意,正常镜片的校正非常小,肉眼看不出有多大差别

2.创建二进制图像

现在我们有了未失真的图像,我们可以开始我们的分析。我们需要探索不同的方案,以便我们可以清楚地检测道路上的感兴趣的对象,在这种情况下,车道线,而忽略其余的。我用两种方法做到了这一点:

I)使用 Sobel 算子计算 x 梯度

图像的渐变可用于识别黑白图像中颜色的急剧变化。这是一种非常有用的检测图像边缘的技术。对于道路的图像,我们通常在黑色道路上有黄色或白色的车道线,因此 x 渐变非常有用。以下示例显示了使用 cv2.sobel() 计算的图像及其在 x 方向的梯度

ii)探索其他颜色通道

使用不同的色彩空间怎么样?HSV(色调、饱和度和值)颜色空间在隔离黄色和白色线条时非常有用,因为它隔离了颜色(色调)、颜色量(饱和度)和亮度(值)。我们可以使用图像中的 S 颜色通道来“看到”车道线,如下图所示:

现在,我们将 sobel x 梯度和 S 颜色通道图像相结合,以获得最终的二进制图像,其中车道线与背景相比对比度更高。见下图:

3.鸟瞰图像

在阈值操作之后,我们执行透视变换以将图像改变为鸟瞰图。这样做是因为从这个俯视图,我们可以确定车道的曲率,并决定如何驾驶汽车。为了执行透视变换,我确定了在图像上形成梯形的 4 个源点和 4 个目的点,以便变换后车道线彼此平行。目的点是通过反复试验选择的,但是一旦选择好,对所有的图像和视频都有效,因为摄像机安装在一个固定的位置。 cv2.getPerspectivecv2.warpPerspective 可用于执行此操作。看看在这个视图中车道线的曲率是多么清晰可见。是不是很神奇!

4.将曲线拟合到鸟瞰图图像

为了更好地估计车道的位置,我们使用图像下半部分的直方图来识别潜在的左右车道标记。我修改了这个函数来缩小左右车道存在的区域,这样高速公路车道分隔符或任何其他噪声就不会被识别为车道。一旦确定了初始的左侧和右侧车道底部点,我们就使用 numpy polyfit 函数来查找表示车道的最佳二阶多项式,如下图所示。

Left and right lane lines fitted

5.将结果绘制到道路上,以便清楚地识别车道区域

快到了!一旦我们确定了车道线并对其进行多项式拟合,我们可以再次使用 cv2.warpPerspective 将车道线扭曲回原始图像。我们还做了一个加权添加来显示未失真图像上的车道线。这是它的样子。

就这些!为了对视频进行这样的操作,我们使用 Moviepy 库到达每一帧,并在其上运行上述所有步骤。对于某些帧,我们可能无法正确识别车道线。我们可以通过一些简单的检查来检测,如车道线是否由逻辑宽度分隔,鸟瞰图中的车道线是否相互平行等。如果检查失败,则预测的车道线被丢弃,并且使用最后良好的左和右车道值。这非常有效。

虽然这种逻辑适用于大多数情况,但它并不完美。当相机图像质量差时,它可能会失败,如照明不足或车道线不可见,道路上有雪或碎片。此外,如果道路呈波浪形或 S 形,我们可能无法用二阶多项式来拟合它。

PS:我住在多伦多,我希望将职业生涯转向深度学习。如果你喜欢我的帖子,并能把我联系到任何人,我将不胜感激:)。我的电子邮件是 priya.toronto3@gmail.com

参考资料:

Udacity 无人驾驶汽车 Nano Degree——我感谢 Udacity 给我机会成为他们新的无人驾驶汽车项目的一部分。这是一次非常有趣的旅程。我使用的大部分代码都是在课堂讲课中建议的。

Python OpenCV 库让应用计算机视觉技术变得如此简单

支持向量机(SVM)——概述

原文:https://towardsdatascience.com/https-medium-com-pupalerushikesh-svm-f4b42800e989?source=collection_archive---------1-----------------------

SVM classifier

机器学习涉及预测和分类数据,为此,我们根据数据集采用各种机器学习算法。

SVM 或支持向量机是用于分类和回归问题的线性模型。它可以解决线性和非线性问题,并能很好地解决许多实际问题。SVM 的想法很简单:算法创建一条线或一个超平面,将数据分类。

在这篇博文中,我打算提供一个关于支持向量机的高层次概述。我将讨论支持向量机背后的理论,它在非线性可分数据集上的应用,以及用 Python 实现支持向量机的一个快速示例。在接下来的文章中,我将探索算法背后的数学,并挖掘引擎盖下。

在第一级近似下,支持向量机所做的是找到两类数据之间的分隔线(或超平面)。SVM 是一种算法,它将数据作为输入,如果可能的话,输出一条线来分隔这些类。

让我们从一个问题开始。假设您有一个如下所示的数据集,您需要将红色矩形从蓝色椭圆中分类出来(让我们从负面中找出正面)。所以你的任务是找到一条理想的线,将这个数据集分成两类(比如红色和蓝色)。

Find an ideal line/ hyperplane that separates this dataset into red and blue categories

不是什么大任务,对吧?

但是,正如您注意到的,并没有一个独特的行来完成这项工作。事实上,我们有一条无限长的线可以把这两个阶级分开。那么 SVM 是如何找到理想伴侣的呢???

让我们采取一些可能的候选人,自己找出答案。

Which line according to you best separates the data???

这里有两条候选线,绿色的线和黄色的线。根据你的说法,哪条线最适合分隔数据?

如果你选择了黄线,那么恭喜你,因为那是我们正在寻找的线。在这种情况下,黄线分类更好,这在视觉上非常直观。但是,我们需要一些具体的东西来固定我们的线。

上图中的绿线与红色类相当接近。虽然它对当前数据集进行分类,但它不是一条一般化的线,在机器学习中,我们的目标是获得一个更一般化的分隔符。

SVM 寻找最佳路线的方法

根据 SVM 算法,我们从两个类中找到最接近直线的点。这些点称为支持向量。现在,我们计算直线和支持向量之间的距离。这个距离叫做边缘。我们的目标是利润最大化。边缘最大的超平面是最优超平面。

Optimal Hyperplane using the SVM algorithm

因此,SVM 试图以这样一种方式做出一个决定边界,即两个阶级(那条街)之间的间隔尽可能宽。

很简单,不是吗?让我们考虑一个有点复杂的数据集,它不是线性可分的。

Non-linearly separable data

这个数据显然不是线性可分的。我们无法画出一条直线来对这些数据进行分类。但是,这些数据可以转换成高维的线性可分数据。让我们增加一个维度,称之为 z 轴。让 z 轴上的坐标受约束支配,

z = x +y

所以,基本上 z 坐标是该点到原点距离的平方。让我们把数据标在 z 轴上。

Dataset on higher dimension

现在数据显然是线性可分的。设高维空间中分隔数据的紫线为 z=k,其中 k 为常数。因为,z=x +y 我们得到 x+y = k;这是一个圆的方程式。所以,我们可以用这种变换,把高维空间中的线性分隔符投射回原始维度。

Decision boundary in original dimensions

因此,我们可以通过向数据添加一个额外的维度来对数据进行分类,使其成为线性可分的,然后使用数学变换将决策边界投影回原始维度。但是为任何给定的数据集找到正确的转换并不容易。谢天谢地,我们可以在 sklearn 的 SVM 实现中使用内核来完成这项工作。

超平面

现在我们理解了 SVM 逻辑,让我们正式定义超平面。

n 维欧几里得空间中的超平面是该空间的平坦的 n-1 维子集,它将该空间分成两个不相连的部分。

例如,让我们假设一条线是我们的一维欧几里得空间(也就是说,我们的数据集位于一条线上)。现在在这条线上选择一个点,这个点将这条线分成两部分。线有 1 维,而点有 0 维。所以一个点就是这条线的超平面。

对于二维,我们看到分隔线是超平面。类似地,对于三维,具有二维的平面将 3d 空间分成两部分,因此充当超平面。因此,对于一个 n 维空间,我们有一个 n-1 维的超平面把它分成两部分

代码

import numpy as np
X = np.array([[-1, -1], [-2, -1], [1, 1], [2, 1]])
y = np.array([1, 1, 2, 2])

我们在 X 中有我们的点,在 y 中有它们所属的类。

现在我们用上面的数据集训练我们的 SVM 模型。对于这个例子,我使用了线性核。

from sklearn.svm import SVC
clf = SVC(kernel='linear')
clf.fit(X, y)

预测新数据集的类别

prediction = clf.predict([[0,6]]) 

调谐参数

参数是在创建分类器时传递的参数。以下是 SVM 的重要参数-

1】C:

它控制平滑决策边界和正确分类训练点之间的折衷。大的 c 值意味着你将正确地得到更多的训练点。

Smooth decision boundary vs classifying all points correctly

考虑一个如上图所示的例子。我们可以为这个数据集绘制许多决策边界。考虑一条直线(绿色)决策边界,这非常简单,但代价是几个点被错误分类。这些错误分类的点称为异常值。我们也可以做一些更摇摆不定的东西(天蓝色的决策边界),但我们可能会得到所有正确的训练点。当然,像这样非常错综复杂的东西的代价是,它很可能不能很好地推广到我们的测试集。因此,如果你着眼于精度,更简单、更直接的方法可能是更好的选择。较大的 c 值意味着你将得到更复杂的决策曲线来拟合所有的点。弄清楚你有多希望有一个平滑的决策边界,而不是一个正确的决策边界,是机器学习艺术的一部分。因此,为您的数据集尝试不同的 c 值,以获得完美平衡的曲线并避免过度拟合。

2】伽玛:

它定义了单个训练示例的影响范围。如果伽马值较低,则意味着每个点都有很远的范围,反之,伽马值较高,则意味着每个点都有很近的范围。

如果γ值非常高,那么决策边界将只取决于非常靠近该线的点,这实际上会导致忽略一些离决策边界非常远的点。这是因为更近的点得到更多的权重,这导致了曲线的摆动,如上图所示。另一方面,如果伽玛值很低,即使远点也会得到相当大的权重,我们会得到更线性的曲线。

中的即将出现中的

我将探索 SVM 算法和最优化问题背后的数学。

结论

我希望这篇博文有助于理解支持向量机。 写下你的想法、反馈或建议 如果有的话。

Connect with the Raven team on Telegram

重启随机梯度下降新手指南

原文:https://towardsdatascience.com/https-medium-com-reina-wang-tw-stochastic-gradient-descent-with-restarts-5f511975163?source=collection_archive---------3-----------------------

简单地找到一个学习率来经历梯度下降将有助于最小化神经网络的损失。但是,还有其他方法可以使这一过程更顺利、更快速、更准确。

第一种技术是重启随机梯度下降(SGDR),这是学习率退火的一种变体,它通过训练逐渐降低学习率。

Image 1: Each step decreases in size

有不同的退火方法,不同的减小步长的方法。一种流行的方法是逐步降低学习率:在最初的几次迭代中简单地使用一个学习率,然后在接下来的几次迭代中降低到另一个学习率,然后在接下来的几次迭代中进一步降低学习率。另一种变型是随着每次迭代线性降低学习速率。

Left: Decrease learning rate by steps; Right: Linearly decrease learning rate

SGDR 使用余弦退火,以半余弦曲线的形式降低学习率,就像这样:

Image 4: Cosine Annealing

这是一个好方法,因为我们可以在开始时以相对较高的学习速率开始几次迭代,以快速接近局部最小值,然后随着我们接近最小值而逐渐降低学习速率,以几次小的学习速率迭代结束。

然而,我们可能会发现自己处于局部极小值,其中权重的小变化会导致损失的大变化。在下面这个损失函数中,通过训练,我们已经降落在局部最小值。

Image 5: Approaching a local minimum

但是,如果我们在不同的数据集上测试这个网络,损失函数可能会略有不同。在这个局部最小值中损失函数的小移动将导致损失的大变化:

Image 6: Slight shift in loss function resulting in a large change in loss

突然间,这个局部最小值成了一个可怕的解决方案。另一方面,如果我们在这个更平坦的槽中找到了解决方案:

Image 7: Approaching a more stable local minimum

即使不同的数据集稍微改变了损失函数,损失也会保持相对稳定:

Image 8: Slight shift in loss function doesn’t impact loss as much

这种更平的槽更好,因为它提供了精确和稳定的解决方案。它更多的是广义;也就是对新数据有更高的反应能力。为了找到更稳定的局部最小值,我们可以不时地增加学习率,鼓励模型在处于陡峭的低谷时从一个局部最小值“跳到”另一个局部最小值。这是 SGDR 的“重新开始”。

Image 9: Increasing the learning rates every few iterations to “restart” the gradient descent // Source

在上图的第一个“半余弦”周期中,我们下降到局部最小值,如下所示:

Image 10: Descending into local minimum

突然,我们提高了学习率,在下一次迭代中迈出了一大步:

Image 11: “Restarting”

在第二个“半余弦”周期,我们下降到另一个局部最小值。

Image 12: Descending into a more stable local minimum

然后我们再次大幅提高学习率。只是这一次,因为我们处于损失函数的一个更稳定的区域,这种“重新开始”并没有把我们带出局部最小值:

Image 13: “Restarting” doesn’t take us out of this local minimum

最后,我们再次逐渐降低学习率,直到我们最小化损失函数,找到稳定的解决方案。

Image 14: Settling into this local minimum

这些“周期”中的每一个都被称为一个周期,在训练我们的神经网络时,我们可以自己选择周期的数量和每个周期的长度。还有,既然我们是逐渐降低学习率,那么最好从略大于最优学习率的学习率开始(你是怎么确定最优学习率的?点击这里。选择一个足够大的学习率也很重要,以允许函数在“复位”时跳到不同的最小值。

为了在 3D 中可视化,这里有两个模型:

Image 15: Stochastic Gradient Descent with Restarts // Source

左边的模型缓慢下降到一个局部最小值,而右边的模型在几个局部最小值之间跳跃,寻找一个更稳定的。

您也可以在每次循环后增加循环长度,如下所示:

Image 16: Increasing cycle length // Source

这似乎输出了更好、更准确的结果,因为它允许我们更精确地找到稳定区域中的最小值点。

理解基于深度学习的图像分类器的终极纳米书

原文:https://towardsdatascience.com/https-medium-com-rishabh-grg-the-ultimate-nanobook-to-understand-deep-learning-based-image-classifier-33f43fea8327?source=collection_archive---------13-----------------------

理解卷积神经网络的指南

Fig 1: The Four Superheroes of Deep Learning, Source: bit.ly/2Re5HNE

在当今世界,我们广泛使用图像。不是吗?你有没有想过脸书是如何自动检测图像中的人脸,然后像上图一样分辨出图像中的人是谁?当我将指针移近图像中的一张脸时,它会自动说出这个人的名字,不是别人,正是 Yann le Cun(CNN 架构的提出者)。你用过 Snapchat 吗?它首先自动检测您的面部,然后相应地应用您选择的过滤器。苹果的 Face ID 也做了类似的事情,当它发现你的脸在设备前面时,它会自动解锁你的手机。

有很多这样的例子,它们都有一个共同点。他们在摆弄图像,让机器变得聪明,所以它们会自动从中提取有意义的信息。太神奇了。不是吗?当我第一次了解这些技术时,我非常好奇它们是如何工作的?说实话,一开始好像很神奇。电脑怎么会自动分辨出这是哥哥的照片不是我的?如果你也发现自己和我在同一页上,那么拿一杯咖啡,因为在这本纳米书中,你会学到很多关于这些事情背后的主要思想的每一个细节,但以一种非常有趣的方式。

有许多任务,如图像分类、目标定位、目标检测、目标分割等等。但是在这篇文章中,我们将主要关注图像分类。

这篇文章分为三个部分。在第一个中,我们将尝试通过跟随我们自己的直觉来建立这个技巧,这将是非常有趣的,也是学习这个魔术的独特方法。在第二部分中,我们将使用 python 实现它,以查看它的运行情况。在第三部分,我们将尝试通过问几个有趣的问题来探索和了解更多信息。

理解语义差距

我们人类是视觉动物,我们用眼睛看到周围的各种物体,但你有没有想过图像对计算机意味着什么?我们感知图像的方式和计算机感知图像的方式有很大的不同。我们特别称这个间隙为Semantic Gap,下图对此进行了很好的描述。

Fig 2: On the left— What we see using our eyes. On the right — What computer sees, Source: bit.ly/2ga5Cpu

在上面的图片中,很明显,对于计算机来说,图像只不过是一串排列成网格状结构的数字,正式名称为Array.,然而,我只展示了其中的一小部分。如果您想看到计算机的整个图像,您可以使用下面的代码。

import os 
import cv2 
import numpy as npnp.set_printoptions(threshold=np.inf)image = cv2.imread('/cat.jpeg')
print(type(image))
image = cv2.resize(image , (28,28) , cv2.INTER_AREA)
print(image.shape)
#visualizing the seperate channels of image
print(image[: , : , 0]) #prints out Blue channel
print(image[: , : , 1]) #prints out Green channel
print(image[: , : , 2]) #prints out Red channel
#To visualize the whole image with all 3 channels
print(image[: , : , :])

现在,你可能会问,我们心爱的电脑是否有办法知道哪个物体出现在画面中。当然有,我们会建造它。我知道,这似乎是一项艰巨的任务,但请忍耐到最后。我们一定会实现的!

我们旅程的第一步也是最重要的一步:

正如我以前说过的,我们将简单地问一些问题,这些问题将引导我们建立一个图像分类器。为了简洁起见,我们将称图像分类器为 IC
。现在,我们准备开始我们的旅程。所以让我们问第一个问题:“你能说出下面的图片属于哪一类吗?猫还是狗?

Fig 3: Images of Cats, Source: bit.ly/2V5RBwK and bit.ly/2Q2OaTG

我相信你说得对!他们属于Cat的范畴,但是等等,退一步想想你是怎么得出这个结论的?试着想想,你的大脑是怎么做到的?你怎么能如此确定这些照片是猫而不是狗?你知道猫长什么样,你刚才可能做的是相似性检查在你无意识地储存在你大脑中的猫脸的粗略图像和这些图像(更具体地说是这些图像的中间部分)之间,如果它返回一个高分。然后你得出结论,这些图像实际上是猫

现在,你可能会说“我们不能把同样的机制整合到我们自己的图像分类器中吗?”这似乎是一个很棒的想法,但它带来了两个主要挑战:

  1. 哪个图像会充当我们已经储存在脑海中的图像(粗糙图像)?
  2. 我们将如何测量两幅图像之间的相似性?

让我们解决第一个问题。在这里,我们主要集中在分类一个图像是猫还是不是猫。那么我们就不能用一张猫脸的形象作为我们的粗糙形象吗?为什么不呢!我们可以使用下面的图像作为粗略的图像,然后我们可以对上面显示猫脸的图像的中间部分进行相似性检查,或者我们可以使用数组中间的像素值

Fig 4: Face of a cat — Our rough image

现在,我们的粗糙图像也将像我们的主图像(必须分类)一样,以数字或像素值的形式存储在计算机中。

对于第二个问题,有没有办法做两幅图像之间的相似性检查,换句话说,在大矩阵(原始图像)和小矩阵(粗糙图像)之间?是啊!我们有东西可以代替我们。在数学上被称为 Frobenius 内积。不要害怕。我将解释它是什么和它做什么。

Frobenius 内积无非是 两个数组按元素相乘后再加运算。假设你有下面两个网格或矩阵,我们称它们为 AB ,如下所示,那么弗罗贝纽斯内积(FIP)将计算如下。

Fig 5: Frobenius Inner product

Frobenius 内积,总的来说,是你衡量两个事物(矩阵)相似度的方式之一。它只不过是点积的一般化版本,只有一点不同:点积是为向量定义的,内积是为矩阵定义的。它如何准确地测量相似性超出了本指南的范围,但是如果你想详细了解相同的内容,那么请随意查看这篇博客文章这篇文章以了解内积。

现在我们有了两个图像(粗略的和主要的)和一种方法来衡量两个矩阵或图像之间的相似性。酷!因此,让我们来看看我们的非常简单的管道来将图像分类为猫或非猫,它包括两个步骤:

  1. 选择需要分类的图像的中间部分
  2. 对所选区域和粗略图像进行相似性检查。如果它返回一个高值,那么主图像是一只猫。

但是这个管道或者我们的图像分类器对下面的图像有效吗?

Fig 6: Images of cats, Source:bit.ly/2DkrlZd

不,一个大大的不!它对这些图片不起作用,因为上面的图片中间没有猫的脸。这将导致两幅图像之间的相似性降低,这意味着不正确的分类。我们能解决这个问题吗?是的,我们可以。我们不应该只关注图像的中间部分,我们应该做的是对主图像的每个部分与粗糙图像进行相似性检查,这将使我们的图像分类器具有全局平移不变性,这意味着人脸或图案位于图像中的哪个位置并不重要,我们的图像分类器肯定会检测到它。最后,结果将存储在输出矩阵中,我们必须对主图像的每个部分重复这个过程。请注意,选择主图像的特定部分的方向将是从左到右和从上到下。我们在主图像上移动粗略图像的步数或单位数称为步距。现在,让我用下面的图形和伪代码更清楚地说明这一点。

category = None
for selected_part in (each part of main image):
    1\. calculate the similarity between selected part and rough part
    2\. if similarity == HIGH:
    3\.     category = cat
if category == cat:
     print("Cat is present in image")
else:
     print("Cat is not present in image")

Fig 7: Convolution operation with stride = 1 and no padding | Source : bit.ly/2kDIN1O

看起来很简单也很有前途。这种在主图像上卷积粗糙图像的特定过程被称为卷积运算(线性运算),它非常直观,因为它只是通过计算两个矩阵之间的 Frobenius 内积来检查主图像中的某些特定模式。这个过程的结果将是另一个矩阵,它存储了粗略图像和我们的主图像的每个部分的相似性分数。

你有没有注意到一些非常有趣的事情?我们的输出矩阵或特征图的尺寸将总是小于主图像的原始尺寸。不是吗?如果你不服气,我建议你仔细看看上面的操作。但是,如果您想保留主图像的大小,以便即使在操作之后也能保留主图像的大部分信息,该怎么办呢?有什么办法可以做到呢?是的,有。为了保持输出图像的尺寸,我们简单地用零填充主图像的边界,这个过程被称为填充。

Fig 8: Zero padding, Source: bit.ly/2rK7fAM

现在,是时候让我给你介绍一下深度学习社区中已知的这些矩阵的名称了。形式上,粗糙图像被称为特征检测器滤波器,我们正在进行相似性检查的主图像的特定部分被称为感受野。输出矩阵被称为激活或特征图

到目前为止一切顺利。是时候感谢我们自己了,我们已经走了这么远,并建立了一个图像分类器,它可以在单个内核的帮助下检测主图像中的特定模式。让我们再走一步,尝试使我们的图像分类器对各种不同类型的图像更加鲁棒。我们的图像分类器适用于以下图像吗?

Fig 9: Images of cats, Source:bit.ly/2DkrlZd

同样,答案是否定的,这背后的原因很简单。上面图片中猫的脸和我们选择作为内核的猫的脸是有区别的。即使图像中某个对象的颜色或形状发生很小的变化,也会改变数组的值。那么,这种差异就足以导致我们的分类器出现不正确的分类。我们必须解决这个问题。我们必须通过使我们的分类器更加健壮来解决这个问题。我们不能只使用一种特定的模式对每张图片进行分类。我们的分类器还应该对猫的脸部轻微旋转、变形或出现任何其他图案的图像进行分类。因此,非常需要多个内核或特征检测器,因为我们不能只依赖一个内核。我们应该有不同的内核来识别图像中的不同模式。这样,它将提高我们的图像分类器的性能。

因此,现在我们将对之前的卷积运算进行修改,它包含以下三个部分:

  1. 输入体:可以是深度为 3 (RGB)的图像,也可以是之前卷积运算的输出。
  2. 特征检测器矩阵:这将构成 K 个内核来检测各种模式。
  3. 特征图:这将是卷积运算的输出,它将简单地存储相似性值。

形式上,这三个组件的组合被称为单个卷积层。而如果你在琢磨这次卷积运算会怎么做。下面仔细看看。

Fig 10: Convolution operation in case of multiple kernels and input depth > 1, Source: bit.ly/2PnUwSr

现在,我们的图像分类器可以检测图像中任何位置的各种特征。看起来我们做得很好。但是仍然需要改进。我们不能减少工作量吗?注意这里的一件事,我们手动定义我们的特征检测器,这个特定的内核应该检测这个特定的特征。这总是可能的吗?作为人类,我们能够识别构建分类器所需的所有模式吗?这可行吗?答案是不,我们不能。但是,我们能让我们的计算机足够智能来学习特征检测器本身吗?是的,我们可以。我们将利用现代计算机的计算能力,通过机器学习,用大量带有各自标签的图像来训练我们的机器。然后,它将自己识别各种特征检测器,以建立鲁棒的图像分类器。如果这对你来说没有多大意义,我会建议你去看看这个博客

我们一致认为,我们的机器将足够智能,能够自己学习特征检测器,并将能够在图像的任何位置检测多个特征,但这里有一件更重要和关键的事情需要理解:你的机器将像你一样学习这些特征检测器。我这么说是什么意思?还记得你是如何学习英语或其他概念的吗?首先,你已经学习了字母,然后是单词,从这里开始,你可以学习如何收集有意义的单词,也就是句子。我们作为人类以一种分等级的方式学习。机器也将模仿我们的学习方式,它不会直接学习更高层次的特征,如猫的脸、手或人的腿。但首先,它将学习非常低级的特征,如检测图像中的水平边缘、垂直边缘或颜色的特征。从那里,它将学习更高层次的特征,如脸、手和形状。因此,这清楚地表明我们的图像分类器将不仅具有单个卷积层,而且具有多个卷积层。

引入非线性

你有没有注意到,随着我们的进步,我们正在推出一个更好的图像分类器版本?在上一节中,我们了解到我们的分类器应该有多个卷积层,以便以分层的方式学习。这意味着我们的分类器的结构如下:

CONV LAYER--> CONV LAYER--> CONV LAYER --------> CONV LAYER

召回!我们之前已经了解到卷积是一种线性运算,简单来说就是,不管你在分类器中引入多少层,它只会学习线性函数。即使您在网络中添加 100 个层,它们都将作为单个卷积层。是的,100 Layers == 1 Layer不相信我?好吧。让我借助简单的线性方程来阐述一下。

Fig 11: Linear Equations (Captured by me)

从“u”到y的转换由 3 个线性方程完成,但如上图所示,这也可以由一个线性方程60u+31完成,即Power(3 linear equations) = Power of 1 linear equation

因此,我们必须在卷积层之间引入非线性,原因如下:

  1. 学习复杂和非线性函数来分类图像。
  2. 通过保护100 Layers == 100 Layers使我们的网络更加强大

如今在深度学习社区中常见的非线性函数或激活函数ReLU(校正线性单元)。

Fig 12: ReLU Function, Source: bit.ly/2uPTxNx

可以把 ReLU 函数想象成一个接受任何数字的盒子,如果是正数,它将给出输出 0 或数字。下面的代码将使它更加清晰。

def relu(x):
    if x < 0:
        return 0
    else:
        return x

因此,引入激活函数将使我们的图像分类器更加鲁棒,并将帮助它学习非线性决策边界,但这不是强制性的,您应该只使用 ReLU 作为激活函数。你可以自由使用任何非线性函数。要了解更多关于激活功能的信息,请随意阅读这个博客

池化:使其更加健壮和高效

到目前为止,在本指南中,我们更多地关注图像分类器的鲁棒性,但现在,让我们也关注分类器的效率。我们的分类器的输入是一幅图像。对吗?并且它的大小可以根据手头的问题而变化。图像的形状可以是28x2864x64128x128256x256。图像的尺寸越大,我们的图像分类器中的参数数量就会越多。深度学习社区中众所周知的一个事实是参数数量越多,你的模型就越容易过度拟合,需要更多的时间来训练。因此,没有任何方法可以解决这个问题吗?是的,有。我们可以使用称为池化的操作来减少输入体积的形状。

汇集是一种非常简单的操作,它通过用单个值替换非常小的子数组来对输入形状进行子采样或下采样,并且该单个值通常是该小子数组的汇总统计。下图将使其更加清晰。

Fig 13: Pooling operation | Source: stanford.io/2Td4J2d

在上图中,红色的数组是我们的子数组,蓝色的小矩阵是池化操作的输出。用2x2数组减少20x20数组将导致进一步卷积运算中参数数量的急剧变化。这个小的子数组被称为内核,而步幅的概念也适用于此,并在决定您希望内核移动多少步时发挥作用。我们可以使用任何汇总统计数据将其替换为一个数字,这可以通过从子数组中取最大值来完成,称为 Max-Pooling ,或者我们可以取子数组值的平均值,称为 Average-Pooling

Fig 14: Various Pooling operations | Source: bit.ly/2K5zlP2

我们将利用池操作来缩减输入体积的大小,但是池操作还有一个更有趣的地方。在池中,我们用单个值替换小的子数组,这意味着我们不太关注特征检测器操作的结果的确切位置。相反,我们缩小一点,并要求该子数组的近似结果。这将使我们的图像分类器对局部平移不变量具有鲁棒性。下面的例子肯定会有帮助

Fig 15: Images of different faces with different spacing

【以上是三张不同的人脸图片,略有不同。如果你仔细注意,两对眼睛之间的间距和眼睛与鼻子之间的间距是不一样的,但我们仍然希望我们的图像分类器能够完美地对所有这些人脸进行分类。但是我们对图像分类器还有什么期望呢?我们希望我们的人脸检测器内核不要关注眼睛和鼻子的确切相对位置,而是检查是否有一只眼睛在左边,一只眼睛在右边,鼻子在中间,后面是嘴唇,如果满足以上所有条件,则将其声明为人脸。这正是池化操作帮助我们实现的目标。因此,池主要执行两个功能,现在您已经知道这两个功能了!

我们图像分类器的最后一个组件

我们已经完成了最困难的部分。现在,让我们覆盖最简单的一个,使我们的分类器充分工作。它会给我们一个单一的数字,通过它我们可以保证这个图像是一只猫,对吗?但是,你注意到另一件事了吗?到目前为止,我们已经覆盖的所有层的输出都是形状(width,height,depth)的,但我们感兴趣的是一个单一的数字,它可以告诉我们一只猫是否出现在图像中。那么,我们如何实现这一点呢?我们如何利用存在于先前层的输出体积中的所有神经元,因为这些神经元将告诉我们特定特征是否存在于图像中?我们如何智能地将那些神经元的信息组合起来,得到一个单一的数字?首先,我们必须执行一个名为Flattening的操作,这样我们就可以智能地利用所有这些神经元来获得这个数字。展平是一个非常简单的操作,它将形状为(width,height,depth)的输入体积转换为形状为(K,1)的一维数组,其中K=width*height*depth

Fig 16: Flattening operation | Source: https://bit.ly/2AUN6Mq

现在,我们有一个一维数组作为图像分类器的输出,到这一部分,我们的分类器充当了特征提取器。它从图像中提取出有意义的信息,这将在确定图像中是否存在猫的过程中发挥至关重要的作用。现在,我们必须利用这些有意义的信息来得到一个单一的数字。这将由称为全连接层的层来完成,该层将前一层中存在的所有神经元连接到下一层中的所有神经元。

如果你知道简单的神经网络(没有任何花哨的层),那么连接多个具有不同数量神经元的全连接层就相当于在基于深度学习的特征提取器之上堆叠一个简单的神经网络。不是吗?下图将进一步阐明这个概念,它也将帮助你理解一维数组如何被转换成一个单一的数字。

Fig 17: Fully connected layer | Source: bit.ly/2JaVD0w

恭喜你!借助我们的直觉,我们已经完全开发了成熟的基于深度学习的图像分类器。我们已经介绍了这种基于深度学习的图像分类器的每一层,很明显,在所有这些层中,最重要的一层是卷积层,因此这种分类器被称为卷积神经网络

Fig 18: Convolutional Neural Network

第 2 部分:卷积神经网络的作用

我们已经非常详细地了解了卷积神经网络。让我们转换一下模式。现在,足够的理论和直觉。让我们实现我们到目前为止学到的所有东西,并建立一个端到端的 LeNet 架构,这是第一个由 Yann LeCun 提出的 CNN 架构。然而,还有许多其他 CNN 架构,你可以在这里阅读。LeNet 架构中各层的排列如下:

Input -> Conv -> Activation -> MaxPooling -> Conv -> Activation -> MaxPooling -> Flattening -> FC -> FC

我们将使用 CNN 将手写数字分为 10 类中的一类。我们将使用的数据集是MNIST Database,看起来像

Fig 19: MNIST Dataset — Hand Written Digits | Source: bit.ly/2InhIcI

现在,让我们使用 Keras 在 python 中实现我们到目前为止学到的所有东西。

第 1–10 行:我们已经导入了所需的类,这些类将进一步用于实现 LeNet 架构。

第 13 行:将 MNIST 数据集加载到四个变量((x_train,y_train), (x_test,y_test))

第 15–18 行:这些行将打印出训练和测试数据集的形状。

第 21 行和第 22 行:它们将通过将图像的每个像素的范围从 0–255 转换为 0–1 来标准化输入图像。

第 24–25 行:执行 一次热编码 ,这基本上是为了明确地告诉我们的模型,类之间没有顺序关系。

第 27 和 28 行:它们将把数据(训练和测试)从(data.shape[0],28,28)整形为(data.shape[0],28,28,1),这将用于表示卷积层的输入图像的通道数。

第 38–49 行:这些行将定义 LeNet 架构。为了实现这个架构,我们使用了 keras 的Sequential API(第 38 行)。网络的第一个隐藏层是具有 30 个大小为(5,5)的滤波器的卷积层,接着是 ReLu 激活层,然后是池大小=(2,2)的 MaxPooling 层,堆叠在前一层的顶部。这 3 层的组合根据架构再次重复。在三层的这两个块之后,由展平层(第 47 行)进行展平操作,然后将两个全连接层附着 500 和 10 个神经元(第 48 和 49 行)。

第 52 行和第 53 行:这些行将定义所需的优化器,该优化器将用于训练 CNN(第 52 行),而第 53 行将编译定义的模型,其中categorical crossentropy作为损失函数,accuracy作为监控度量。

第 56 行:它将负责训练我们的 CNN(真实的东西)以 10 为纪元数。

第 59–63 行:这些行将用于评估经过训练的模型,通过计算测试数据集的对数损失值和准确性,帮助我们检查我们的模型在未知数据上的表现。

如果您将执行上述代码,您将获得以下输出。

Accuracy of our model is 97.008%
Log loss value : 0.079

因为我们的模型的准确度大约等于 98%,并且对数损失值等于 0.079,这是非常好的。

希望这一节能让您体会到 python 中卷积神经网络的实现细节。现在,让我们转到这本纳米书最激动人心和最重要的部分,以更好地理解卷积神经网络。

第 3 节:使用 ConvNets 来更好地理解它们

在深度学习社区中,大多数人将卷积神经网络视为“黑盒”,而没有太多关注它们如何做它们所做的事情。在本节中,我们将研究卷积神经网络,并主要关注卷积神经网络的可视化方面。通过研究一些最重要和最有趣的论文,我们将对 CNN 有更多的了解,但同样通过问一些有趣的问题。这一部分将包括深度学习社区中大多数人不经常讨论或不知道的所有细节。希望你也能学到新的东西。你兴奋吗?我知道你是!

3.1:可视化中间输出

我们非常清楚,从输入层到输出(softmax)层,卷积神经网络中存在许多层。当我们通过网络前馈一个图像时,如果我们能够可视化每一层所做的转换或每一层的输出,这将是一个有趣的练习。这个练习将帮助我们了解每一层到底对输入图像做了什么。这正是论文作者所做的: 通过深度可视化理解神经网络 。如果你想看看这个东西的运行,你可以使用他们开发的工具,可以在这里找到。

Fig 20: Output of various intermediate layers | Source: video.

3.2:在给定 CNN 代码的情况下重建图像

在前面的小节中,我们已经尝试了在图像通过网络时可视化中间层的输出,中间层的输出也称为该特定层的图像的encoding。但是,除了可视化中间层的输出,是否有可能使用图像的编码来构造原始图像?是的,这是可能的,这在论文中有广泛的论述: 通过反转 来理解深层意象表征。本文作者通过提出以下问题对包含在中间表征中的视觉信息进行了直接分析:给定图像的编码,在多大程度上可以重建图像本身?

他们使用的方法很简单。他们将这个问题设计成一个最优化问题,该问题将计算图像表示的近似逆,使得图像的原始表示(φ(0))和我们试图找出的表示(φ(x))之间的差异或损失应该是最小的。

Optimization problem

这里,x 代表我们试图寻找的图像,φ(0)是中间层的输出或图像的编码,φ(x)是我们试图寻找的图像的编码,loss(φ(x),φ(0))是两种编码的差,λR(x)是正则化项。他们用来测量两种编码之间差异的损失函数是Euclidean distance,数学上看起来如下:

Loss function: Euclidean distance

下面是对应于不同层的编码的单个图像的反转表示的图像。

Fig 21: Result of the inverse of image representations of different layers, Source: paper

从上面示出的结果中,非常清楚的是,与从远离输入层的层构建的图像相比,使用更靠近输入层的层的编码的图像重建包含更多的视觉信息。

3.3:图像的哪个部分负责分类?

到目前为止,我们已经就图像中对象的存在负责图像分类器的输出这一事实达成一致。例如,图像中猫的脸的存在将负责图像分类器的输出。但是我们怎么能确定呢?如果分类器基于周围环境而不是基于猫的脸的存在将图像分类为会怎样?主要有两种方法可以确定,第一种是遮挡实验,第二种是通过使用显著图

3.3.1:遮挡实验

这种方法最早是在马修·泽勒的 可视化和理解卷积网络 中提出的。在这种方法中,他们用灰色方块遮挡图像的特定部分,然后监控该图像的分类器输出。他们通过从上到下和从左到右滑动灰色框,为图像的每个可能部分完成了上述步骤,与我们在卷积运算中在输入图像上滑动小子阵列的方式相同。

这个实验有什么值得期待的?

当我们遮挡图像的不太重要的部分时,图像分类器的输出(概率)应该不变,但是当我们用灰色方块替换主要对象时,概率应该显著下降。下面是这个实验结果的图片。

Fig 22: Result of occlusion experiment, Source: paper

因此,我们现在可以确定,图像中对象的存在负责图像分类器的输出。

3.3.2:显著性图

这种方法首次在 深入卷积网络中引入:可视化图像分类模型和显著性图 。这是一种非常简单的方法,上面提到的论文的作者试图知道图像的哪组像素对于分类的输出是重要的。他们试图观察一个非常简单的事情,即如果我们一个接一个地改变图像的像素值,那么多少和哪个像素组将最大程度地影响该图像的类得分?这背后的原因非常简单,即与对象相对应的像素集比其他像素集更能影响类得分。

他们已经通过简单地计算图像的输出分数相对于图像的梯度(Score(Ic))来做到这一点。

w = ∂Sc /∂I:类别分数相对于图像的梯度。*

Fig 23: Images with their corresponding saliency maps, Source : paper

具有较高梯度值的像素组在上面的图像中被突出显示,这表示这些是图像中最重要的像素,因为这些像素的值的微小移动或改变可以极大地改变类别分数。因此,它清楚地告诉我们,图像中对象的存在是分类器输出的原因。

3.4:我们的假设对吗?

毫无疑问,卷积神经网络的骨干是卷积层,它由许多内核特征检测器组成,这些检测器寻找图像中某些特征的存在,如果该特征存在于图像中,则反过来用大数字进行响应。这是我们已经在这本纳米书中涉及的内容。

我们的整个直觉和解释是基于最重要和唯一的假设,即卷积层中存在的子阵列充当特征检测器,但事实真是这样吗?我们如何确定子阵列充当特征检测器?有什么方法可以确定这一点吗?你打赌,有。这将是这本纳米书的一个非常重要的部分,因为它将检验我们关于 ConvNets 的假设,这是整本纳米书的基础。用于确定这一点的方法主要分为两个阵营,一个是以数据集为中心,另一个是以网络为中心。

3.4.1:以网络为中心理解 CNN

与同样需要数据的以数据集为中心的方法不同,以网络为中心的方法只需要经过训练的卷积神经网络。本文首先介绍了一种主要且有效的以网络为中心的方法: 通过深度可视化理解神经网络

在这种方法中,该论文的作者做了一件非常简单的事情,即他们试图通过强加一个优化问题来可视化激活,该优化问题将试图构建一个输入图像,使得任何层上存在的任何激活的值都应该是最大的。

这里, x 是要构建的输入图像, ai(x) 是第 I 个激活的值, Rθ(x) 是正则化项。

最大化特定激活的值将导致图像(x)的构造,该图像将包含与该激活相关的视觉信息。下面的图片将帮助你将使用这种方法构建的不同层的不同激活的输出可视化。

Fig 24: Visualization of different activations of different layers, Source: paper

3.4.2:理解 CNN 的以数据集为中心的方法

以数据集为中心的方法需要经过训练的卷积神经网络和通过该网络运行的数据(图像)。其中一个主要的以数据集为中心的方法首先是在马修·泽勒的 可视化和理解卷积网络 中介绍的。在这篇论文中,他们介绍了一种可视化技术,揭示了在模型中的任何层激发或激活单个特征图的输入刺激(输入图像的一部分)。为了做到这一点,他们利用了去进化神经网络,它可以被认为是一个使用相同组件(池化、非线性)但顺序相反的 convnet 模型。但是你会问 deconvnet 是做什么的,它将如何帮助我们?当输入图像通过网络传递时,我们获得了激活图作为中间层的输出,当我们将 deconvnet 附加到每个激活图时,它将这些活动映射回输入像素空间。将特定激活映射回输入像素空间将在输入像素空间上形成该激活正在寻找的图案。

本文中的以下摘录和图表不言自明,有助于您更好地了解 deconvnet 和一般使用的方法。

为了检查一个 convnet,需要将一个 deconvnet 连接到它的每一层,如图 1(上图)所示,提供一条返回图像像素的连续路径。首先,将输入图像呈现给 convnet,并计算各层的特征。为了检查给定的 convnet 激活,我们将该层中的所有其他激活设置为零,并将特征映射作为输入传递给附加的 deconvnet 层。然后,我们连续地(I)取消 pool,(ii)校正和(iii)过滤,以重建引起所选激活的下层中的活动。然后重复这一过程,直到到达输入像素空间。

Fig 25: Deconvolutional neural network

现在,让我们看看上述实验的结果,并试图理解不同层的激活在寻找什么。

Fig 26: Visualizing the activations of Layer 1 and 2

Fig 27: Visualizing the activations of Layer 3

Fig 27: Visualizing the activation of Layer 4 and 5

从上面显示的图像中可以清楚地看到,靠近输入层的层正在寻找较低级别的特征(如角、边、颜色),而远离输入层的层正在寻找较高级别的特征(如狗脸、键盘),从而证实了我们的另一个假设,即卷积神经网络以分层的方式学习。

在纳米书籍的最后也是最重要的部分,我们已经研究了卷积神经网络,并通过回顾 CNN 的四篇最重要的论文对它们有了更多的了解,这些论文也考虑了可视化方面。希望你也像喜欢其他部分一样喜欢这个部分。

我希望你喜欢这本纳米书的每一个部分,如果你从书中学到了什么新东西,那么你可以通过与他人分享来表达你的爱。花了这么多时间来写这么全面的博文,希望我的努力能帮助你们中的一些人理解卷积神经网络。

欢迎在 LinkedIn 上与我联系,在 TwitterQuora 上关注我。

用移动平均法确定板球比赛中击球手的状态

原文:https://towardsdatascience.com/https-medium-com-satnalikamayank12-using-moving-averages-to-determine-batsmen-form-d165c08be809?source=collection_archive---------0-----------------------

尝试在板球领域使用简单的算法交易策略来确定击球手的当前形式。

滚动平均值:它是从数据值的连续段中得到的一系列平均值,或者更简单地说,平均值是通过取一些前几天的值计算出来的,比如说过去 10 天(对于短期移动平均值)或者过去 50 天(对于长期移动平均值)。第二天的移动平均值通过排除第一天的值并包括今天或当前日期的最新值来计算。10 日均线是通过找出前 10 天的收盘价作为第一个数据点。下一个数据点将删除最早的价格,添加第 11 天的价格,然后取平均值。MAs 最常见的应用是识别趋势方向,即价值是上升还是下降。

股票交易中的交叉策略:投资者使用移动平均线作为指标来检测股票价格的运动,即它是上涨还是下跌。涉及均线的一个基本策略是交叉技术。

取 2 MA 的一个长期(比如 50 天)和一个短期(比如 10 天)。交叉点是曲线相交的点,即短期移动平均线高于长期移动平均线的点,反之亦然。

当短期移动平均线越过长期移动平均线(短期移动平均线>长期移动平均线)时,买入信号被触发,这表明股价开始上涨。同样,当短期均线穿过长期均线下方时,就会触发卖出信号(短期< Long Term MA) indicating prices are starting to go down and the investor should steer clear from the stock and sell the stocks if any.

将其应用于击球手:击球手通常被称为状态良好(表现良好)或状态不佳(表现不佳)。可以用股票市场和板球生态系统来进行类比,玩家类似于股票公司,他们的得分类似于股票价格。在板球比赛中使用的策略没有什么不同。我们计算 2 个 MAs:一个短期(比如 4 局)和一个长期(比如 15 局)。我们用击球手在特定局中的得分来代替价格。

如果有一个交叉,其中短期移动平均线变得高于长期移动平均线,这表明击球手将处于良好状态,并将在接下来的几局中取得好成绩,并将处于良好状态。类似地,如果出现交叉,短期移动平均线变得低于长期移动平均线,击球手在接下来的几场比赛中表现不佳。

导入所需的模块

import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
%matplotlib inline

读取记录并计算 15 局(长)和 4 局(短)的移动平均值。

df1 = pd.read_csv("51880batting.csv")
#player 51880 from statsguru is Chris Gayle
maLong  = df1['runs'].rolling(window = 15, center = False).mean()
maShort = df1['runs'].rolling(window = 4, center = False).mean()

绘图:

plt.plot(df1['runs'].rolling(window=15,center=False).mean(),color = 'k')
plt.plot(df1['runs'].rolling(window=4,center=False).mean(), color= 'g')
plt.show()

Long Term and Short Term MAs for Chris Gayle (WI Batsman)

Long Term and Short Term MAs for Virat Kohli (IND Batsman)

如果短期均线大于长期均线(相当于买入信号),找出交叉点,计算接下来 3 局的平均值。

sp = 0 
snp = 0
playCnt = 0
noplayCnt = 0
x = 15               #long term averages begin from index 15
while( x <= 260):    #number of innings is 263 
 if(maLong[x] < maShort[x]):
  if(maLong[x+1] > maShort[x+1]):   #crossover detected
    print ‘no play at’ , x
    snp= snp +df1[‘runs’][x+1] + df1[‘runs’][x+2] + df1[‘runs’][x+3]
    noplayCnt = noplayCnt+3

 if(maLong[x] > maShort[x]):
  if(maLong[x+1] < maShort[x+1]):   #crossover detected
   print ‘play at’ ,x
   sp = sp + df1[‘runs’][x+1] + df1[‘runs’][x+2] + df1[‘runs’][x+3] 
   playCnt = playCnt+3
 x = x+1

计算和显示平均值:

#overall career average
overallAvg = df1[‘runs’].mean()#average over the next 3 innings after positive or 'BUY' signal
playAvg = sp/playCnt#average over the next 3 innings after negative or 'SELL' signal noPlayAvg = snp/noplayCnt print 'Career average: ', overallAvg
print 'Positive Signal average: ', playAvg
print 'Negative Signal average: ', noPlayAvg 

克里斯·盖尔的结果

职业生涯平均:34.928030303
正信号平均:48
负信号平均:32

Virat Kohli 的结果:

职业平均:45.0595238095
正信号平均:59
负信号平均:30

在击球手状态良好的比赛中,平均得分(48 分和 59 分)分别比职业生涯平均得分(35 分和 45 分)高得多。这可能会进一步发展使用 WMA(加权移动平均),其中最近几局被赋予更高的权重年龄,同时计算平均值,我相信会给出更好的结果。

完整的代码和数据集,请访问我的 Github 简介

所用数据来源于criinfo stats guru

要进一步了解移动平均线和交叉策略,请访问 Investopedia 上的链接。

如果你喜欢这篇文章,请点击下面的小心形按钮。

泰勒·斯威夫特 vs 人工智能:谁更胜一筹?

原文:https://towardsdatascience.com/https-medium-com-sh-reya-taylor-swift-or-artificial-intelligence-19f2989ab7a4?source=collection_archive---------6-----------------------

我从小就是泰勒·斯威夫特的超级粉丝。我的中学 iPod Nano 的顶级播放歌曲都是从 讲到现在 。记得高二的时候趁父母熟睡,熬夜浏览 Tumblr,想找T5【红 的样品,因为没钱买专辑。

很自然地,我上周每晚都熬夜,急切地期待着泰勒新专辑的预告曲。但是当“看你让我做了什么”出来打破 YouTube 记录的时候,我有点……失望。不要误会我的意思——我还是听了至少二十遍。但是泰勒那铿锵有力的歌词和朗朗上口的旋律后来怎么样了?为什么这首歌充满了仇恨和复仇?

过去的这个周末,我想看看机器学习(ML)技术能否为泰勒创作出更好的歌曲。我将泰勒所有的歌词输入一个递归神经网络(RNN),并采样了一些新歌词。这是我得到的(未经修改,直接从我的终端复制粘贴):

**

Two different samples generated with around 900 characters each.

在阅读了这些生成的歌词后,我得出结论,泰勒肯定更擅长创作自己的音乐。生成的歌曲语法怪异,许多单词拼写错误。大多数短语都没有真正的意义。左括号或引号有时不闭合。但是,嘿——令我印象深刻的是,RNN 能够学习用逗号、行长和换行来表达歌词结构!

为了结束这个有趣的实验,我用相同的 RNN 生成了可能的歌曲标题。以下是 ML 生成的声望中的歌曲标题:

围棋不会打到我那里

你的爱贯穿一切

我们说要变得更好

墙如果英里

没有对话

我应该这么说

我不想看到路

我不会把你留在这里

你想我吗

我们说我是如何

有好的塔夫绸吗

爱在那里

"有好的塔夫绸吗?"对我来说听起来有点奇怪。但是我可以看到自己被其中的一些卡住了,像“你的爱贯穿一切”或“我不想看到的方式。”

我想我会回去不耐烦地等待真正的名声在 11 月出来。与此同时,如果你有任何有趣的 AI 或 ML 想法可以尝试,请告诉我!

**技术细节:我分叉了安德烈·卡帕西的 char-RNNTensorflow 实现。我发现了一个不错的。包含泰勒·斯威夫特歌词的 txt 文件。我用的代码这里是这里是。该模型基于 LSTM,有 3 层,隐藏状态大小为 12。应用辍学。我没有做任何超参数测试,所以肯定有改进的空间。

区块链和数字身份

原文:https://towardsdatascience.com/https-medium-com-shaanray-how-blockchains-will-solve-privacy-88944f3c67f0?source=collection_archive---------2-----------------------

Digital Identity.

每当我们在互联网上交易时,我们都会留下全面的数字足迹。我们使用的平台越多,留下的数字痕迹就越多。处理金融交易的互联网平台包括 Paypal、信用卡处理器、直销银行、谷歌钱包、Apple Pay、亚马逊支付、Square、Stripe、Venmo 和加密货币。用户必须公开个人和财务数据才能使用这些服务。

一个人的数据通常存储在各种不同的数据库中,并在不同的时间生成。这些个人数据中的一些会随着时间的推移而变化(例如,居住地址),因此在数据库之间并不相同。结果是一个人的多个“数字克隆”存在于不同的数据库中。

当前的身份管理系统存在许多问题。用户在几个在线平台和网站上输入数据和注册,并且必须创建和记住大量密码。人们不能同时更新他们所有的凭证和数字身份。这破坏了安全性和便利性。此外,正如 Equifax 黑客事件所显示的那样,不良分子只需侵入一个主要数据库,就能获取每个用户的信息。

简而言之,当前的数据身份实践是不可持续的。

Similar but not the same.

政府 id

爱沙尼亚和印度政府已经试验了集中式数字身份证。个人身份证可以用来投票、报税、从银行提款、登记财产以及遵守其他政府报告要求。由于数字身份证是由政府颁发的,收集的信息存储在一个中央数据库中。数据的集中存储会产生单点故障。为了保证此类数据的安全,需要实施极其严格的控制和协议。

A specimen government ID.

区块链解决方案

区块链技术以去中心化、可信和不可变的方式存储数据。区块链可以确保用户的单一数字身份存储在一个安全和廉洁的方式。这种单一的数字身份可以始终与最新的用户信息保持同步。

鉴于这一潜力,各公司正争相开发基于区块链的数字身份管理和认证解决方案。这个领域的早期参与者包括 Bitnation、Civic、Cambridge Blockchain LLC、BlockAuth 和 Existence ID。

Bitnation 的治理平台寻求提供与政府相同的服务。它的用户被称为比特国家的“公民”。

专注于减少欺诈和防止身份盗窃的 Civic 去年 7 月推出了极其成功的 ICO。

Cambridge Blockchain LLC 正在与金融机构合作开发一种直观、用户友好的数字身份解决方案,该解决方案完全符合隐私法规。为了赢得企业客户的信任,解决方案必须强大。

IBM 和 SecureKey Technologies 也为消费者推出了一个基于区块链的数字身份网络。它将建立在 Linux 基金会的 Hyperledger Fabric v1.0 之上。Hyperledger Fabric 是一个许可的区块链(这意味着其网络参与者可以限制谁可以参与区块链的共识机制)。许可的区块链将允许用户分配谁可以访问他们的数字身份数据的权限。

Early movers working on blockchain enabled digital identity solutions.

网络效应

如果没有消费者的认可,任何数字身份区块链解决方案都无法为互联企业和机构所用。许多希望采用基于区块链的身份管理解决方案的行业都受到高度监管,例如银行、信用卡公司和医疗保健提供商。项目的数据隐私机制、节点的分布和开发团队将是成功的关键。

结论

未来,我们每个人都将拥有一个最新的数字克隆体。基于区块链的数据加密将防范身份盗窃。我们将能够跨不同的商务和合规事务渠道选择与谁共享哪些数据。哪些基于区块链的数字身份管理平台将达到临界质量并利用网络效应是一个开放的问题。

沙安雷

关注媒体上的 Lansaar Research ,了解最新的新兴技术和新的商业模式。

为什么使用上下文管理器是更好的选择?

原文:https://towardsdatascience.com/https-medium-com-sinister-why-using-a-context-manager-is-a-better-choice-55ccfcecddb8?source=collection_archive---------3-----------------------

每当我用 python 写几行代码时,脑子里总会冒出一个问题,有没有更好的方法来写这段代码!更好的方法不是在算法方法的意义上,虽然它很重要,实际上它是最重要的,像减少时间或空间的复杂性或两者都有!与其他人解决同样问题的方式相比,这是让你的方法占上风的原因。但是紧接着的下一个重要问题是,你是否按照它应该的方式写了它?

长话短说,有没有更 pythonic 化(当然也更好)的方法来编写同样的代码?

假设您应该将一些 json 数据写入一个文件。

显而易见的方法是打开文件,将 json 数据写入文件,然后关闭它。这种简单直观的方法只有在没有例外的情况下才是好的。

比方说,第 16 行产生了一个错误,可能是data不是一个有效的 json。在这种情况下,进一步的执行会停止,程序会立即停止。这里你应该注意到一件事,close()在第 18 行没有被调用。因此,文件描述符已经泄漏,数据很有可能会被破坏。现在,这是一个可怕的问题,尤其是如果您正在处理的文件对您所在的系统或业务组织至关重要。

那么,您应该如何解决这个问题呢?一个可能的解决方案是使用 try-except 块,它不仅可以捕获错误,而且在任何一种情况下,我们都有能力显式关闭文件。

然而,将代码放入 try-except 块大多数时候看起来很难看,更好更漂亮的替代方法是使用上下文管理器。

非常简单的语法如下

with context_manager as something:
     # do anything with something
     pass

这相当于 try-finally 块

something = expression
something.__enter__()
try:
    # do anything with something
    pass
finally:
    something.__exit__()

我们用with语句重写的函数现在看起来更干净了

我们不需要显式关闭文件,所有这些都由with语句负责。当然,在引擎盖下会发生一些事情。为了更详细地理解它们,让我们创建一个我们自己的上下文管理器。

我们的自定义上下文管理器是一个具有(特别是)以下两种方法的类:

  • __enter__()
  • __exit__()

在调用上下文管理器的过程中调用__enter__(),当with块的执行完成时,即在块的末尾,调用__exit__()方法来包装代码。所以任何你认为应该在with块的初始化阶段执行的东西都应该放在__enter__()的体内。__exit__()应该包含您希望在with块末尾执行的所有清理代码。即使在运行时遇到错误,也会执行__exit__()主体中的代码。这确保了清理动作被保证执行,就像在前面的情况中关闭文件一样,即使在调用json.loads()json.dump()的过程中有错误。

需要记住的一点是,with块中定义的变量有局部作用域,但是上下文管理器本身没有局部作用域(w.r.t. with块),因此可以重用。

上下文管理器可以用于其他目的,而不是简单的文件 I/O,比如打开和关闭套接字,在测试期间实现设置和拆除功能,以及超出我知识范围的事情。

我希望你喜欢读这篇文章,如果你有什么建议,请在评论中告诉我。最后,如果你觉得这篇文章值得你花时间,请点击推荐按钮,我认为如果你不动它,跟随 按钮会嫉妒的。感谢阅读,希望你学到了新的东西;——)

用于能源市场算法交易的机器学习框架

原文:https://towardsdatascience.com/https-medium-com-skuttruf-machine-learning-in-finance-algorithmic-trading-on-energy-markets-cb68f7471475?source=collection_archive---------1-----------------------

[image by Geralt on Pixabay]

人工智能的新突破每天都是头条新闻。远离面向客户的企业的嗡嗡声, 机器学习在金融 中的广泛采用和强大应用却鲜为人知。事实上,很少有领域像金融行业一样拥有如此多的历史、干净和结构化的数据,这使其成为“学习机器”取得巨大成功的早期案例之一,这种成功仍在继续。

大约三年前,我参与了开发机器学习(ML)模型,用于能源市场的价格预测和算法交易,特别是针对欧洲碳排放证书市场。在这篇文章中,我想分享一些我发现与我所有的 ML 项目相关的学习、方法和见解。我在这里关注的不是技术细节,而是建模选择背后的一般考虑,这在经典的学术教科书或在线新技术教程中很少讨论。—关于算法交易的例子,我提出了一些“交易技巧”,当你作为一个孤独的搜索者或与你的数据科学家团队一起将机器学习应用到合成例子之外的广阔世界的现实生活中时,你可能会发现这些技巧很有用。

上下文

在 2005 年《京都议定书》之后,欧洲碳排放证书(EU ETS)市场作为欧盟气候政策的主要支柱已经建立,通过“上限和交易”计划来调节欧洲大约一半的人为 CO2 排放。这一机制为各国政府提供了对温室气体排放总量的控制(“cap”),同时将排放权的有效分配让给市场力量(“贸易”)。基本想法是给污染定价:该计划覆盖的每个工业设施必须监控并向当局报告其温室气体排放的准确数量,然后通过上交配额来抵消各自的数量(以吨为单位)。这些“污染权”被拍卖或免费给予工业参与者,然后可以在场外交易或在中央市场交易,价格由供求关系灵活确定。由于环境政策的减排目标限制了年度许可证的总体供应,一些污染者被迫选择减少污染的措施(“减排”),例如在他们的烟囱中安装额外的过滤器。这些边际减排成本低于当前许可市场价格的污染者(例如,因为他们特定的过滤要求很便宜)可以在市场上出售他们的超额污染限额以获取利润,卖给面临更高边际减排成本的污染者。在一个完全有效的排放交易市场中,许可证的均衡价格将决定于最终减排单位的边际减排成本,该成本是实现许可证供应上限所设定的总体减排目标所必需的。

[Image by Pixabay via Pexels]

鉴于特定行业实际减排成本的不确定性,该工具允许政府控制排放总量,而排放许可的实际价格根据需求方市场力量波动,即

市场对未来政策变化的预期

即将进行的许可拍卖的规模,正在进行的拍卖的价格和覆盖率(见图 1)

市场参与者的投机

银行行为(一年内发放的许可证在同一政策阶段的所有年份都有效)

其他能源商品的价格关系。

为了举例说明后者,假设每单位热量的天然气价格低于布伦特原油的价格。电力生产商和公用事业公司将转向这种碳强度较低的燃料,从而降低对碳配额的需求。相应地,津贴的价格在这些时期也会下降(见图 2)。

Figure 1: Bullish signal from a highly covered auction at 2pm shortly breaking a bearish trend [image by author]

Figure 2: Positive 30day correlation of EUA with UK Gas in 2017 (absolute and normalized) [image by author]

一个全面的模型需要反映所有这些因素。虽然我们可以有把握地假设,在丰富的历史市场数据中观察到的模式会延续到现在,并将延续到未来(这实际上是任何分析建模的必要条件和不可或缺的假设),但很明显,对于任何试图基于一般信念、基本关系或经济物理学的状态空间概念对市场建模的方法来说,这种设置都太复杂了。

所以这真的是一个释放机器学习力量的用例。如何利用它?

以下是使用监督学习的交易系统的典型工作流程:

  1. 数据

把数据放好。金融时间序列的好来源是你想交易的交易所的 API, AlphaVantageQuandl 的 API。数据的规模至少应该和您想要建模并最终预测的规模一样小。你的预测范围是多少?更长期的视野将需要额外的输入因素,如市场出版物、政策展望、twitter 披露的情绪分析等。如果您在玩基于来自分笔成交点数据的纯市场信号的短期甚至高频交易游戏,您可能希望包括各种长度的滚动平均值,以便为您的模型提供历史背景和趋势,特别是如果您的学习算法没有像递归神经网络或 LSTMs 那样的显式存储单元。技术分析中使用的所有常用指标(如 RSI、ADX、布林线、MACD)都是基于某种数量(价格、交易量)的移动平均线,即使你不相信简单的交易规则,包含它们也有助于模型反映大多数市场参与者的交易行为。你的计算能力可能是一个限制因素,尤其是在你的 ML 模型将面对做市者或套利者的硬编码、快速和专用算法的情况下。部署专用的云服务器或 ML 平台,如 H2O 和 TensorFlow,可以让你将计算分散到不同的服务器上。清理数据(如何插入间隙?),绘制图表,玩玩它——你已经发现交易机会、趋势、异常了吗?

2。监督模型训练

将您的数据分成互补的集合,用于训练、验证(用于参数调整、特性选择等)和测试。这实际上比听起来更复杂:最理想的是,测试集应该尽可能“类似”于当前的“市场状态”,验证和测试集应该遵循相同的分布。否则,您可能会浪费精力在验证集上调整模型参数,却发现它很难推广到测试集。遵循“市场机制”的概念,即特定商品组合主导目标工具价格动态的延长期,首先让无监督学习的聚类算法发现数据中定义的相关性,然后评估属于相同聚类的验证和测试集中数据的模型性能,这可能是值得的(见图 3-在本项目中,聚类将预测性能提高了 8%)。

Figure 3 Coherent market periods as identified by a clustering algorithm (colored segments of EUA settle price) [image by author]

在早期,决定并建立一个单一的数字评估指标。追逐太多不同的指标只会导致混乱。在算法交易的背景下,一个合适的衡量标准是“损益”(PnL),因为它用波动的实际大小(“相关性”)来衡量分类精度(价格上涨/下跌)。它符合你可能考虑的交易政策的标准。在训练集和验证集上观察模型性能。如果训练集的误差,即“模型偏差”,很高,您可能需要考虑更多的模型参数(例如,通过在深度学习模型中添加更多的层/神经元)。如果模型泛化能力很差(“模型过度适应训练集”),即验证和训练集的性能差异(“模型方差”)很高,您可能需要向训练集添加更多数据,减少最相关的特征数量,添加正则化(例如 L2、L1 或下降)或提前停止(在梯度下降优化中)。仔细检查模型出错的案例将有助于识别任何潜在的和可避免的模型偏差,见图 4。

Figure 4 Error analysis — price move versus forecast confidence (>0.5: up, <0.5: down) [image by author]

确立你的目标绩效:对于市场预测,75%的分类精度实际上已经很不错了——比随机猜测(50%的精度)好 50%。该基线与其他 ML 应用程序(如在封闭环境中运行的对象或语音识别)非常不同,在封闭环境中可以清楚地识别影响建模目标的因素(图像像素的 RGB 通道、声音样本的波频率)。

3。交易政策

定义你的交易政策:定义模型输出的具体交易含义的一套规则:例如,取决于给定预测的模型置信度的阈值,你在市场上放置什么位置,什么位置大小,在给定的市场状态下你持有位置多长时间,等等。策略通常带有一些需要优化的自由参数(下一步)。在这里讨论的监督学习环境中,这是一个基于回溯测试和网格搜索的相当手工的过程(下面列出了一些缺点)。

4。回溯测试&优化

现在到了数字上——你的交易系统,或者说预测模型和给定交易政策的相互作用,在一组隐瞒的历史市场数据上表现有多好?这里,步骤 2(模型训练)中使用的测试集可以成为调整策略参数的验证集。遗传算法允许你探索政策空间,从第一代比如说 100 个随机选择的政策参数开始,迭代地消除 80 个表现最差的,并使 20 个幸存者每个产生 4 个后代。或者,您可以在多维参数空间中进行网格搜索:从策略参数的一些看似合理的值开始,通过逐个改变参数值,您可以实现的最佳性能设置是什么。在这里,你的绩效指标是你在交易策略中最终要优化的指标,如 PnL 或一些衍生的量,如投资回报、夏普比率(每波动风险的回报)、风险价值、贝塔系数等,见图 5。

Figure 5 PnL and Sharpe Ratio for various trading policies [image by author]

防止使参数过度适合验证集的一个好方法是使用“walk-forward-test”(WTF)进行交叉验证,以验证您的方法的健壮性:优化验证段上的策略参数,在验证段之后的数据上及时向前测试它们,向前移动验证段以包括该测试数据,重复。这里的基本假设是,与更久远的过去相比,最近的过去是对未来更好的衡量。

5。模拟&现场交易

在您的策略生效之前,冻结所有系统参数并实时测试,就像根据您的交易算法的输出实际下单一样。这个重要的步骤叫做纸上交易,是检验你的方法有效性的关键。您可能会注意到,在您的历史数据中,您实际上使用了在给定时间并不真正可用的值,例如在计算移动平均值时。如果你的策略看起来仍然有希望,那么恭喜你——是时候投入使用了!虽然您可能会从手动下单开始,但不要低估将您的策略与交易所的 API 集成在一起所需的管理和技术工作。

这里介绍的典型工作流程有一些严重的缺点:

对于衍生合约,如基础期货,历史数据通常报告一天或选定时间间隔内的开盘价和收盘价,以及在该时间间隔内实现的所有交易的合约平均价格。但这不太可能是你可以结清买入或卖出订单的价格,这取决于订单簿的动态,订单簿在不同的买入价/卖出价水平下有不同的交易量。所以你在第二步中的模型预测确实指的是一个理论价格,但可能不是你将要下注的价格。更详细的建模方法需要考虑订单簿的实际结构和动态

制定策略(步骤 3)不是基于机器学习的建模的一部分,而是由直觉、经验或简单的启发指导的手动过程。例如,当模型预测价格上涨时,你会下一个买入订单(“做多”)。但是你买多少份合同呢?你用什么信心阈值?面对不利的市场条件,你会持仓多久?

反馈姗姗来迟:你需要经历第 1-3 步,才能对你的策略表现有初步的了解。预测模型和策略的参数被独立优化,即使模型和策略实际上密切交互。在这个框架中探索政策参数的空间是通过低效的数值优化完成的,而不是通过你的预测机器学习模型的强大梯度优化。

强化学习的框架整合了上面的步骤 2 和 3,将交易建模为代理(交易者)与环境(市场、订单)的交互,以通过其行为(下单)优化回报(如回报)。虽然仍处于早期阶段,但最近的研究表明,这是一条值得探索的道路——“需要做进一步的研究”。

参考文献:

参见维基百科,排放交易中关于“总量管制和排放交易”机制的广泛讨论,以及维基百科,欧盟排放交易中关于欧洲市场框架的更多具体信息。

南 Smith,环境经济学(牛津大学出版社 2011 年)对环境政策的市场方法的历史和影响做了很好的介绍。

Denny Britz 的博客文章给出了更多关于指令书机制的细节,以及算法交易中强化学习方法的前景。

免责声明:上述项目是为减排资本有限责任公司承担的,该公司是一家专注于碳和其他环境商品的专有投资和贸易公司,同意以当前形式发布本出版物。本文表达的所有内容和观点的责任完全由作者承担。

作者:作为一名热情的数据科学家,我在过去四年里一直担任全球初创公司的技术主管,并实施现实生活中的人工智能解决方案。请通过 simon@deepprojects.de 联系我。

关于气候

原文:https://towardsdatascience.com/https-medium-com-stephaniewillis808-concerning-climate-5a6b923eb8eb?source=collection_archive---------11-----------------------

为什么我们不能放弃减缓气候变化,以及对迄今为止进展情况的分析。

Photo by NOAA on Unsplash

动机

当我想到气候变化以及我们可以做些什么来缓解它时,我常常会对这一切感到绝望。它看起来如此重要,却又如此难以解决。

排放大量的二氧化碳给了我们不可思议的生活方式。当我们排放时,没有即时的反馈机制——我们无法直接感受到排放的成本。更何况费用大多是其他人承担的。巨大的直接利益和缺乏直接的负面反馈使得我们很难说服自己或我们的政府来抑制排放。事实上是如此之难,以至于我认为放弃这份糟糕的工作并继续我们的生活是很诱人的。我们觉得我们的政府和行业没有机会做出必要的改变,以满足巴黎协定将全球变暖限制在“比工业化前水平高出 2 摄氏度以下”的目标——所以我们放弃了。

但是我们不应该。因为 2 C 比 3 C 好,3 C 比 4 C 好。我认为这是一个被忽略的关键点。排放的二氧化碳越多,温度就越高,后果就越严重。已故的大卫·麦凯——我的英雄——将二氧化碳排放量与时间的图表下的面积描述为等于“痛苦”。面积越大,苦难越多。因此,我们应该尽我们所能来限制这些排放和由此带来的痛苦,即使我们怀疑气温上升将达到 2 摄氏度。

在深入研究我们应该采取什么行动之前,我认为有必要了解我们现在的处境。气候变化已经造成了多大的破坏,还会造成多大的破坏?我们在减排方面做得怎么样?这些问题(以及我目前的失业和无限时间的状态)促使我做了一些研究和数据分析。总的来说,我尝试使用开源数据集来产生我自己的数据。有时我没有做到这一点,所以复制了其他人的数据——在这种情况下,我会在说明中这样说。如果你想在阅读文章时看到数据操作和绘图的代码,你可以在这里做

气候影响

政府间气候变化专门委员会的最新报告(T0)和最近公布的美国全球变化计划(US Global Change Programme)的气候科学特别报告(T2)描述了气候变化已经造成的影响。这些变化包括:从 1850-1900 年到 2003-2012 年,气温上升了约 0.78 摄氏度(气专委);1901-2010 年期间全球平均海平面上升约 19 厘米(气专委);世界大部分大陆地区极端温度和强降水事件的强度和频率增加。

这些报告还包括对不同排放情景下气候变化未来影响的预测。IPCC 使用了四种被称为“代表性浓度途径”(RCP)的情景。它们是 RCP2.6、RCP 4.5、RCP 6.0 和 RCP 8.5。名字中的数字代表“辐射力”——大气中的气体如何影响地球吸收的能量和辐射回太空的能量之间的平衡。这个数字越大,辐射进来和辐射出去的比例就越大——所以温度就越高。具体来说,这些数字与 2100 年每种情况下的辐射作用力有关。在这四种情况下,化石燃料使用和工业的二氧化碳年排放量如下所示。

Annual emissions of CO2 from fossil fuels and industry under the 4 RCP scenarios. Data and citations for scenario development here.

在 RCP 8.5 中,年度 CO2 排放量继续增加。高人口和适度的技术变革导致了长期的高需求和高排放。

在 RCP 6.0 中,二氧化碳年排放量在 2080 年达到峰值,然后下降。人口稳定,增长相对缓慢,经济的能源强度(二氧化碳排放量/美元)逐渐改善。

在 RCP 4.5 中,二氧化碳年排放量在 2040 年达到峰值,然后下降。缓慢的增长和随后的减排是通过大规模采用核能和碳捕获与封存(CCS)以及大规模植树造林来实现的。

在 RCP 2.6 中,二氧化碳年排放量在 2020 年达到峰值,然后下降,2070 年后变为负值。这一情景在很大程度上依赖于 CCS 和生物燃料的使用来实现碳负发电(通过种植植物,燃烧它们,然后捕获和储存过程中排放的 CO2)。这是一项未经证实的技术。

下图显示了每个 RCP 下预计的全球温度变化。显示的温度变化是相对于 1986-2005 年的平均值而言的。值得一提的是,这不是《巴黎协定》所指的“前工业化”基线。我对“前工业化”基线做了更多的研究,并在这里写下了相关内容。结论是,如果我们希望它们相对于工业化前的水平,我们需要将下面报告的温度变化增加 0.55°C 至 0.8°C。

Projected global temperature increase relative to 1986–2005 under each of the emissions scenarios as determined by multi model simulations. Time series are shown on the left for RCP 2.6 and RCP 8.5. On the right the projected temperature change to the period 2081–2100 is shown for all 4 scenarios. The solid line indicates the mean of multiple different models and the shading indicates the 5 to 95% range of the model outputs. This plot is taken directly from the IPCC’s latest report as I was unable to find a tractable data set from which to make my own plot.

Projected global temperature increase (°C) from 1986–2005 to 2081–2100 under the 4 scenarios. This table summarizes the key numbers from the plot above. ‘Mean’ in this context refers to the average result of many different climate models. The likely range of temperatures under each scenario is shown on the right. The IPCC uses the word ‘likely’ to describe something which has a greater than 66% probability of happening.

将 0.55℃和 0.8℃之间的温度变化加到报告的温度变化上,我们看到,即使我们遵循 RCP2.6,到 2010 年,我们可能会超过 2℃的变暖。在高排放情景下,变暖的规模和速度是可怕的。我不知道到 2100 年再变暖 3.7 摄氏度会是什么样子,但我对 0.78 摄氏度的变暖已经导致(饥荒、洪水、飓风)的痛苦有所了解。看着这些温度估计,我强烈希望我们远离 RCP 8.5。

现状核实

记住这些温度变化,让我们看看数据。在过去的几年里,毫无疑问,我们一直在努力减少二氧化碳的排放,他们取得了哪些成效?我们似乎在遵循哪种情景?

RCP 方案始于 2000 年。截至 2015 年,化石燃料和工业二氧化碳排放量的详细数据已经公布。因此,历史数据和“未来情景”之间有 15 年的重叠。这种重叠让我们能够弄清楚现实与场景相比是如何形成的。在下图中,我绘制了 4 种情景下的历史排放量和预测排放量。我已经用每个场景的平均温度上升估计值替换了场景名称(来自上表)。我发现温度变化的估计比辐射力的估计更容易理解。但是请注意,温度数值只是模型的平均输出。它们没有涵盖每种情况下可能的温度上升的全部范围。

Comparison of historical and projected annual CO2 emissions from fossil fuel use and industry. Each scenario is labelled with the average predicted increase in temperature between the period 1986–2005 and the period 2081–2100 under that scenario. For a explanation of why only emissions from fossil fuels and industry are being analyzed see the end of this article.

A zoomed in look at the previous figure. The intermediate emissions scenarios have been omitted for clarity.

令人沮丧的是,全球二氧化碳排放量似乎很大程度上遵循了 RCP 8.5——有增无减的增长情景。然而,最近排放量增长已经放缓,并偏离了 RCP 8.5 的设想。2015 年,尽管国内生产总值增长了 3%,二氧化碳排放量却下降了 0.1%,因此脱碳努力似乎产生了一些影响。

我们每年排放的准确轨迹不需要完全遵循这些情景中的任何一个——它们仅仅是一些可能的未来的指示。最重要的是二氧化碳的总排放量,而不是我们的排放量随时间变化的确切方式。下图显示了自 2000 年以来的累计排放量,并与各种情景下的累计排放量进行了比较。

Comparison of historical and projected cumulative CO2 emissions from fossil fuel use and industry. Each scenario labelled with the average predicted increase in temperature between the period 1986–2005 and the period 2081–2100 under that scenario. See below for a zoomed in version.

A zoomed in version of the previous figure. The huge cumulative emissions under the 3.7°C scenario dwarfs current emissions and makes current differences seem small. They are not! We saw in the annual plots that a year’s worth of emissions is of the order of 30 Gtonnes so the difference between the 3.7°C and the 1.0°C scenario is almost a whole years worth of global emissions.

所以我们的累积排放量超过了低温情况下的排放量。因此,将我们的年排放量与较低温度情景下的排放量保持一致是不够的。为了弥补我们已经做出的承诺,我们需要比这些情景所显示的更大幅度地减少我们的年排放量。这意味着我们越是拖延控制排放的时间,排放限制就需要变得越严格。我们需要想出如何大幅减少排放,而且我们需要尽快行动。如果我们不这样做,我们很可能会看到比我们目前敢于考虑的更大的温度上升。

在以后的文章中,我会更深入地研究几个主要国家的排放量,并试图找出不同的政策措施对二氧化碳排放量的影响。希望这些结果能告诉我们一些关于如何务实地向前推进,以最小化变得更热的程度。

后记:为什么只有化石燃料和工业排放的 CO2?

这项分析只关注化石燃料使用和工业过程中的二氧化碳排放。我没有研究其他人为的二氧化碳来源,比如土地使用的变化。除了二氧化碳,我也没有研究其他温室气体。RCP 方案包括对其他排放类型的预测,但我无法找到它们的最新历史数据集。因此,我在分析中省略了它们。为了了解这种忽略是否合理,我查看了人为温室气体排放的明细。下图显示了 2010 年的细分情况。

Breakdown of anthropogenic greenhouse gas emissions (gigatonne of CO2-equivalent (GtCO2 eq) per year ) in 2010. The equivalence of different greenhouse gases is based on their 100 year global warming potential — as calculated in the IPCC’s 5th Assessment report. Data is also from the IPCC’s 5th Assessment report Note that there are very large uncertainties about CO2 emissions due to forestry and other land use change.

化石燃料和工业排放的二氧化碳构成了大部分人为温室气体排放。土地使用变化产生的甲烷排放和二氧化碳排放也是重要因素,观察它们如何演变将是有趣的。然而,在缺乏最新的排放数据的情况下,我认为忽略它们并关注最大的因素是合理的。

超收敛:使用大学习速率非常快速地训练神经网络

原文:https://towardsdatascience.com/https-medium-com-super-convergence-very-fast-training-of-neural-networks-using-large-learning-rates-decb689b9eb0?source=collection_archive---------4-----------------------

Photo by Mike Enerio on Unsplash

这篇文章概述了一种叫做 【超级收敛】 的现象,与传统的训练方法相比,我们可以更快地训练一个深度神经网络。其中一个关键要素是使用具有最大可能学习率的 【单周期策略】 来训练网络。我鼓励你看看这篇 精彩的论文 了解更多细节。

在训练中允许“超级收敛”的一个见解是使用大的学习率来正则化网络,因此需要减少所有其他形式的正则化,以保持欠拟合和过拟合之间的平衡。

动机:

斯坦福大学最近组织了一场名为 DAWNBench 的比赛。获胜的参赛作品是 by, fast.ai 他们训练 CIFAR10 在 3 分钟内达到 94%的测试准确率。他们使用了很多很酷的技巧,避免坚持传统的训练技巧。

你可能想知道,在大约 75 个周期内训练一个模型在 CIFAR10 上达到 94% (高)测试精度是没有意义的,因为最先进的技术已经超过 98%。但是你不认为,“最先进水平”准确性是一个病态的目标,因为在这个问题上投入更大的模型、更多的超参数调整、更多的数据扩充或更长的训练时间通常会导致准确性的提高,使不同作品之间的公平比较成为一项微妙的任务。此外,超收敛的存在与理解深度网络的泛化有关。

上图展示了 CIFAR10 数据集上的“超级收敛”。我们可以很容易地观察到,与典型的训练(91.2%)相比,使用修改的学习率时间表,我们实现了更高的最终测试准确度(92.1%),并且也只是在几次迭代中。

Super-Convergence of Neural Nets

超收敛:

因此,让我们快速进入正题,讨论我们如何在少得多的训练迭代次数中实现这些最先进的结果。许多人仍然认为用最佳超参数训练深度神经网络是一种魔法,因为有太多的超参数需要调整。遵循什么样的学习率策略,为架构选择什么样的内核大小,什么样的权重衰减和丢失值对于正则化来说是最优的?所以,让我们打破这种刻板印象,尝试释放一些这些黑色艺术。

我们将从 LR 范围测试开始,它可以帮助你找到最大的 学习率 ,你可以用它来训练你的模型(最重要的超参数)。然后,我们将运行网格搜索 CV 来搜索剩余的参数( 权重衰减&下降 ),以找到它们的最佳值。

学习率查找器:

Leslie Smith 在他的论文中首次介绍了这种技术来寻找 max learning,这篇论文更加详细地介绍了使用循环学习率循环动量的好处。我们以很小的学习率开始预训练,然后在整个跑步过程中线性(或指数)增加。这提供了我们在一个学习率范围内训练网络有多好的一个概览。在学习率较低的情况下,网络开始收敛,随着学习率的增加,网络最终变得过大,导致测试精度/损失突然发散。

Max LR is the peak value in the graph after which accuracy starts decreasing!

典型的曲线看起来类似于上面所附的曲线,第二个图说明了训练迭代次数和达到的精度之间的独立性。

单周期政策:

为了实现超收敛,我们将使用“单周期”学习率策略,该策略要求指定最小和最大学习率。Lr 范围测试给出最大学习率,最小学习率通常为最大值的 1/10 或 1/20。一个循环由两个步长组成,一个是 Lr 从最小值增加到最大值,另一个是从最大值减少到最小值。在我们的例子中,一个周期将比迭代/时期的总数小一点,并且在剩余的迭代中,我们将允许学习率比其初始值小几个数量级。下图更好地说明了单周期策略——左图显示了循环学习率,右图显示了循环动力。

Cyclical Learning rate and Cyclical Momentum

“一个周期”策略的动机如下:学习率开始时很小,以允许收敛开始,但是随着网络穿过平坦的谷,学习率变大,以允许更快地通过谷。在训练的最后阶段,当训练需要进入局部最小值时,学习率再次降低到一个小值。

Loss function topology

左图显示了训练如何跨越损失函数拓扑的可视化,而右图显示了优化结束时的特写。

为什么一个大的学习率表现得像一个正则化者?

LR 范围测试通过结果显示了正则化的证据,其显示了当使用 Cifar-10 数据集和 Resnet-56 架构进行训练时,训练损失增加且测试损失减少,而学习率从大约 0.2 增加到 2.0,这意味着在使用这些大的学习率进行训练时正则化正在发生。此外,该定义称正则化是我们对学习算法进行的任何修改,旨在减少其泛化错误。

批量大小:

众所周知,小批量会导致正则化效应,一些人还显示 CIFAR-10 的最佳批量约为 80,但与之前的工作相反,本文建议在使用单周期策略时使用更大的批量。批量大小应该只受内存约束的限制,而不受任何其他因素的限制,因为较大的批量大小使我们能够使用较大的学习速率。尽管如此,较大批量的好处在某一点后逐渐消失。

批量大小对测试损失/准确度的影响

左图显示了批次大小对测试准确度的影响,右图显示了测试损失。在这里,我们可以观察到,与其他相比,批量大小为 1024 在最少的训练迭代次数中实现了最佳的测试准确性。

将测试损失与测试准确度进行对比也很有趣。虽然较大的批量在训练早期获得较低的损失值,但最终的损失值仅在较小的批量时最小,这与准确度结果完全相反。

周期性动力:

动量和学习速率对训练动力学的影响是密切相关的,因为它们是相互依赖的。动量被设计为加速网络训练,但是它对更新权重的影响与学习速率的大小相同(可以容易地显示为随机梯度下降)。

最佳的训练程序是增加的循环学习率和减少的循环动量的组合。循环动量情况下的最大值可以在对几个值(如 0.9、0.95、0.97、0.99)进行网格搜索后选择,并选择一个给出最佳测试精度的值。作者还观察到,最终结果几乎与动量的最小值无关,0.85 就可以了。

上图显示了动量对采用 ResNet56 体系结构的 CIFAR10 数据的测试精度的影响。

在增加学习速率的同时减少动量提供了三个好处:

  • 较低的测试损耗,
  • 更快的初始收敛,
  • 在更大的学习速率范围内更大的收敛稳定性。

还有一点需要注意的是,先减小动量,然后再增大动量,这比反过来会产生更好的结果。

重量衰减:

这是最后一个值得讨论的重要超参数。正则化的量必须针对每个数据集和架构进行平衡,权重衰减的值是调整正则化的关键旋钮。这需要对几个值进行网格搜索,以确定最佳幅度,但通常不需要搜索一个以上的有效数字。

利用数据集和架构的知识,我们可以决定测试哪些值。例如,更复杂的数据集需要更少的正则化,因此测试更小的权重衰减值,如 104、105、106 和 0 就足够了。浅架构需要更多的正则化,因此测试更大的权重衰减值,如 102、103、104。在网格搜索中,我们经常使用 3.18e-4 这样的值,选择 3 而不是 5 的原因是考虑了指数的二等分,而不是幅度本身的二等分(即,在 104 和 103 之间,一等分为 103.5 = 3.16×104)

从上面的图中我们可以看到,1.8e-3 的权重衰减(再次平分指数 b/w -0.5 和-1,即 10^-0.75)允许我们使用更大的学习速率,加上与其他值相比给出最小的测试损失。

现在,按照这个学习率时间表和一个明确定义的程序来做网格搜索 CV 将会给你带来更好的结果,在训练迭代中几乎减少 50%。

感谢阅读!我会尽力多写一些这样的博客。我的Linkedin简介。你可以关注我的 推特 太。

掌握新一代梯度推进技术

原文:https://towardsdatascience.com/https-medium-com-talperetz24-mastering-the-new-generation-of-gradient-boosting-db04062a7ea2?source=collection_archive---------1-----------------------

Catboost

梯度提升决策树和随机森林是我最喜欢的表格异构数据集的 ML 模型。这些模型是在 Kaggle 比赛中表现最好的,并在行业中广泛使用。

Catboost ,这个街区的新小子,到现在已经有一年多一点的时间了,它已经在威胁 XGBoostLightGBMH2O

为什么选择 Catboost?

更好的结果

Catboost 在基准测试中取得了最好的结果,这很好,但是我不知道我是否会仅仅为了对数损失改进的一小部分而替换一个工作的生产模型(特别是当进行基准测试的公司对 Catboost 有明显的兴趣时😅).
然而,当你看到分类特征发挥巨大作用的数据集时,比如亚马逊互联网数据集,这种改进变得显著且不可否认。

GBDT Algorithms Benchmark

更快的预测

虽然训练时间可能比其他 GBDT 实现要长,但根据 Yandex 基准测试,预测时间比其他库快 13-16 倍。

Left: CPU, Right: GPU

含电池

与其他 GBDT 算法相比,Catboost 的默认参数是一个更好的起点。对于想要一个即插即用模型来开始体验树合奏或 Kaggle 比赛的初学者来说,这是一个好消息。
然而,我们必须解决一些非常重要的参数,我们稍后会谈到这些参数。

GBDT Algorithms with default parameters Benchmark

Catboost 的一些更值得注意的改进是功能交互、对象重要性和快照支持。

除了分类和回归,Catboost 支持开箱即用的排名

经过战斗考验

Yandex 严重依赖 Catboost 进行排名、预测和推荐。这种模式每月为 7000 多万用户提供服务。

CatBoost 是决策树上梯度提升的算法。它由 Yandex 的研究人员和工程师开发,是公司内部广泛用于任务排名、预测和提出建议的 MatrixNet 算法 的继任者。它是通用的,可以应用于广泛的领域和各种问题。

该算法

经典梯度增强

Gradient Boosting on Wikipedia

Catboost 秘制酱

Catboost 引入了两个关键的算法进步——实现了有序提升,这是一种替代经典算法的置换驱动算法,以及一种用于处理分类特征的创新算法
这两种技术都使用训练样本的随机排列来对抗预测偏移,这种偏移是由一种特殊的目标泄漏引起的,这种泄漏出现在梯度增强算法的所有现有实现中。

卡特彼勒电气特征处理

有序目标统计

大多数 GBDT 算法和 Kaggle 竞争对手已经熟悉了目标统计(或目标均值编码)的使用。
这是一种简单而有效的方法,其中我们用类别条件下的预期目标 y 的估计值对每个分类特征进行编码。
事实证明,不小心应用这种编码(y 在具有相同类别的训练示例上的平均值)会导致目标泄漏。

为了对抗这种预测转变 CatBoost 使用了一种更有效的策略。它依赖于排序原则,并受到在线学习算法的启发,该算法按时间顺序获取训练样本。在这种设置下,每个示例的 TS 值仅依赖于观察到的历史。
为了使这种想法适应标准的离线设置,Catboost 引入了一个人工“时间”——训练示例的随机排列 σ1
然后,对于每个示例,它使用所有可用的“历史”来计算其目标统计。
注意,仅使用一个随机排列,导致前面的例子比后面的例子具有更高的目标统计方差。为此,CatBoost 对梯度增强的不同步骤使用不同的排列。

一个热编码

Catboost 对所有具有最多 one_hot_max_size 唯一值的特征使用一键编码。默认值为 2。

Catboost’s Secret Sauce

有序推进

CatBoost 有两种选择树结构的模式,有序和简单。普通模式对应于标准 GBDT 算法与有序目标统计的组合。
有序模式提升中,我们执行训练示例的随机排列- σ2,并维护 n 个不同的支持模型- M1。。。,Mn ,使得仅使用排列中的第一个 i 样本来训练模型 Mi
在每一步,为了获得第 j 个样本的残差,我们使用模型mj1
遗憾的是,由于需要维护 n 个不同的模型,这种算法在大多数实际任务中并不可行,增加了 n 倍的复杂度和内存需求。Catboost 在梯度推进算法的基础上实现了对该算法的修改,使用了所有要建立的模型共享的一个树结构。

Catboost Ordered Boosting and Tree Building

为了避免预测偏移,Catboost 使用排列使得 σ1 = σ2 。这保证了目标 yi 不用于训练 Mi ,既不用于目标统计计算,也不用于梯度估计。

把手放在某物或者某人身上

对于这一部分,我们将使用 亚马逊数据集 ,因为它很干净,并且非常强调分类特征。

Dataset in a brief

调谐 Catboost

重要参数

cat_features —为了利用 Catboost 对分类特征的预处理,该参数是必需的,如果您自己对分类特征进行编码,并且没有将列索引作为 cat_features 传递,那么您就错过了 Catboost 的精髓

one_hot_max_size —如前所述,Catboost 对所有具有最多 one_hot_max_size 唯一值的特征使用 one-hot 编码。在我们的例子中,分类特征有许多唯一值,因此我们不会使用一个热编码,但根据数据集调整该参数可能是个好主意。

learning_rate&n_estimators—learning _ rate 越小,利用模型需要的 n 个估计量就越多。通常,方法是以相对高的学习率开始,调整其他参数,然后降低学习率,同时增加n _ 估计量

max_depth —基树深度该参数对训练时间有很大影响。

subsample —行的采样率,不能用于贝叶斯增强类型设置。

colsample_bylevel, colsample_bytree, colsample_bynode —列的采样率。

l2_leaf_reg — L2 正则化系数

random_strength — 每一次分裂都会得到一个分数,random_strength 为分数增加了一些随机性,这有助于减少过度拟合。

Check out the recommended spaces for tuning here

使用 Catboost 进行模型探索

除了 GBDT 模型非常流行的特性重要性之外,Catboost 还提供了特性交互对象(行)重要性

Catboost’s Feature Importance

Catboost’s Feature Interactions

Catboost’s Object Importance

SHAP values can be used for other ensembles as well

完整的笔记本

查看一些有用的 Catboost 代码片段

Catboost Playground Notebook

结果

Catboost vs. XGBoost (default, greedy and exhaustive parameter search)

拿走

  • Catboost 的构建方法和属性与“老”一代 GBDT 车型相似。
  • Catboost 的强大之处在于它的分类特征预处理预测时间模型分析
  • Catboost 的弱点是它的训练和优化时间
  • 不要忘记将 cat_features 参数传递给分类器对象。没有它,你就不能真正利用 Catboost 的能力。
  • 尽管 Catboost 在默认参数下表现良好,但有几个参数在优化时可以显著改善结果。

进一步阅读

非常感谢 Catboost 团队负责人安娜·维罗妮卡·多罗古什

如果你喜欢这篇文章,请按下鼓掌键👏🏽如果你对接下来的帖子感兴趣,一定要关注我

中:https://medium.com/@talperetz24 推特:https://twitter.com/talperetz24 领英:https://www.linkedin.com/in/tal-per/

像每年一样,我想提一下data hack——最好的数据驱动黑客马拉松。今年,我和דור פרץ在我们的项目中使用了 Catboost,并获得了第一名🏆。

超越单词表示的分布模型。

原文:https://towardsdatascience.com/https-medium-com-tanaygahlot-moving-beyond-the-distributional-model-for-word-representation-b0823f1769f8?source=collection_archive---------5-----------------------

在任何基于现代机器学习的 NLP 流水线中,单词矢量化是一个典型的步骤,因为我们不能直接输入单词。在单词矢量化中,我们通常为单词分配一个 n 维向量,以捕捉其含义。因此,这是流水线中最重要的步骤之一,因为不好的表示会导致下游 NLP 任务的失败和意想不到的影响。

单词向量化最常用的一类技术是单词的分布模型。它基于一个假设,即单词的意思可以根据它出现的上下文来推断。大多数深度学习论文使用来自分布假设的词向量,因为它们是任务不变的(它们不是特定于任务的)和语言不变的(它们不是特定于语言的)。不幸的是,分布式方法并不是单词矢量化任务的灵丹妙药。在这篇博文中,我们强调了这种方法存在的问题,并提供了改进单词矢量化过程的潜在解决方案。

分布式模型存在以下问题:

  • 稀有词:对于语料库中出现频率较低的词,他们没有学习到很好的表征。
  • 混义:他们把一个词的所有义项混为一谈,比如“bank”这个词可以指“河岸”或“金融机构”。分布模型将这些解释合二为一。
  • 词法缺失:他们在学习表征时没有考虑单词的词法。例如,单词“evaluate”和“evaluates”具有相似的意思,但是它们被视为两个独立的单词。

幸运的是,有大量的研究致力于解决这些问题。这些方法大致分为三大类,我们将按以下顺序进行探讨:

  • 形态学敏感嵌入
  • 将语言学或功能约束增加到单词嵌入中
  • 处理词义。

形态学敏感嵌入

这类技术在学习嵌入时考虑了单词的形态。Fasttext 是这类技术的一个典型例子。它将单词视为字符 n 元语法表示的总和。例如,单词“where”表示为“< wh,whe,her,ere,re >”。每个字符 n 元语法被分配一个向量,该向量随后被用于计算上下文向量和目标向量之间的匹配分数:

当这种方法(sisg)在诸如德语(De)、法语(FR)、西班牙语(es)、俄语(RU)和捷克语(Cs)等形态学丰富的语言的语言建模任务上被评估时,它显示出在不使用预训练的词向量的情况下,以及在不使用子词信息(sg)的情况下预训练词向量的情况下,相对于 LSTM 的改进。

此外,fasttext 可以为从未出现在语料库中的单词提供嵌入,因为它将单词表示为已知字符 n 元语法的总和。在生命科学等领域,像这样的嵌入非常有用,因为语料库中的大多数单词都属于有限词汇量的未知类别(长尾现象)。

向单词嵌入灌输形态学的另一种方法是由 Morphfitting 提供的。在这项工作中,他们使用吸引-排斥方法对嵌入进行后处理,以吸引屈折形态学(单词形式表达有意义的句法信息,例如动词时态,而单词的语义没有任何变化的一组过程)并排斥派生形态学(语义发生变化的新单词的形成)。关于吸引-排斥方法的细节将在下一节讨论。

通过灌输形态学语言约束,Morphfitting 显示了在下表中给出的 10 个标准嵌入上 SimLex 和 SimVerb 的相关系数的增益。

将语言学或功能约束增加到单词嵌入中

用于单词空间特殊化的另一类方法是用语言/功能约束对单词嵌入进行后处理。在上一节中我们已经看到了这种方法的一个例子——morph fitting。在这一节中,我们将探讨嵌入特殊化-吸引-排斥的变形拟合中使用的方法。

吸引-排斥是一种后处理技术,它采用预先训练的嵌入,并根据语言约束对其进行特殊化。例如,在 morphfitting 中,语言约束以两组形式表示,如下所示:

表格的上半部分显示吸引集,矩阵的下半部分显示排斥集。使用这些集合,形成小批量,用于优化以下损失函数:

该损失函数中的第一项对应于吸引集,第二项对应于排斥集。第三项保持分布表示。此外,前两个术语还反复灌输反面例子,这是从段落模型中借鉴来的思想。前两项的成本函数由下式给出:

第三项 term 由下式给出:

人们可以使用吸引-排斥来灌输语言限制,这可以用吸引或排斥集来表示,例如“同义词和反义词”或“屈折和派生形态学”。或者,在语言约束不暗示相似或不相似的情况下,不能专门化嵌入,例如,类型“treat”的关系不能使用吸引-排斥来捕获。为了适应这样的功能关系,我们引入了另一种叫做功能改造的方法。

在功能改造中,关系的语义学习和词空间特殊化同时发生。这是通过用在优化过程中学习的函数替换来自吸引排斥的点积来实现的。

上述公式中的第一项保持分布嵌入,第二和第三项从知识图中吸取正(E+)和负(E-)关系,最后一项对学习的函数执行正则化。

通过预测两个实体 I,j 之间的关系 r,在 snomed-ct 上使用链接预测来测试所学语义在功能改造中的功效。跨四种功能改造的四种关系(“has 发现部位”、“has 病理过程”、“due to”和“cause of”)的结果如下所示:

关于功能改造的更多信息,请参考克里斯多佛·波茨博客。如果你正在寻找功能或语言约束来专门化你的嵌入,在链接的开放数据云查看互联本体的优秀汇编。

上述方法更新了词汇资源中提供的单词的嵌入。如果你对专门化整个单词空间感兴趣,你可以使用 EMNLP 2018 论文中建议的 Adverserial Propagation(Adversarial Propagation and Zero-Shot Cross-language Transfer of Word Vector Specialization)作者Ivan vuliNikola mrk ii)来实现。

处理词义

最后,最后一类专门化技术通过考虑上下文或利用词义清单来考虑词义。让我们从前一类的方法开始——ELMO。

在 ELMO,单词是根据上下文进行矢量化的。因此,为了对单词进行矢量化,还需要指定单词出现的上下文。与那些不考虑上下文的矢量化技术相比,这种方法被证明是非常有效的。当比较来自 ELMO 的最近邻居(biLM)和 Glove 时,可以看到相同的例子:

ELMO 背后的基本思想是生成嵌入作为双向语言模型的层的内部状态和字符卷积网络的最终层表示的加权和。

来自 ELMO 的嵌入已经在三个下游任务班、SNLI 和 SRL 进行了测试,发现其提供了超过基线的显著增益:

想了解更多关于 ELMO 的信息,请参考 AllenNLP 的博客文章。

如果您对使用词汇资源从单词的分布表示中提取意义感兴趣,您可以使用 [DECONF](https: //pilehvar.github.io/deconf/) 。在这种方法中,穆罕默德·塔赫尔·皮莱赫瓦尔提出了一种机制,使用以下优化标准从分布式嵌入中压缩感知嵌入:

这里,第一项保持了对有义分布表示的接近,第二项使有义嵌入偏向更接近偏向词。从视觉上来说,这个过程可以通过下面的图片得到最好的描述。

在词汇术语的语义网络(使用词汇资源创建)上使用个性化页面排名算法来计算偏置单词集。

使用 Pearson 和 Spearman 相关性在四个单词相似性基准上评估 DECONF。发现在如下所示大多数任务中获得了最先进的结果。

结论

如果你没有足够的训练数据来从零开始学习单词嵌入,我强烈推荐使用上面提到的单词专门化方法来获得一些百分点。对于这个主题更严格的报道,我强烈推荐Ivan vuliESSLLI 2018 上关于单词向量专门化的课。

数据能为你的创业做的最重要的事情

原文:https://towardsdatascience.com/https-medium-com-towards-data-science-the-single-most-important-thing-that-data-can-do-for-your-startup-2d90813de180?source=collection_archive---------4-----------------------

如何减少企业家在数据决策方面面临的认知负荷

Let the key, current, and future questions that you’ll need to answer be the guide for making the data decisions at your startup.

我与许多初创公司合作过,当涉及到数据时,企业家会面临一系列非常常见的问题:

(为表达观点而简化)

  1. 我们如何跟踪我们需要的核心业务指标?
  2. 我们应该如何/在哪里存储和组织我们的数据?
  3. 到目前为止,数据告诉了我们什么?
  4. 我们还应该追踪什么?
  5. 在内部和外部分享这些信息的最佳方式是什么?
  6. 关于我们的产品、业务、客户等数据,我们还能做些什么??

沿着“数据之路”走下去,并试图回答这些和其他问题(又名:做出数据决策)可能会令人望而生畏,对没有数据头脑的企业家来说有点可怕。在如此关注和强调处理数据的情况下,有一种“正确处理”和高效处理的隐性压力。

没有人想说,“天啊,如果我们当时知道我们现在知道的事情就好了…”

与此同时,除了导师、投资者和客户不断告诉他们戴上的不合适的数据帽子之外,许多企业家还戴着销售、营销、业务发展和产品的帽子。如果不在他们的工作范围内,这不是一个容易完成的角色,而且试图理解初创公司在数据之旅中面临的总体决策可能会令人生畏。

虽然上面列出的每个问题都值得单独研究,但企业家可以通过一个思维模式来整合和简化关于数据的问题、想法、想法和待办事项。(使用这种模式有助于减轻一些数据决策压力。)

(好的)数据只是回答关键、当前和未来问题的备忘单。

是的,就是这样。这听起来非常简单,确实如此,但是也很容易忽略所有数据的真正用途。

向后工作

如果我们看看上面的第 4 条——“我们还应该跟踪什么?”—在当今这个超级简单的数据生成的世界里,回答这个问题可能会非常困难。

“让我们追踪一切!”难道不是一个好的答案吗?因为这样做通常会让人不知所措、迷惑不解,而且成本高昂。

相反,你可以逆向工程,列出代表你的业务和产品你想要和需要回答的关键/当前/未来问题,将哪些清晰度指标包含在你的报告中。

企业家可以利用他们的创造力想出一个问题景观,而不是被眼前的数据导向挑战吓倒。

Credit

利用你所拥有的,做你擅长的,并利用这些来驾驭那些对你来说不那么容易的东西——比如学习什么是 ETL,以及 Luigi 不仅仅是任天堂的那个家伙。

需要注意的是,从答案通过关键/当前/未来问题到需要做出的数据决策的逆向工程不是一步到位的过程。这些问题可能来自内部或外部的利益相关者,并且在结构和重要性上有所不同,它们通常嵌套在更广泛的主题和业务核心问题中。

这可能是一件麻烦的事情,但是列出你所有的关键/当前/未来问题,并从那里逆向工程你的数据决策,对你和你的团队来说是一个很好的练习。

(这也是开发创业公司数据路线图的好方法。)

[## 您的数据路线图可以回答的 10 个问题

“什么是数据路线图?”我们先来回答这个问题。(而且我们不会把它算进 10。)

medium.com](https://medium.com/@markschindler/10-questions-that-your-data-roadmap-can-answer-8db0bb0aa235)

磨练你的预测技能

确定对您的业务最重要的问题是事情变得有趣的地方:确定关键的和当前的问题可能有点简单,但是“未来的问题”呢?你怎么能预测未来并提前知道你需要回答什么问题呢?

成为一名好学生的最好步骤之一是学会预测考试问题,而成为一名成功企业家的最好步骤之一是预测你的投资者、客户和团队可能会问什么问题。

这样做你可能做不到 1.000,这只是成功退出的众多因素之一,但如果你能磨练这一技能,那么它可以让你把时间和精力集中在对你的业务有最大影响的追求上。

(在此插入俗气的“准备”引言或陈词滥调)

最后,预测客户和投资者的问题是很好的准备——没有什么比被一个你没有准备好或准备不足的问题弄得措手不及更糟糕的了。虽然许多企业家可能会在一次重要会议前考虑这一点,但为什么不从第一天就使用相同的方法呢?

它将关注并简化您的数据决策,并使重要会议的准备变得更加容易。

用 Python 实现上升趋势线指标——从获取数据到建模算法和实现解决方案——第 1 部分使用 REST API

原文:https://towardsdatascience.com/https-medium-com-vedranmarkulj-implementing-the-up-trendline-indicator-with-python-part-1-10f19939431e?source=collection_archive---------5-----------------------

最初发表于【softwarejargon.com】 在我的博客上找到这篇文章的更新版本【https://softwarejargon.com/blog】

要求—您应该熟悉以下主题:

  • 使用过 python、对象、循环和数据类型。
  • 对熊猫和图书馆有一些了解。
  • 知道什么是技术分析。

希望更新您的技能或获得上述主题的介绍?我强烈推荐以下资源:

这是关于处理股票价格数据和用 Python 实现上升趋势线指标的系列文章的第一篇。完整系列将详细描述技术指标上升趋势线的实现。本文将描述解决方案中使用 REST API 的部分,这将为我们提供后续文章中需要的数据。

上升趋势线指示器的简要说明

在技术分析中,最著名和简单的技术指标是上升趋势分析。该指标本质上是一条直线,因此在查看图表时相对容易识别。图案是一条直线,至少要经过三个点。线的斜率必须增加,并且不能被图中更靠前的点打断。

上升趋势线表明;股价将继续高于趋势线,因此将继续上涨。如果在任何时候股价触及趋势线,并因此穿过趋势线;这预示着股票价格将有下跌的趋势。请参见下图。

如果你想学习更多关于指标和技术分析的知识。你可以在这里找到更多信息。

这就是我们将在本文中构建的内容

首先,你需要在你的机器上安装 Python。我建议安装蟒蛇;在我看来,在本地使用 python 最简单的方法。但是在本文中,我不会详细介绍开发环境的设置。然而,这个问题将会在一篇关于安装 Anaconda 和建立开发环境的独家文章中讨论。

本文的其余部分将关注:

  • 如何连接到 Alphavantage REST API?
  • 处理数据并将其放入熊猫数据框。
  • 使用 pandas 数据框架,为实际分析做准备。

连接到 Alphavantage

首先你需要有一个 API 密匙。这可以通过访问以下链接获得:https://www.alphavantage.co/选择“立即获取免费 API 密钥”。

这里我假设您已经安装了 Anaconda 并创建了一个安装了 Python 2.7.xx 的环境。

您还必须在使用的环境中安装以下库:

  • json
  • 要求
  • 熊猫

接下来创建。py 文件。创建以下内容。项目文件夹中的 py 文件:

  • get _ historical _ data.py
  • get_main_df.py

文件“get_historical_data.py”

首先,您需要导入我们将在 get_historical_data.py 文件中使用的所有必要的库。

然后,我们感兴趣的是创建一个新的类,它将包含连接到 REST API 和检索必要数据所需的所有必要方法。

我们将这个类命名为AlphaVantage。这个类需要一个__init__方法,该方法将在类的实例化时被调用。__init__方法应该如下所示:

现在我将逐行检查每一行代码。我们已经通过定义 inline 5 创建了一个类。在第 7 行,我们定义了__init__方法。该方法将接受三个参数,其中两个将具有默认值,这意味着它们在调用该类时是可选的。在__init__方法中,第 8 行到第 13 行之间定义了六个变量。

  • self.base_url包含值"https//www.alphavantage.co"。每次我们需要构建调用 REST API 的 url 时,都会用到这个值。
  • self.default_endpoint包含值"/query"。这个值是我们将多次调用的 REST API 的端点之一。因此,我们想把它放在__init__方法中,从而避免多次定义它。
  • self.api_key在这里,您需要输入从 Alphavantage 检索到的 API 密钥。
  • self.symbol_code该变量的值由参数symbol_code设置,我们将在实例化该类时解析该参数。
  • self.interval由参数interval设置,其默认值设置为"60min"。这个变量稍后将在调用 REST API 提供的一个端点时用作参数。
  • self.outputsize是由参数outputsize设置的变量,其默认值也设置为"compact"。这个变量也将在以后调用 REST API 端点时用作参数。

到目前为止,我们已经包含了所有必要的库,定义了一个类,并在该类中创建了我们的__init__方法。现在我们将在 AlphaVantage 类中创建一个名为intraday的额外方法。

intraday方法不接受任何参数,除了self.如果你想了解self在 Python 中做了什么,我建议阅读这篇文章。

intraday方法的目的是用一些参数调用特定的端点,并以 JSON 的形式返回响应。为了调用 REST API,我们使用请求库,更具体地说,我们将使用requests.get()方法。这个方法有许多参数。我们将提供以下内容:

  • 我们要调用的 url。我们在第 21 行构建 url,特别是部分"{0}{1}".format(self.base_url, self.default_endpoint)。如你所见,我们使用了在__init__方法中定义的一些变量。
  • 我们还必须提供 REST API 端点需要的参数。为此,我们将构建一个名为parameters的字典,包含一些键和值。第 12 到 19 行定义了 dict 及其键和值。dict 中的键和值,每一个都代表一个参数,REST API 端点需要这个参数来响应期望的输出。

让我们来看看在我们的字典parameters中定义的一些参数。

  • "symbol"该键的值被设置为变量self.symbol。我们需要向端点提供这个参数,以便指定我们想要查看哪个公司的股票价格。
  • "interval"该键的值被设置为变量self.interval,其值为"60min"。这意味着我们需要每小时一天的数据,每天有 24 个数据点。
  • "outputsize"该键的值被设置为变量self.outputsize,其值为"compact"。简而言之,这意味着我们将收到我们请求的任何给定"symbol"的最新 100 个数据点。

如果您想了解这个特定端点的更多信息,以及 Alphavantage REST API 的一般信息。我建议看一下文档

所以现在我们已经定义了方法intraday,其中我们调用了 Alphavantage REST API 中的一个特定端点。此外,我们还在 dict 中定义了所有必要的参数,并将 dict 作为参数提供给第 21 行的requests.get()方法。最后,我们方法的最后一部分,第 23 行,返回我们从调用的 REST API 收到的响应。

现在我们将在我们的类AlphaVantage中实现另一个叫做daily的方法。

这个方法和上一个很像。daily方法的目的是每天而不是当天返回股票价格数据。为此,这种方法与以前的方法相比有两个不同之处。在第 13 行,键"function"的值现在被设置为"TIME_SERIES_DAILY”,我们不再有键"interval"。其他一切都保持不变,因此这种方法不需要额外的解释。

最终的 get_historical_data.py 文件现在应该如下所示:

文件“get_main_df.py”

对于这个文件,你需要导入库pandasjson,此外你还需要从文件 get_historical_data.py 导入AlphaVantage

我们现在对创建一个名为get_main_data_frame的新函数感兴趣。这个函数将包含我们在 get_main_df.py 文件中实现的所有逻辑。

我们想在函数中做的第一步是调用AlphaVantage类,以便获得一些我们可以使用的数据。我们将这个实例命名为historical_data_daily

注意,我们还调用了方法daily(),它是在类AlphaVantage中实现的方法之一。这意味着我们将接收每日数据,而不是当天数据。

下一个代码片段包含大量代码,但是,主要重点是遍历调用 Alphavantage REST API 所收到的响应。

在第 15 和 16 行定义了两个空列表。list_keys将包含所有与我们相关的键,而list_historical_data_daily将包含我们想要处理的所有数据。在这里,我假设您有一些使用 dicts 和 JSON 数据的基本知识。

第 17 行和第 18 行遍历在键"Time Series (Daily)"中找到的所有键。我们找到的每个键都被附加到list_keys。在这种情况下,每个键实际上代表一个日期。

第 20 到 40 行做了几件事。首先,我们访问list_keys中每个键的数据,并将其赋给变量data。然后识别出四个数据点price_openprice_highprice_lowprice_close。所有四个变量都将包含一个代表给定日期价格的数值。

接下来,用关键字定义字典。这将是我们每天想要保存的数据。dict 包含一个日期和一个符号,以及四个价格值。最后,该字典被附加到list_historical_data_daily

可以在下一个代码片段中看到的代码的其余部分集中在与 pandas 一起工作,以便为进一步的分析准备数据。

我们要做的第一件事是将所有存储在list_historical_data_daily中的数据转换成熊猫数据帧。这是在第 15 行完成的。

  • 第 20 行创建了字段'date_str'。此字段源自“日期”字段。
  • 第 21 行将字段'date'设置为数据帧的新索引。
  • 第 22 行对索引进行排序。默认排序是升序,这意味着最早的日期排在最前面。
  • 第 24 行创建了字段'price_close_lag'。本栏位显示前一天的收盘价数据。当我们在随后的文章中想要比较今天的价格和前一天的价格时,这将是有用的,以便确定价格的方向。
  • 第 25 行创建了字段'price_close_lag'。该字段显示明天的收盘价格数据。与前一个字段一样,该字段也将有助于后面的价格比较分析。
  • 第 27 行创建了字段'date_id'。该域从 1 开始递增一个 int 值。熊猫数据框按升序排序很重要。因此,以前索引是一个日期值,按升序排序。

最后返回名为df的数据帧。

最终的 get_main_file.py 文件现在应该如下所示:

希望这篇文章可以提供一些关于如何开始处理股票数据、从哪里获取数据以及如何开始准备数据以应用算法的想法。

下一篇文章的第 2 部分将关注技术指标上升趋势线的实现。我希望你准备好了,因为这将会有点复杂,但相反更令人兴奋。

如果你有兴趣了解我更多。请访问我在 LinkedIn 上的个人简介https://www.linkedin.com/in/vedranmarkulj/

感谢阅读。如果你对我写的关于机器学习和类似主题的未来帖子感兴趣,请在 MediumLinkedIn 上关注我。更多文章即将发表。

使用 NLP 算法人性化客户投诉

原文:https://towardsdatascience.com/https-medium-com-vishalmorde-humanizing-customer-complaints-using-nlp-algorithms-64a820cef373?source=collection_archive---------3-----------------------

Image Source: Adobe Stock

去年圣诞节,作为一名消费者,我经历了最令人沮丧的经历。我正在做一些最后一分钟的假日购物,在排了很长的队后,我终于到达了受祝福的收银台,却发现我的借记卡被封了。我能感觉到收银台的老太太眯着眼睛打量着我。感觉非常尴尬,我马上给银行打了电话。令我惊恐的是,他们告诉我,我的储蓄账户被黑了,几千美元已经不见了!

“天哪!这种事怎么会发生在我身上?”

最初的震惊平息后,我决定马上解决这个问题。我不得不拨打另一个号码,证明我的身份,并提出正式投诉,拿回我的钱希望渺茫。打了一个小时的电话后,我挂断了。我太生气了!五分钟后,我看到我的银行发来一条短信,问我:在我们银行工作开心吗?我的第一反应是一些措辞,然后是更多的沮丧和怀疑。

“他们怎么能这样问我?他们不知道刚刚发生了什么吗?他们只是假装关心我吗?对他们来说我只是一个数据点吗?沧海一粟?”

在众多的问题中,出现了一个明显的认识。我意识到,作为一名数据科学专业人员,我也在做同样的事情。在我的组织中,我们以同样的冷漠对待我们自己的客户投诉。只是另一个数据点;只是沧海一粟。我有什么不同吗?

我们需要人性化的客户数据。

即使在数据科学中,人类的情感也很重要,这一观点在我脑海中生根发芽。我开始痴迷于分析和解读客户投诉数据。在花了几个月的时间进行内部研究后,我们发现了一个鲜为人知的关于投诉叙述的非结构化数据源。举个例子,让我们来看一个向消费者金融保护局 (CFPB)登记的关于信用卡计划的实际投诉。

Anonymized Customer Complaint from CFPB Complaint Database (Image Source: Adobe Stock)

我打赌你读了 3-4 行后就不再读了,对吗?我们只是把这样的描述性叙述扔掉,仅仅是因为我们不知道该怎么处理它。传统的统计方法相当无用,我们之前的文本分析工作(也称为词云)没有产生任何可操作的消费者洞察。此外,我们通常会收到数以千计的此类投诉。因此,对如此庞大的数据进行全面分析被认为是不可能的。输入 NLP 算法!

自然语言处理

NLP 是机器理解和分析人类语言的能力。它是人工智能(AI)领域的一部分,与语言学有很大的重叠。

然而,自然语言是极其复杂的系统。想象一个人体。它由 11 个独立的系统组成(如神经系统、消化系统等。)相互协同工作。类似地,人类语言有几个子系统,如音韵学、形态学和语义学,它们彼此无缝协作。

不同子系统之间复杂的相互作用使得学习一门新语言变得困难。如果你的母语是英语,你可能需要 2000 多个课时才能说一口流利的普通话。那是几年的学习价值!这就是为什么与机器学习和人工智能的其他领域相比,NLP 的进展缓慢的原因。

NLP 流程:

典型的 NLP 流程有以下步骤:

1)数据收集:数据挖掘或 ETL (extract-transform-load)过程收集非结构化数据的语料库。

2)数据预处理:

  • 分词:将连续文本分割成单词。
  • 词尾变化:去除词尾变化以返回基本形式。
  • 词性标注:将单词识别为名词、动词、形容词等。

3)特征工程:

  • 单词嵌入:将文本转换成有意义的向量或数字数组。
  • N 元语法:一元语法是文档中的一组单词;二元语法是文档中两个相邻单词的集合。
  • TF-IDF 值:Term-Frequency-Inverse-Document-Frequency 是一个数字统计量,表示一个单词对文档集合中的一个文档有多重要。

4)自然语言处理算法的应用:

现在,我们来看几个关于实际客户投诉的真实案例研究。

案例研究#1:主题建模

问题:在提交投诉时,要求客户选择投诉类别或主题。然而,客户不知道商业术语,所以他们经常选择错误的类别。这对于我们来说是一个大问题,超过 20%的投诉被错误分类和错误发送。这导致了长时间的等待和客户投诉的不完全解决。

解决方案:我们利用 TF-IDF 和 LDA 等主题算法,根据投诉中使用的确切语言对客户投诉进行重新分类。如下图所示,原始主题(客户主导的)和新主题(NLP 推荐的)之间存在一些差异。特别是,NLP-themes 将“滞纳金”确定为客户投诉的主要原因(17%),大大高于之前的估计。

这种分析更快、更准确地确定了投诉的根本原因。尽管有了这一突破,我们仍在努力以 100%的准确率对投诉进行分类。有时,一个投诉有多个方面,可归因于几个类别,这导致不准确的分类和不适当的解决工作。为了提高准确性,我们使用余弦相似度度量标准构建了所有投诉的定制知识图或网络图,该度量标准可作为各个投诉之间的引力。此外,力定向图被用于更好的可视化。

Knowledge Graph based on ~18K complaints from CFPB Complaints Database (powered by Quid)

我知道你在想什么!是的,它看起来确实像一种奇怪的海洋珊瑚!但这个知识图中的每一个节点都是一个个体的抱怨。相似的投诉根据使用的确切语言聚集在一起,并用不同的颜色表示。通过这一分析,我们能够获得以下见解:

  • 多个投诉主题:一个典型的投诉有 2 或 3 个不同的主题。通过知识图表示投诉可以更好地识别集群中的重叠主题和异常值。
  • 中心主题与边缘主题:在上图中,“账户关闭”是一个中心主题,改善关闭体验可以让其他主题受益。相比之下,“社会保障”投诉存在于它们自己的岛屿上,因此需要用单独的解决策略来处理它们。
  • 隐藏的主题:知识图可以揭示非结构化数据中隐藏的关系,并帮助识别新的主题。

结果:基于这些认识,我们确定“客户费用”是一个比以前认为的更大的问题。我们免除了大约 150 万客户的国外交易费用。我们还修改了滞纳金政策,实施了更多以客户为中心的标准,并免除了每年约 3 万名客户的滞纳金。这些努力最终使我们在过去 4 年中获得了最高的客户满意度得分和最低的投诉率。

案例研究#2:情感分析

问题:历史上,我们忽略了客户投诉中的潜在情绪。显然,投诉都与负面的客户体验有关,但重要的是要弄清楚客户是否在质疑某项政策,或者他们是否有原本应该避免的真正可怕的体验。本质上,我们需要量化客户的“恼火”因素,以优先处理和上报需要立即处理的投诉。

解决方案:对于情感分析,我们维护了一个标准的 NLP 工作流程,并增加了一些关键步骤。首先,有一个情感检测步骤,其中利用一个单词袋模型通过基于词汇的方法来确定文本是否属于客观事实或观点。其次,通过机器学习算法来确定情绪的极性(积极或消极)。我们测试了几种分类算法,包括随机森林、支持向量机和梯度推进。深度学习算法,特别是长短期记忆( LSTM )网络,能够忘记无关信息,也显示出很大的前景。一旦消费者情绪被汇总,它们就被映射回知识图,以便更好地可视化。

Sentiment Analysis based on ~18K complaints from CFPB Complaints Database (powered by Quid)

如你所见,“欺诈和身份盗窃”主题与最负面的消费者情绪相关。其他有问题的投诉主题是“商家纠纷”和“信用额度下降”。此外,通过开发一个情感仪表板,可以随时跟踪客户情感。这样做主要是因为业务主管喜欢仪表盘!下面是一个例子。

An Example of Sentiment Dashboard for Customer Complaints

结果:该分析促使我们对防欺诈计划进行了全面的审查和后续改进,并改进了商户争议/信贷实践。重要的是,采取这些措施来加强我们的客户倡导计划,使我们在 2018 年 J.D. Power 满意度调查中从第 7 名升至第 3 名。

吸取的教训:

1)数据是我们最大的资产:我们扔掉了投诉文本数据,但它变成了宝贵知识的金矿。我敢打赌,如果你足够努力地寻找,你会在自己的企业中发现这样的原石。

投诉=洞察力:客户投诉通常与很多耻辱联系在一起。我们不喜欢谈论抱怨,因为根据定义,这些都是失败的故事。这就是为什么,通常情况下,他们会被掩盖起来。重要的是要改变我们的态度,开始将投诉视为可操作的消费者洞察力的来源。

"你最不满意的顾客是你最大的学习来源."

比尔·盖茨

3)人类的情感是非常强大的:最好的品牌总是与他们的消费者联系在一起,并诉诸人类的情感。情感分析不仅是增强客户体验的强大工具,也是品牌管理、营销策略和新产品开发计划的强大工具。

4) NLP 将是未来 AI 的基石:随着 AI 的出现,预计到 2022 年,非结构化数据将占到数字宇宙中所有数据的 93%。NLP 算法将是释放非结构化数据真正潜力的关键,可以帮助企业为自己发展长期竞争优势。

最后,感谢我的同事 Jeorge CorotanAnurag Setty 完成了这项惊人的工作并分享了我的困扰!请让我知道你是否有任何反馈,或者在下面分享你自己关于 NLP 算法的经验。

从 2018 年纽约人工智能峰会吸取的 5 个关键教训

原文:https://towardsdatascience.com/https-medium-com-vishalmorde-lessons-learned-from-ai-summit-d7c071cb4c06?source=collection_archive---------17-----------------------

炒作、现实、道德、颠覆等等…

2018 AI Summit, NYC, https://theaisummit.com/newyork/

本周早些时候,我很高兴参加了在纽约市雅各布贾维茨中心举行的 2018 年人工智能峰会(@ Business _ AI# AISummit)。这是一个会见领先的人工智能研究人员、思想领袖和同行的绝佳机会。

人工智能峰会:

现在是第三年,人工智能峰会是专注于企业人工智能应用的最负盛名的会议之一。3,000 多名与会者,300 多名发言人和 150 多场会议,峰会为每个人提供了一些东西。所有通常的嫌疑人都出席了,包括谷歌、亚马逊、微软,当然还有机器人索菲亚( @RealSophiaRobot ),汉森机器人的人工智能倡议。就连金融机构也以高盛、摩根大通、花旗、第一资本、美洲银行和巴克莱为代表。这些会议很好地结合了案例研究、商业见解和来自各个行业的技术解决方案。以下是我在峰会经历中的 5 个要点。

#1:我们超越了宣传

几年前,人工智能被认为是世界上所有问题的解决方案。它应该让世界变得更好,这样我们就可以永远幸福地生活下去!今年,我们听到了人工智能悲惨失败的故事,包括令人沮丧的故事在亚利桑那州坦佩发生的无人驾驶车祸,以及亚马逊 Alexa 在德国慕尼黑开始她自己的派对的欢乐。

另一个现实检验是人们意识到,人工智能的好坏取决于它可以从中学习的数据。一个接一个的演讲者指出,“人工智能战略”始于“数据战略”,我们需要以正确的顺序攀登“人工智能金字塔”。这种回归基础的支点表明,我们正处于拐点,并准备超越早期的人工智能宣传。

#2:“人工智能即服务”是一个令人兴奋的命题

AI 的民主化是会议最突出的主题之一。需要博士学位来构建机器学习算法的日子已经一去不复返了。随着云服务提供商的出现,强大的算法只是一个简单的 API 调用。这些解决方案大大降低了更大的商业社区的准入门槛。

“人工智能就是将不可描述的自动化”——Cassie Kozyrkov,谷歌

Cassie Kozyrkov(@ quae Sita)发表了一篇精彩的主题演讲,讲述了谷歌如何通过云计算和发展决策智能学科来实现人工智能的民主化。AWS 和微软 Azure 等其他云服务提供商展示了利用现成人工智能能力的强大解决方案。此外,来自 SingularityNET 的 Ben goertz El(@ bengoertz El)倡导“去中心化的人工智能”,将人工智能和区块链融合在一起,创造一个开放的市场。对于确保未来人工智能发展的民主化,这是一个有趣的提议。

#3:可解释的人工智能是真实存在的:

深度学习被誉为“黑盒”方法,但模型可解释性是一个活跃的研究领域。为了提高透明度和可解释性,分享了几个建立“玻璃盒子”模型的成功案例。这里有几个可解释人工智能领域的有趣项目:

  • 反向时间注意力模型(RETAIN):RETAIN 模型的开发是为了帮助医生理解为什么一个模型可以预测有心力衰竭风险的患者。
  • 局部可解释的与模型无关的解释( LIME ):一个在决策做出后提供解释的临时模型。
  • 逐层相关性传播( LRP ):这对于计算机视觉通过在神经网络中运行反向传递来识别重要像素特别有用。

#4:金融机构颠覆的时机已经成熟

此次峰会有一个单独的“人工智能在金融”环节,来自全球银行和金融科技的演讲人讨论了金融领域的最新趋势。关键的人工智能用例包括欺诈/合规/网络防御的异常检测,机器人顾问的专家系统和聊天机器人/虚拟代理的客户体验。

“当我们考虑人工智能/人工智能时,它是关于消除摩擦,为客户提供无缝体验”——加文·迈克尔,花旗银行

特别是亚马逊连接和谷歌联络中心,我最近宣布了联络中心人工智能解决方案,承诺更高的效率和更低的运营成本。专家们一致认为,人工后台银行操作可能是人工智能投资在不久的将来的目标。

#5:负责任的人工智能势在必行

去年 7 月,技术界的两位最大人物就人工智能的未来展开了一场非常公开的争论。埃隆·马斯克认为人工智能将导致人类的灭亡,而马克·扎克伯格认为人工智能实际上将有助于进一步创新。两人在社交媒体上争斗,交换琐碎的言论,但本质上两人都代表了人工智能的对立双方:天启与涅槃。无论如何,商业界已经意识到,一般的或“类似人类”的智能要遥远得多,并将其努力集中在具有巨大就业增长潜力的特定领域有影响力的人工智能应用上。

“我们看到人工智能正在帮助人们的工作……同时也开辟了新的工作机会”——Beth Smith,IBM Watson

尤其是“负责任的人工智能”这一主题贯穿了每一次演讲。几位发言者谈到了将“信任”整合为工程原则之一,并将道德和价值观嵌入为人工智能交付成果的一部分。

“我们需要创造负责任的人工智能,这样我们才能给技术带来信任”——大卫·卡莫纳,微软

IBM 已经创建了 AIFairness360 ,这是一个开源工具包,用于减轻机器学习模型中不必要的偏见,以及对抗性鲁棒性工具箱,用于分析机器学习模型的攻击和防御方法。纽约市最近通过了第一项法案来检查政府机构中的“算法偏见”。在可预见的未来,负责任的人工智能可能会成为技术、社会学和政治讨论的焦点。

总的来说,这是一次了不起的学习经历,有精彩的演讲、演示和小组讨论。我真的很喜欢与其他人工智能专业人士互动,并能够在行业内建立有价值的联系。感谢 AI Summit(@ Business _ AI# AISummit)举办了一场现象级的大会!

咖啡势利和机器学习的故事

原文:https://towardsdatascience.com/https-medium-com-yoni-levine-coffee-snobbery-45ed534136e5?source=collection_archive---------8-----------------------

机器学习能帮助我们找到一杯完美的咖啡吗?

“Snobs come in all shapes and sizes. In the food world you’ll find some of the biggest snobs around, those who only eat the most hand-foraged or urban-farmed, artisanally crafted, truffled morsels. But no snob is more outrageously self-righteous than the coffee snob”

我们都有这样的朋友,那个令人讨厌的朋友,他认为自己比任何人都好。他们鄙视星巴克,大规模生产咖啡,一边喝着他们的早茶,一边大声宣称“葡萄酒的味道、馅饼皮和活泼的草莓酸味在舌头上跳舞”🙄。

嗯,就是我!

我决定将我对咖啡的热爱与我对机器学习的热情结合起来,尝试回答世界上最紧迫的问题之一:是什么造就了一杯完美的五星咖啡?

是什么造就了⭐️⭐️⭐️⭐️⭐️☕️那杯完美的五星咖啡?

第一步是获得一些数据。我使用一个名为 Selenium 的 Python 包来收集近 500 种咖啡、它们的评级、评论和许多其他细节的【mistobox.com (我使用的一种奇妙的咖啡订阅服务)。

痴迷于一杯咖啡需要考虑很多因素——原产国、品种、海拔、加工方法、烘焙方式、混合与单一产地,当然还有品尝记录。

这些特征中的任何一个能帮助预测哪种咖啡会获得五星评级吗——还是人们的口味太多样化了,以至于无法确定哪种咖啡胜出?

一旦我清理和组织了所有的数据,我就开始做探索性数据分析 ( EDA)。EDA 正在探索和可视化我们的数据,以帮助我们了解我们的数据是什么样的。有多少台烘烤机?一杯咖啡的平均等级是多少,什么应该被认为是一杯特别的咖啡?

我还使用了自然语言处理(使用文本作为我们的输入特征,而不仅仅是数字),使用用户留下的书面评论来创建额外的特征,从而为我们的数据集增加更多价值。我认为任何分数高于 80 分的咖啡都是“好”咖啡。

我认为任何分数高于 80 分的咖啡都是“好”咖啡。

机器学习(为了掩盖整个博士课程的知识价值)是指我们使用数学公式和大量数据来看看我们是否能发现模式并做出预测。它通常集中在这个问题:给定输入 X,正确的预测 Y 是什么?在这种情况下,假设一种咖啡有 X 个因素(国家、品种等),我们能否预测它是否会得分高于 4 星(我们的输出 Y)?

我尝试了几种流行的机器学习模型,最终使用了一种叫做随机森林的算法对我们的咖啡进行分类。随机森林模型的一个伟大之处在于,我们可以回顾过去,看看我们的模型在做出决策时发现哪些特征是重要的。

Feature importances of our model. Note that it could be important in determining a good or bad coffee.

该模型确定了四个最重要的特征,即海拔、价格、混合和埃塞俄比亚。这与我在 EDA 中观察到的情况非常吻合,生长在高海拔和更贵的咖啡比低海拔和更便宜的咖啡得分更高。埃塞俄比亚是我最喜欢的咖啡种植区,也比其他国家得分高。此外,混合咖啡比标有浓缩咖啡或单一产地的咖啡得分更低。

虽然我们的特性确实有意义,但我们仍然需要看看我们的模型实际上表现如何。我们的准确率是 76 分,这听起来还不错,直到我们考虑到 75%的咖啡被贴上“不太好”的标签。我们的模型甚至没有超过基线准确度(对于每一种咖啡,仅仅猜测所得到的准确度分数),所以它实际上没有做得很好。

因此,虽然从准确性的角度来看这个项目不是很好,但它仍然是一个有趣的工作,也是一个很好的学习经历。似乎人们对咖啡的偏好差异太大,很难选出一个明确的赢家,还是我们没有足够的数据?

对你来说,怎样才是一杯完美的咖啡?你做过类似的项目吗?留言评论!

想看看我的代码或问我一个问题吗?看看我的 GitHub 或者和我在 LinkedIn 上聊天。

在新闻文章上使用情感分析的算法交易

原文:https://towardsdatascience.com/https-towardsdatascience-com-algorithmic-trading-using-sentiment-analysis-on-news-articles-83db77966704?source=collection_archive---------4-----------------------

嗯,我应该为我的考试而学习,但我很想在我休息的时候探索这个。我意识到,我可以使用我以前项目中的元素来做这件事。我之前写了关于通过网络抓取实现社交媒体竞赛自动化的文章,我还写了关于 T2 生成新加坡式文本信息的文章,我在那里处理文本数据。这一切是如何重叠的,难道不有趣吗?

算法交易

Algo trading 通过根据一套定义的规则快速准确地执行订单,实现了金融市场交易流程的自动化。它们消除了人为错误(假设算法是在没有人为错误的情况下开发的),也消除了根据情绪采取行动的危险。生产中使用的算法可能相当复杂,并且需要针对低延迟系统进行大量优化。

我将对一只股票实施一个非常基本的策略(基于趋势)。使用简单的技术指标,如均线,趋势跟踪策略通常简单明了。有趣的是,我们将在算法中加入与公司相关的新闻中的定性元素(讽刺的是,这是基于情感的行为)。

情感分析

情感分析或观点挖掘是指使用 NLP、文本分析和计算语言学来确定主观信息或作者/主题/话题的情绪状态。它通常用于评论,为企业节省了大量手动阅读评论的时间。

Why bother reading the entire description on https://www.comp.nus.edu.sg/programmes/ug/ba/ when you could just mine a sentiment score out of it?

Why should you dampen your mood from reading unconstructive comments on your FB page?

就像算法交易一样,情绪分析也可以作为一个领域深入发展。除了给出积极/消极的情绪,我们还可以理解文本有多主观,不同情绪的强度(兴奋、沮丧等)。),如何莎士比亚式或特朗普式的文本,等等。

方法学

脸书最近面临很多反弹,我认为观察股票如何随着新闻情绪波动会很有趣。

这个想法很简单。我们在商业时报上搜索任何与脸书相关的文章,挖掘文本,获得每天的总体情绪,如果情绪上升 0.5,就买入 10 股,如果情绪下降 0.5,就卖出。请记住,情绪范围从-1 到 1,0 是中性的,我们使用前一天的情绪在当天交易。

与我之前关于网络抓取的文章类似,我使用了同样的想法,从搜索页面中提取 URL,并访问每篇文章来挖掘其前一天的情绪。

Scraping Business Times articles related to Facebook

情感存储在字典中,例如{datetime.date(2018,7,5):-0.59,...,}

VADER 情感分析

VADER(用于情感推理的效价感知词典)是一个预建的情感分析模型,包含在 NLTK 包中。它可以给出积极/消极(极性)以及文本的情感强度(强度)。它以规则为基础,严重依赖人类通过亚马逊机械土耳其人(Amazon Mechanical Turk)对文本进行评级。亚马逊机械土耳其人是一个众包电子平台,利用人类智能来完成计算机目前无法完成的任务。这实际上意味着其他人已经为我们做了建立情感词汇的脏活。对我们来说,这些是单词或任何文本形式的交流,通常根据它们的语义取向被标记为正面或负面)

Throwback to the good old days of Human Calculators

文本的情感得分可以通过对文本中每个词的强度求和,然后归一化得到。维达的人类评分员使用 5 种试探法来分析情绪:

  1. 标点 —我爱披萨 vs 我爱披萨!!
  2. 大写 —我饿了!!vs 我饿了!!
  3. 程度修饰语(强化词的使用) —我要吃饭!!VS 我好想吃!!
  4. 连词(情感极性的转变,随后决定极性) —我爱披萨,但我真的讨厌必胜客(差评)
  5. 先于三元组(通过检查词汇特征之前的三元组来识别相反的极性——加拿大比萨饼其实并没有 那么好。

然而,VADER 专注于社交媒体和短文本,不像财经新闻,它们几乎是相反的。我在笔记本中加入了一大块内容,用来自其他来源/词典的词汇+情绪来更新 VADER 词典,例如拉夫兰-麦克唐纳金融情绪词汇列表

有了这样一个简单的代码,我们可以很容易地从一篇文章中获得情感。

from nltk.sentiment.vader import SentimentIntensityAnalyzernltk.download('vader_lexicon')
sia = SentimentIntensityAnalyzer()
polarity_scores(passage)['compound']

执行战略

最后,通过使用 backtrader 包,我们有了一个方便的框架来回溯测试和编写我们的交易策略。我使用了文档中的快速入门代码作为基础,并对其进行了修改,以包括我们的情感分数。

我指定了从 Yahoo Finance 获取的“FB”股票源,设置了 10 万美元的初始金额,每笔交易 10 手的固定规模,0.1%的佣金,以及一个简单的策略,如果前一天的情绪得分比前一天增加 0.5,就买入,如果减少 0.5,就卖出。

结果

Results from backtest with Day, Close, Sentiment Score, Details of Trade

我以 10 万美元开始,以 99742 美元结束。哈哈。对此我什么都不会说。

From top to bottom panels: 1) Cash Value across time 2) Net Profit/Loss 3) Buy/Sell orders executed at Green/Red markers 4) Sentiment Score.

好吧,这个结果有点出乎意料,因为现实比我们的模型要复杂得多。注意当情绪得分波动时,交易是如何执行的。事实上,这个模型/我肯定非常愚蠢,我们总是落后,在“炒作”之后立即执行交易。但你可以看到这一点,我们肯定可以通过纳入更多的技术指标来建立战略,甚至通过在更多相关的金融新闻上训练我们自己的模型(可以使用 NLTK)来改善情绪分析。

我希望你们都喜欢这本书,这次我对可读性和简洁性更加谨慎了。如果您有任何意见、反馈和想法,请留下。我真的很感激。下次见!

链接到项目回购

在 LinkedIn 或通过 jasonyip184@gmail.com 与我进一步讨论!

参考文献

http://datameetsmedia . com/Vader-情操-分析-解释/

部署机器学习从未如此容易

原文:https://towardsdatascience.com/https-towardsdatascience-com-deploying-machine-learning-has-never-been-so-easy-bbdb500a39a?source=collection_archive---------4-----------------------

使用 Google App Engine 快速启动您的 sklearn 代码并在云中运行🚀

对于数据科学从业者来说,第一次从概念验证到实际工作产品可能会令人望而生畏。幸运的是,不断发展的云服务可以提供帮助。迈出部署的第一步并不像过去那样困难。

在这篇文章中,我将通过一个基于 sklearn 框架的例子来演示如何借助谷歌应用引擎轻松实现这一点。

A bartender spraying a cloud of App Engine smoke on a whiskey drink, making it ready for serving

当谈到为公司的需求构建机器学习应用程序时,工程师可能会热衷于遵循某些最佳实践。我个人的灵感来自于谷歌的 ML 规则,特别是:

规则#4 :保持 模型简单 架构 正确

来自一个以研究为导向的学术背景,我承认这是一个我很容易忽略的规则。与研究环境不同,在公司工作会让机器学习工程师面对其他类型的利益相关者,主要是:

  • :对于工程师来说,能够提出可解释的结果、可解释的算法以及能够就此进行交流是很重要的。无论是哪种情况,黑匣子被批准和实际使用的机会总是较小,因为在监控它们时会出现困难。
  • 其他工程师 :对于机器学习模型来说,不仅要以离线模式运行来描述过去的事件,还要提供预测能力,这些可能需要与公司 IT 基础设施的其余部分进行通信(例如在电子商务平台上提供实时建议,或者在打车应用程序上提供驾驶员的预计到达时间)。实现这一点的一种方法是将每个模型视为一个微服务,并使其通过 REST API 接口进行通信。

基础设施即服务( IaaS )和平台即服务( PaaS )提供商的大规模增长,使得机器学习工程师更容易部署实时产品,并确保估计器管道的可靠性。

在您可以用来部署模型的云工具中,值得一提的有:

  • 【亚马逊网络服务(AWS) :弹性容器服务,SageMaker,Lambda
  • 【谷歌云平台(GCP) :计算引擎、App 引擎、云 ML、云功能
  • 其他 : Heroku,Algorithmia

在这篇文章中,我将展示如何利用云服务部署和服务一个简单的机器学习模型。

我将重点介绍 PaaS Google App Engine,它是一个完全托管的多功能工具,允许工程师构建几乎任何类型的应用程序。App Engine 附带了大多数流行语言(Java、PHP、Node.js、Python、C#)的标准运行时。Net,Ruby,Go)。它还支持定制运行时的 Docker 容器部署。

该项目

它是关于基于 Python 包 sklearn 中可用的 20Newsgroups 公共数据集部署文本分类器。

该数据集由论坛文本消息组成,从 20 个论坛/主题中取样。主题被同等地表示,每个论坛消息被分配给恰好一个主题。

文本分类器被设计成将字符串列表作为输入,并为每个字符串返回前 3 个最可能的论坛主题,以及置信度得分。

哪些工具

虽然 Google Cloud ML 提供了 sklearn ,但是只支持纯 sklearn 模型。包装的 sklearn 型号尚不支持

因此,我们将使用多功能工具 App Engine 来训练包装的文本分类器,将其二进制表示转储到 Google 云存储中,从那里加载并交付预测。

我们将使用 Python、Google Cloud Python SDK、Flask/Gunicorn 进行应用部署,使用 sklearn 进行模型规范。

基础设施

这是我们将要构建的云基础架构的概述。

because an article on Google Cloud is not really one without a flow chart

1 |设置您的 Google 云项目

为了能够在 GCP 上部署应用程序,您首先需要设置一个项目 。特别是,你必须安装谷歌云软件开发工具包(T21),它允许你从命令行与 GCP 服务进行交互。*

在撰写本文时,谷歌提供了 12 个月的试用期,价值 300 美元。更多信息 此处

2 |编写 sklearn-Flask 应用程序

完整的资源库可以在 Github 上找到。其组织结构如下:

*/ 
|_ core.py           # sklearn estimator definition
|_ main.py           # Flask app definition
|_ requirements.txt  # Python dependencies
|_ app.yaml          # AppEngine config file*

一些代码亮点

core.py为一个(文本矢量器,分类器)Pipeline定义一个包装器类。它的fit方法获取20 个新闻组数据集,并在其上安装一个 20 类分类器。

Custom sklearn wrapped estimator

main.py定义烧瓶应用程序。特别是,它有两个处理器/fit/predict以及一个初始化处理器_load_model

  • _load_model 检查在环境变量GCS_BUCKETGCS_BLOB指定的路径下是否有模型二进制文件,如果有加载它:

  • fit_model 适合一个TextClassifier转储到谷歌云存储:

  • predict_from_model 返回基于文本输入参数的预测,假定TextClassifier已经预先加载到内存中:

3 |配置

AppEngine 服务的所需配置通过app.yaml文件进行通信。特别是,您可以指定运行时、环境变量、实例资源以及一个entrypoint。这个项目的entrypoint基于我们的 Flask 应用程序启动了一个 Gunicorn 服务器。

App Engine configuration

4 |部署

如果你已经安装了 Google Cloud SDK,你可以cd进入项目的根目录并调用

*$ gcloud app deploy*

如果部署成功,返回消息应该是这样的(注意项目名称):

*Deployed service [textclassifier] to [https://textclassifier-dot-*my-project-name*.appspot.com]You can stream logs from the command line by running: $ gcloud app logs tail -s textclassifier To view your application in the web browser run: $ gcloud app browse -s textclassifier*

让我们做些测试,好吗?或者*curl* 它喜欢贝克汉姆⚽️

我们使用优秀的命令行工具curl向我们刚刚部署的端点发出 HTTP 请求。

测试 1:训练模型并将其转储到 GCS

*curl --request GET [https://textclassifier-dot-*my-project-name*.appspot.com/fit](https://textclassifier-dot-*my-project-name*.appspot.com/fit)*

几秒钟后返回

*Model successfully fitted and dumped to gs://textclassifier/model.joblib*

测试 2:获得预测

输入字符串是

  • "My car wont start."
  • "I have been having a sore throat for a month"
*content_type="Content-Type: application/json"
request="POST"
data='{"text":["My car wont start.", "I have been having a sore throat for a month"]}'
http="https://textclassifier-dot-sephora-analytics.appspot.com/predict"curl --header "$content_type" \ --request POST \ --data "$data" \ $http*

返回

*[
  [
    { "label" : "rec.autos" "score" : 0.20318951690486 },
    { "label" : "rec.motorcycles", "score" : 0.0730013311549759 },
    { "label" : "misc.forsale", "score" : 0.0593155469643825 }
  ],
  [ 
    { "label" : "sci.med", "score" : 0.119263497157416 },
    { "label" : "sci.crypt", "score" : 0.0616682653727299 },
    { "label" : "talk.politics.guns", "score" : 0.0599605990114599 }
  ]
]*

我们所看到的

我们在 sklearn 和 Flask 之上构建了一个简单的 Python 应用程序。我们使用 Google App Engine 进行模型部署和服务,使用 Google Cloud Storage 进行模型二进制存储。这个例子已经尽可能的通用,以适应其他的用例,所以你没有理由不…

开始建造🔨!

图片来源:Artem PochepetskyAnnie SprattUnsplash

马尔科夫蓝调:使用 VLMMs 和 PST 为 12 小节蓝调人工生成的旋律

原文:https://towardsdatascience.com/https-towardsdatascience-com-markovian-blues-ba35ce9f21d4?source=collection_archive---------11-----------------------

想象一下,当你感到穷困潦倒时,你唯一的解决办法就是沉浸在一些忧郁中。你拿出吉他,开始弹奏 12 小节蓝调,很快意识到如果你的生活依赖于它,你就不能即兴创作,甚至不能唱歌。你站起来,砸碎你的吉他,反复观看柯基犬的视频,让自己感觉更好。

有了可变长度马尔可夫模型(VLMMs)和预测后缀树(PST ),你再也不必经历这一悲剧事件。使用这些算法,你可以人工生成你自己的蓝调旋律,而不必担心你缺乏天赋!

动机

当在作曲过程中遵循基于规则的方法时,音乐创作本身可以是相当算法化的。音乐理论的数学本质允许在对某些音乐作品或流派建模时进行非常有趣的分析。这让我们可以训练算法,可以为我们生成音乐!

许多机器学习算法被用于模拟音乐的序列方面。简单的基于规则的编程和复杂的深度学习技术已经被用来人工生成听起来非常自然的歌曲。在这个项目中,我们设计了一个简单的方法来模拟和生成 12 小节蓝调旋律。

将音乐建模为马尔可夫链

为旋律建模的一个简单方法是将其视为马尔可夫链。一阶马尔可夫链具有下面的 马尔可夫性质无记忆性质

Markov Property

这就是说,序列中下一个状态的概率只是有条件地依赖于当前状态。在一段旋律中,下一个音符的值只取决于当前的音符,而不考虑之前旋律的其余部分。

考虑一下的前两小节,玛丽有只小羊羔

First two bars of Mary Had A Little Lamb

在这种情况下,我们有三种可能的状态:G,A,b。我们可以简单地用马尔可夫链来模拟这个旋律。

如果我们相信这个序列遵循马尔可夫性质,我们可以创建下面的转移矩阵 A:

Transition Matrix of 1st two bars of Mary Had A Little Lamb

当看这个表时,我们感兴趣的是从状态 i → j 或行→列转换的概率。比如从音符 G音符 A 的概率是 1/3。
(即 P(A|G) = 1/3)

请注意,下一个状态 j 仅依赖于当前状态 I,而不考虑之前的所有状态(即 i-1,i-2,… i = 1)。

在忽略历史的情况下,一阶马尔可夫链当然是对旋律建模的一种非常幼稚的方法。实际上,序列中的音符不仅依赖于之前的音符,还依赖于之前的 L 音符。这就把我们引向了一个叫做高阶马尔可夫链的马尔可夫链的扩展。

高阶马尔可夫链使用这种有限存储器 L 的思想,其中序列中的下一个状态取决于当前状态和 L-1 个先前状态。在音乐中,如果我们设置 L=3,我们可以说下一个音符有条件地依赖于前面的三个音符。

这样够好了吗?

不要!L 阶马氏链的缺点是关键字有限。在一阶马氏链的类似情况下,我们不能假设下一个音符只是条件依赖于前一个固定长度的 L 个音符。实际上,下一个音符取决于上下文、或实际序列本身。

这激发了灵活内存的概念。在过去的不同部分影响未来的情况下,我们将上下文大小 L 设置为变量而不是有限的。比方说,我们有一段音乐,它的上升全音阶序列和琶音序列具有相同的最小值和最大值。我们可以假设,平均来说,全音阶序列的上下文会比琶音序列长。

可变长度马尔可夫模型

VLMMs 允许比马尔可夫链或高阶马尔可夫链更真实的序列建模。他们能够在序列中封装模式,这是以前的模型所缺乏的。为了训练 VLMM,我们必须指出 L 的最大上下文长度和要考虑的序列应该出现的最小次数(nmin)。本质上,我们存储的是 0

Suffix Tries → Suffix Trees →Prediction Suffix Trees

The data structure that efficiently builds and stores VLMMs is a 预测后缀树的所有 I 阶马尔可夫链。要建立理解的基础,我们必须描述一下后缀 Trie* 。*

回到玛丽有只小羊羔的前两小节,我们有这样的顺序:
G→A→B→A→G→G→G→G

Suffix Trie for first two bars of Mary Had A Little Lamb

下面的后缀 trie 可以从这个序列中创建。构建这棵树相当简单。从序列的开头开始,为整个序列创建一个节点路径。然后从序列的第二个音符开始,为该后缀创建一个节点路径。如果还没有为给定的符号创建根节点的子节点,则添加该子节点。否则,沿着路径,直到给定的序列还没有出现在树中;然后将其添加到相应的节点。我们这样做,直到我们到达序列的最后一个音符。

Suffix Tree for first two bars of Mary Had A Little Lamb

后缀 trie 可以很容易地转换成后缀树。前面的后缀 trie 被转换成下面的后缀树。后缀 trie 和后缀树之间的唯一区别是,后者将非分支路径折叠成具有单个节点的单条边。

现在我们对后缀树有了一个概念,让我们来看一下预测/概率后缀树。考虑下面的后缀树。

Suffix tree for BANANA$

该树遵循香蕉\(序列。我们使用\)来表示序列的结束,这样更容易在树中定位结束序列节点。现在,PST 不再像传统后缀树那样自顶向下存储序列,而是以不同的方式构建。

PST for BANANA$ with respective probabilities for symbols ($, A, B, N) respectively. L = 3 and nmin = 1

出于视觉目的,当 PST 侧放时更容易观察。该树按原样从左→右读取,如果垂直显示,则从下→上读取。终端节点代表后缀的开始。从根开始的直接子代是每个后缀的最后一个符号。

该 PST 的最大 L = 3,nmin = 1。此外,每个节点还保存后缀中的下一个符号的概率,这取决于它之前的后缀路径。比如 P($|A-N) = 0.33。根 e 包含生成任何序列的第一个符号的概率。

注意:$不会作为节点出现在这个树中,因为它出现在序列的末尾,没有任何后续状态。此外,请记住,树将根据参数设置(即 L 和 nmin)而变化。增加 L 将创建具有更长路径的树,增加 nmin 将创建稀疏树。

PST 的平滑参数

当使用 VLMMs 进行分类时,避免对序列的训练集过度拟合是很重要的。此外,如果您的目标是人工生成,我们当前的 PST 将只生成它所输入的数据中的序列。为了解决这个问题,我们设置了任意序列的最小概率(ymin)。在下图中,我们设置 ymin = 0.01。

PST for BANANA$ with L = 3, nmin = 1 and ymin=0.01

该平滑参数的添加将减少分类模型的方差,使得它对模型未被训练的观察不敏感。该参数还允许在音乐生成的上下文中有一些艺术自由度。

修剪 PST

像在决策树中一样,我们有能力修剪我们的概率后缀树。我们的重点是从底层到根的子节点的序列分布。从终端节点开始,我们检查与没有前缀的上下文相比,具有这个前缀是否提供了关于最后符号的条件概率的更多信息。例如,与 A|A 相比,A|N-A 能为我们提供多少信息?为了正式确定是否修剪节点,我们执行以下计算。

Pruning equation

等等什么?这个看似复杂的方程,本质上很简单。我们来分解一下!

首先,分数确定后缀的概率分布是否与其父后缀相似,其中相似性由值 C 控制。参数 C 本质上约束了概率商。方括号外的大“I”是一个指示函数,如果计算结果为真,则产生 1,否则产生 0。指示器确定如果给定任何序列 c 和没有其第一个符号 suf(c) 的相同序列,在序列末尾的任何新符号的概率在两者之间是否会显著不同?然后我们加起来有多少新符号是真的(因此是求和符号)。如果对于至少一个新符号这是真的(≥1 项),那么我们将保留该节点。否则,修剪!

修剪将通过移除不提供显著信息增益的节点来减轻 PST 的复杂性(我们可以没有它们)。此外,如果您的 L、nmin 和 ymin 的初始设置创建了一个非常复杂的树,修剪将简化它!但是,您仍然应该花时间来适当地优化这些初始参数。

创作蓝调

马尔可夫链或 VLMMs 的结构本身并不复杂。困难在于试图实际定义什么是状态。到目前为止,我们只是在模型中使用旋律的音高值作为状态。下一节将揭示这种方法的缺点,并解释创建状态的更好的方法。然后,我们解释了一个旋律是如何产生的,并证明了 12 小节蓝调旋律使用多个 PST 模型的合理性。

编码状态

分析旋律序列时,考虑每个音符的音高和持续时间是很重要的。如果我们把音高和音长结合在一起,我们会有一个巨大的状态空间。例如,如果我们将粒度级别的持续时间视为至少 1/4(四分音符)的值,我们将有四种不同类型的持续时间值要考虑(即,1/4:四分之一、1/2:一半、3/4:点分四分之一和 1:整)。考虑到四个不同的持续时间值和 12 个音高,我们最终得到 48 个状态。进一步分解持续时间将会成倍地增加我们的状态空间。

为了简化我们的模型,并保持一个较小的状态空间,我们决定将各个时间段视为状态,而不是各个音符。我们把每首歌分解成持续一个酒吧⅛的时间段;一首 12 小节蓝调基本上包含 128 = 96 个事件。每个事件用音调值与二进制值的组合来编码(即,S =停留,L =离开)。*

All durations and encodings of note A

使用这种编码,我们总共有 26 种不同的状态!这来自 12 个不同的音高、1 个休止符和两个延音符号(即 _S 和 _L)。对于我们来说,生成所需长度的序列也容易得多。在具有相同长度的序列固有地具有不同持续时间的情况下,我们以前的方法会很困难。

数据集

歌曲的主体来自老式爵士乐标准假书,其中包括 20 世纪早期到中期的数百个爵士乐标准的铅表。标志性的 12 小节蓝调结构推动了低音线,刺激了架子鼓,触动了象牙,并拉伸了大多数歌曲的声带。在任何调中遵循 12 小节布鲁斯结构的任何线都包含在数据集中。

12-Bar Blues Chord Structure

手动对导音表进行数字编码,记录每个音符及其在旋律中各自的持续时间。我们的语料库继续增长,但目前有 22 个 12 小节蓝调旋律序列,每个序列包含 96 个事件!

建模方案

有了这组 12 小节的蓝调旋律以及编码状态的方法,我们应该如何构建模拟蓝调旋律的模型呢?

注意 12 小节蓝调的严格结构。几乎所有的和弦都不止出现一次。主和弦 I 在这个和弦进行中最多出现八次。此外,当有多个部分具有相同的基本和弦时,旋律的小部分肯定会重复。例如,在现代音乐中,韵文和合唱总是分别有相似的旋律。

如果我们要将原始的 12 小节蓝调分割成两小节部分,我们将得到以下小节序列。

12-Bar Blues Structure with two-bar segments

然后我们决定为每首歌的每两个小节建立一个单独的模型。这给了我们总共六个不同的模型。我们计算了六个部分的 PST 分布之间的成对散度测量。这类似于比较两个分布之间相似性的 KL 散度度量。在信息论中,KL 散度通常用于评估压缩某些文件并确保它包含与原始文件一样多的信息的效率。

在我们的例子中,成对散度的低值表示分布非常相似,反之亦然。这意味着我们可以在不丢失信息的情况下互换使用它们。热图显示,Ia、Ib、Ic 和 Id 部分具有相似的分布。因此,我们可以删除六个模型中的三个,只保留第一个 Ia 模型,将其视为通用 I 模型。

产生旋律

我们剩下三个模型:Ia、IV 和 v。要创建旋律,我们只需从每个模型生成一个两小节序列,并将它们连接在一起。多亏了我们的编码方法,生成双条码序列变得很容易!我们需要做的就是创建长度为 16 的序列,因为每个符号都有一个音高和 1/8 的持续时间值。I 模型的输出将重复四次,以模拟 12 小节蓝调的结构。瞧啊。我们有一段 12 小节的蓝调旋律。

让我们来点刺激的!使用 GarageBand,我添加了一个节奏部分,还将时髦的电脑发声旋律设置到了干净吉他乐器设置中。

摘要

这个项目描述了一种使用可变长度马尔可夫模型生成 12 小节蓝调旋律的方法。修剪的概率后缀树被很好地构造以适合 VLMM,这有助于我们分析和生成新的序列。我们用精心编码的 1/8 音符状态填充 PST,以考虑音高和持续时间。我们还证明了只需要 3 个不同的模型来生成完整的 12 小节旋律。

未来的工作

这种方法可以应用于任何遵循重复和弦进行的音乐流派。许多现代歌曲遵循类似的和弦结构,其旋律可以用 VLMMs 和 PST 来建模。我们甚至可以模拟不同的乐器部件,甚至和弦结构本身!VLMMs 也是 NLP 的很好的模型,所以创作歌词也是可能的。那我们就有了一个完全人工生成的乐队!

所有生成你自己旋律的数据和代码都可以在这里找到。下载回购协议后,只需运行 generateFunction 中的脚本。R 文件,用合适的参数调用 generateMelody() 函数。在 generated_melodies/wav/ 路径下会创建一个 wav 文件。保持原样或者添加到generated _ melodies/midi/blues _ backing 中的背景音轨。**

要进一步了解 VLMMs 和 PST,请参考本文件。用于构建 PSTs 的 R 包的文档在这里是。
这里有一个帮助理解 PST 和使用 R 包的指南

如有任何问题,请随时联系我。希望你喜欢这篇文章!

搜索引擎和神经网络

原文:https://towardsdatascience.com/https-towardsdatascience-com-search-engines-and-neural-networks-97e0df4f088d?source=collection_archive---------5-----------------------

在我们的生活中,没有一天我们不使用谷歌,“谷歌搜索”这个术语已经悄悄进入我们的生活,现在已经成为一种必需品。我们想到的第一个问题可能是谷歌是如何做到的?谷歌,作为一个已经进入如此多专业领域的公司,但对于一个门外汉来说,谷歌总是“搜索引擎”的同义词。搜索结果中的付费广告在公司收入中扮演着重要的角色。他们的搜索引擎有很多竞争对手,比如日本的雅虎,俄罗斯的 Yandex 等等,但是没有一家像谷歌一样吸引了全球的关注。那么这个搜索引擎背后是什么呢?它崛起了,它仍然是搜索引擎中最好的原因与它的底层架构有很大关系。它们背后的主要概念是什么?

信息检索就是这样一个概念,它涉及对搜索引擎的研究。

信息检索 ( IR )是从信息资源集合中获取与信息需求相关的信息资源的活动。搜索可以基于全文或其他基于内容的索引。

这是搜索术语时最相关结果的第一行。这来自它的维基百科页面,因为谷歌已经将维基百科整合到他们的搜索结果中。聪明的策略?当然,鉴于维基百科拥有所有常用词汇和技术的最可信数据集。

Google’s Result Page for ‘Information Retrieval”

这里可以清楚地看到 dictionary 元素的使用。他们有自己的字典,如果这个单词有共同的意义或者不是很多单词的组合,它会显示为第一个结果。基本上,如果与搜索的单词直接匹配,它会显示字典作为结果。在这种情况下,所有部分案例都将被忽略。例如,如果我在前面的查询中添加了单词 concept,那么字典结果不会显示出来。

Google’s Result Page for “information retrieval concept”

现在有一个不同的方法,显示了维基百科页面的预览。如果我们以这种方式继续下去,谷歌的搜索平台将有大量的东西可以探索。让我们回到这里的概念。信息检索:从网络上检索信息并与用户的查询相匹配的概念。给用户提供最相关的结果是搜索引擎行业的标准。我经常使用谷歌的“我感觉很幸运”来查询显而易见的问题的原因。那么他们用什么模型在我们的搜索结果中对页面进行排名呢?

PageRank:-以谷歌创始人之一拉里·佩奇命名的算法最初被称为 BackRub,当时它仍是斯坦福大学的一个研究项目,因为它用于跟踪反向链接以确定网站的重要性。这不是决定页面排名的唯一算法。有超过 250 个其他指标显然是一个秘密,所以我们每天得到的搜索结果是不掺杂的。

咖啡因升级:-推出于 2009 年,这次升级提高了获得搜索结果的速度和更新的索引架构。随着来自微软的 Bing 的竞争,他们转向了 Bigtable,公司的分布式数据库平台。

蜂鸟升级:-蜂鸟是世界上最小也是最快的鸟之一。为了证明这次升级的名称,谷歌在 2013 年增加了改进的功能,在搜索结果中包括网站的特定相关页面,而不是网站的主页。有一个明确的重点是人类搜索互动,从而使它成为一个更好的搜索引擎。

谷歌还做了许多其他改变,比如为用户提供更好的搜索引擎优化功能、知识图表(2012 年)、专用移动搜索结果(2016 年)等等。除了谷歌在他们的产品上所做的,搜索引擎还有其他的进步。从我收集的资源来看,其中最重要的是神经网络在网络搜索中的应用。神经网络已经存在了很长一段时间,但没有人想到过使用深度神经网络来改进搜索引擎,直到 2016 年发表了一篇题为“网络搜索的神经点击模型”的研究论文

用户行为是改进搜索引擎的关键部分。这就是点击模型发挥作用的时候了。下面是研究论文中的一部分,对其进行了总结

这些模型也称为点击模型,因为主要观察到的用户与搜索系统的交互涉及点击,这些模型用于点击预测,并且它们可以在我们没有真实用户进行实验或者因为害怕伤害用户体验而不愿意与真实用户进行实验的情况下提供帮助。点击模型还用于改进文档排名(即,从点击模型预测的点击中推断文档相关性)、改进评估度量(例如,基于模型的度量)以及通过检查点击模型的参数来更好地理解用户

点击模型的两种方法:

  • PGM(概率图形模型):用户行为被表示为一系列可观察和隐藏的事件,如点击、跳过和文档检查。现在为了更好地理解,把一个事件想象成一个有向图。它有一些有向边形式的依赖关系。现在,在基于 PGM 的点击模型中,我们必须手动设置这些依赖关系的结构。不同的车型(UBM、DBN、CM 等)有不同的标准。下图清楚地证明了有向图的工作原理。

Cascade Click Model Representation(From this Survey)

  • DR(分布式表示方法):在这里,用户行为被表示为向量状态,这些向量状态以他/她的信息需求和会话期间消耗的信息的形式捕获用户的行为。这让我们能够挖掘比 PGM 的二进制事件更复杂的模式。神经点击模型是基于这一概念的方法。该模型学习与传统点击模型中使用的概念相似的概念,并且它还学习其他不能手动设计的概念。

在这个神经点击模型中,用户行为被建模为用户信息需求的分布式表示的序列和用户在搜索期间消费的信息。与现有的点击模型相比,所提出的框架的主要优势是用户行为模式可以直接从交互数据中学习,这
允许我们捕获比
现有点击模型中硬编码的用户行为模式更复杂的用户行为模式。Yandex(俄罗斯流行的搜索引擎)的资源被用于评估该模型,并且在点击预测和相关性预测任务中有显著的改进。

Different configurations of NNs explained in the research paper

谷歌在这方面的进展如何?就像可口可乐的配方一样,谷歌搜索中的精确算法是一个秘密。尽管不可否认,他们从 2016 年开始在自己的架构中使用深度神经网络。这里有一篇连线文章更详细地讨论了这个话题。每个人都确信的一件事是,神经网络是信息检索中的下一件大事。从 WSDM 2018(网络搜索和数据挖掘)到 ECIR 2018(欧洲信息检索会议)的所有会议都有关于同一主题的演讲

作为临别赠言,我想说这篇文章可能在你的脑海中引起了更多的疑问。这只是我在不久的将来将要做的一系列文章的介绍,这些文章将对包括神经点击模型在内的每个模型进行更深入的分析(以及代码片段)。

人体活动识别(HAR)教程(第 1 部分)

原文:https://towardsdatascience.com/human-activity-recognition-har-tutorial-with-keras-and-core-ml-part-1-8c05e365dfa0?source=collection_archive---------0-----------------------

如何将 Keras 模型加载到您的 iOS 项目中的分步指南

Photo: a-image/Shutterstock

如果你想在任何 iOS 设备上快速部署神经网络,Keras 和苹果的 Core ML 是一个非常强大的工具集。大多数其他教程侧重于图像识别的流行的 MNIST 数据集。我们将超越这个广泛覆盖的机器学习例子。相反,您将学习如何处理时间分片的多维传感器数据。

更具体地说,我们将训练一个深度神经网络(DNN),以识别运动的类型(行走、跑步、慢跑等)。)基于来自围绕人的腰部携带的移动设备的一组给定的加速度计数据。在本教程中,我们将使用 WISDM 数据集( WISDM )。

本文介绍的方法应该适用于您在物联网(IOT)中可能遇到的任何其他传感器数据。本文将带您完成以下步骤:

  • 从 WISDM 数据集中加载加速度计数据
  • 将加速度计数据转换并重新格式化为时间片表示
  • 可视化加速度计数据
  • 重塑多维表格数据的形状,使其被 Keras 接受
  • 将数据集分成训练集、验证集和测试集
  • 在 Keras 中定义一个深度神经网络模型,该模型稍后可以由苹果的核心 ML 处理
  • 为人体活动识别数据训练深度神经网络
  • 使用学习曲线和混淆矩阵,对照测试数据验证训练好的 DNN 的性能
  • 为核心 ML 导出训练好的 Keras DNN 模型
  • 通过在 Python 中进行样本预测,确保核心 ML 模型被正确导出
  • 在 Xcode 中创建一个游乐场,并导入已经训练好的 Keras 模型
  • 使用 Apple 的核心 ML 库,以便使用 Swift 预测给定数据集的结果

执行本文中解释的所有步骤的先决条件(包括测试代码的版本号):

  • Python(版本 3.6.5)
  • Keras(版本 2.1.6)
  • 张量流(版本 1.7.0)
  • Coremltools(版本 2.0)

不在本文讨论范围之内:为这种类型的问题语句创建具有最高性能的完美机器学习模型不是本演练的重点。

您可能想知道为什么本文选择 Keras 而不是其他框架,即 TensorFlow。有两个主要原因:

  • Keras 非常容易学习,并且拥有比 TensorFlow 更现代、更直观的 API,同时仍然在后端利用 TensorFlow 的功能
  • 有多个 TensorFlow APIs 在尝试使用更方便的估算器 API(这也是 TensorFlow 团队推荐的——你可以在这里找到更多信息这里)时,我在将经过训练的估算器转换为核心 ML 时遇到了编译问题

概念概述

在我们介绍 Python 和 Xcode 中的不同步骤之前,让我们简要地看一下问题陈述和我们的解决方案。我们使用的数据集是从智能手机上采集的加速度计数据,不同的人在进行六种不同的运动(下楼、慢跑、坐着、站着、上楼、走路)时随身携带该智能手机。对于每个练习,测量 x、y 和 z 轴的加速度,并用时间戳和个人 ID 捕获。

有了这些可用的数据,我们想训练一个神经网络,以了解一个人携带智能手机是否正在进行这六种活动中的任何一种。一旦神经网络根据现有数据进行了训练,它应该能够在给定以前看不到的数据时,正确预测一个人正在进行的活动类型。

这个问题的解决方案是深度神经网络。基于可用的数据,它将学习如何区分六种活动中的每一种。然后,我们可以向神经网络显示新数据,它会告诉我们用户在任何特定时间点正在做什么。这个问题的解决方案如下图所示。

“Deep Neural Network Example” by Nils Ackermann is licensed under Creative Commons CC BY-ND 4.0

下面描述了解决机器学习问题的典型步骤。在整篇文章中,我们将经历一个非常相似的过程。

“Machine Learning Workflow” by Nils Ackermann is licensed under Creative Commons CC BY-ND 4.0

导入库

首先,我们需要导入所有必要的 python 库。如果您缺少其中一些,请使用 pip 安装程序安装它们。

导入库之后,让我们设置一些标准参数并打印出我们已经安装的 Keras 版本。WISDM 数据集包含六个不同的标签(楼下、慢跑、坐着、站着、上楼、走路)。因为我们将多次使用标签列表,所以我们为它们创建一个常量(标签)。下一个常量 TIME_PERIODS 存储时间段的长度。常量 STEP_DISTANCE 确定两个连续时间段之间的重叠量。

keras version  2.1.6

加载、检查和转换加速度计数据

接下来,你需要在这里下载的数据集并保存在本地。重要的文件是 WISDM_ar_v1.1_raw.txt,在进行导入之前,我们先定义几个方便的函数,以便读取数据和显示数据的一些基本信息。

数据成功加载到数据帧中。现在,我们可以显示数据帧的前 20 条记录,并进一步了解数据的分布情况。

Number of columns in the dataframe: 6
Number of rows in the dataframe: 1098203

正如我们所看到的,我们有更多关于步行和慢跑活动的数据,而不是其他活动。我们还可以看到有 36 个人参与了实验。

接下来,让我们来看看所有六个可能活动的三个轴的加速度计数据。数据以 20 赫兹的采样率记录(每秒 20 个值)。因为我们显示了前 180 条记录,所以每个图表显示了六个活动中每个活动的 9 秒间隔(计算:0.05 * 180 = 9 秒)。我们将使用两个函数(我从这里借用了)来绘制数据。

正如所料,与坐着相比,慢跑和散步等活动的加速度更高。在我们继续之前,我们将在数据帧中再添加一个名为“ActivityEncoded”的列,其中包含每个活动的编码值:下楼、慢跑、坐着、站着、上楼、散步

这是必要的,因为深度神经网络不能与非数字标签一起工作。有了 LabelEncoder,我们能够轻松地转换回原来的标签文本。

将数据分成训练集和测试集

将整个数据集分成训练集和测试集是很重要的。通常,您会看到数据分割方式上的错误。无论您决定如何分割数据,您都不希望来自测试集的信息渗透到您的训练集中。这可能对您的模型在训练期间的整体性能有很大帮助,然后根据测试集进行验证。但是你的模型不太可能很好地概括它还没有见过的数据。

分裂背后的想法是:我们希望我们的神经网络从几个经历过实验的人那里学习。接下来,我们想看看我们的神经网络预测以前没有见过的人的运动有多好。

要避免的数据分割

仅仅担心每个活动至少有几个示例记录是不够的。您将冒这样的风险:在训练集中,您可能有三个关于人 5 的活动“行走”的记录,而在测试集中,有一个关于人 5 的活动“行走”的记录。当然,在这种情况下,您的模型会表现得很好,因为它已经在训练期间看到了第 5 个人的移动模式。始终对 DNN 的性能持批评态度,这可能是因为一开始就进行了错误的数据分割。

更好的分割方法

在我们的例子中,让我们根据用户 id 进行划分。我们将保留 ID 为 1 到 28 的用户用于训练模型,ID 大于 28 的用户用于测试集。

规范化培训数据

接下来,我们需要在训练数据中标准化我们的特征。当然,有各种各样的方法来标准化。请记住,以后在向神经网络输入新数据时,您会使用相同的归一化算法。否则你的预测将会是错误的。除了标准化之外,我们还将对这三个特征进行舍入。

将数据重组为片段,并为 Keras 做准备

数据帧中包含的数据尚未准备好输入神经网络。因此,我们需要重塑它。让我们为此创建另一个名为“创建 _ 段 _ 和 _ 标签”的函数。该函数将接收数据帧和标签名称(我们在开始时定义的常量)以及每个记录的长度。在我们的例子中,让我们进行 80 步(参见前面定义的常数)。考虑到 20 Hz 的采样率,这等于 4 秒的时间间隔(计算:0.05 * 80 = 4)。除了对数据进行整形之外,该函数还会将要素(x-加速度、y-加速度、z-加速度)和标注(相关活动)分开。

现在,你应该在 x 列车和 y 列车上都有 20.868 的记录。x_train 中的 20.868 个记录中的每一个都是形状为 80x3 的二维矩阵。

x_train shape:  (20868, 80, 3)
20868 training samples
y_train shape:  (20868,)

为了构建我们的深度神经网络,我们现在应该存储以下维度:

  • 时间段数:这是一个记录中的时间段数(因为我们希望有 4 秒的时间间隔,所以在我们的例子中这个数字是 80)
  • 传感器数量:这是 3 个,因为我们只使用 x、y 和 z 轴上的加速度
  • 类别数量:这是神经网络中输出层的节点数量。因为我们希望我们的神经网络预测活动的类型,我们将从我们之前使用的编码器中获取类的数量。
['Downstairs', 'Jogging', 'Sitting', 'Standing', 'Upstairs', 'Walking']

我们希望输入网络的数据是二维的(80x3)。不幸的是,Keras 和 Core ML 不能同时处理多维输入数据。因此,我们需要将输入层的数据“展平”到神经网络中。我们将输入一个包含 240 个值的列表,而不是一个形状为 80x3 的矩阵。

x_train shape: (20868, 240)
input_shape: 240

在继续之前,我们需要将所有特征数据(x_train)和标签数据(y_train)转换成 Keras 接受的数据类型。

我们几乎完成了数据的准备工作。我们需要做的最后一步是对我们的标签进行一次性编码。请只执行这一行一次!

New y_train shape:  (20868, 6)

在 Keras 中创建深度神经网络模型

到现在为止,你已经完成了你这边所有的负重。数据以这样的格式准备好了,Keras 将能够处理它。我已经决定创建一个具有 3 个隐藏层的神经网络,每个隐藏层有 100 个完全连接的节点(可以随意改变网络的形状,甚至切换到更复杂的网络,如卷积神经网络)。

重要提示:正如您所记得的,我们已经将输入数据从 80x3 矩阵重新整形为长度为 240 的向量,以便 Apple 的 Core ML 可以稍后处理我们的数据。为了扭转这种情况,我们在神经网络中的第一层将把数据重塑为“旧”格式。最后两层将再次展平数据,然后运行 softmax 激活函数来计算每个类的概率。请记住,在我们的案例中,我们使用了六个类别(下楼、慢跑、坐着、站着、上楼、走路)。

_________________________________________________________________
Layer (type)                 Output Shape              Param #   
=================================================================
reshape_2 (Reshape)          (None, 80, 3)             0         
_________________________________________________________________
dense_5 (Dense)              (None, 80, 100)           400       
_________________________________________________________________
dense_6 (Dense)              (None, 80, 100)           10100     
_________________________________________________________________
dense_7 (Dense)              (None, 80, 100)           10100     
_________________________________________________________________
flatten_2 (Flatten)          (None, 8000)              0         
_________________________________________________________________
dense_8 (Dense)              (None, 6)                 48006     
=================================================================
Total params: 68,606
Trainable params: 68,606
Non-trainable params: 0
_________________________________________________________________
None

在 Keras 中拟合 DNN 模型

接下来,我们将使用之前准备的训练数据来训练模型。我们将定义一个关于训练准确性的早期停止回调监视器:如果训练在连续两个时期内未能提高,那么训练将以最佳模型停止。用于训练的超参数非常简单:我们将使用 400 个记录的批量大小,并将训练 50 个时期的模型。对于模型训练,我们将使用 80:20 分割来分离训练数据和验证数据。就这么简单。所以让我们继续训练我们的模型。不同的超参数有一些很好的解释,比如这里的

这款简单的 DNN 性能还可以。我们的验证准确率约为 74%。这肯定可以改进,也许通过进一步的超参数调整,特别是通过修改神经网络设计。在我们继续测试验证之前,我们将打印训练和验证数据集的学习曲线。

precision    recall  f1-score   support

        0.0       0.70      0.42      0.53      1864
        1.0       0.98      0.98      0.98      6567
        2.0       0.99      0.99      0.99      1050
        3.0       0.99      0.99      0.99       833
        4.0       0.66      0.63      0.64      2342
        5.0       0.85      0.93      0.89      8212

avg / total       0.87      0.87      0.87     20868

对照测试数据进行检查

让我们继续这个模型,看看它在我们之前保留的测试数据中表现如何。在我们的例子中,我们将根据模型尚未看到的六个用户的运动来检查性能。

6584/6584 [==============================] - 1s 128us/step

Accuracy on test data: 0.76

Loss on test data: 1.39

测试数据的准确率为 76%。这意味着我们的模型对尚未见过的人有很好的推广性。让我们看看我们的模型在哪里错误地预测了标签。

 precision    recall  f1-score   support

          0       0.61      0.27      0.37       650
          1       0.80      0.95      0.87      1990
          2       0.82      0.99      0.90       452
          3       0.91      0.74      0.81       370
          4       0.48      0.42      0.45       725
          5       0.77      0.79      0.78      2397

avg / total       0.74      0.76      0.74      6584

正如您所看到的,模型的精度对于预测慢跑(1)、坐着(2)、站着(3)和行走(5)是很好的。该模型对于清楚地识别楼上和楼下的活动有问题。

当然,改进模型仍有很大的潜力,例如,通过使用更先进的神经网络设计,如卷积神经网络(CNN)或长短期记忆(LSTM)。我可能会在以后的文章中探讨这个问题。对于我们展示端到端流程的目的来说,这个结果已经足够好了。

冻结核心 ML 的 Keras 模型

如果您对该模型及其性能满意,您应该现在就将其转换,以便与 Core ML 一起使用。convert 函数只接受几个参数:

  • 对您的 Keras 模型的引用
  • 要为输入数据指定的名称;在我们的例子中,我们将加速度数据输入网络
  • 要分配给输出的名称
  • “人类可读的”标签名称;你可以再次使用我们在开始时定义的标签常数
input {
  name: "acceleration"
  type {
    multiArrayType {
      shape: 240
      dataType: DOUBLE
    }
  }
}
output {
  name: "output"
  type {
    dictionaryType {
      stringKeyType {
      }
    }
  }
}
output {
  name: "classLabel"
  type {
    stringType {
    }
  }
}
predictedFeatureName: "classLabel"
predictedProbabilitiesName: "output"

将 Keras 预测与核心 ML 预测进行比较

在使用您的核心 ML 模型之前,让我们确保导出是成功的,并且当给定一个随机数据集时,我们的 Keras 模型和核心 ML 模型提供相同的预测。

Prediction from Keras:
Jogging

Prediction from Coreml:
Jogging

好消息!对于索引为 1 的记录,Keras 和 Core ML 都预测相同的标签,即慢跑。我们现在可以在任何 iOS 设备上使用我们的核心 ML 模型了。

总结和下一步

在本文中,您已经学习了如何加载和转换复杂的加速度计数据,并通过 Keras 中的深度神经网络运行它。您将训练好的模型导出到一个核心 ML 文件中。在我的下一篇文章中,我将向您介绍在一个简单的 Swift 程序中使用这一经过培训的核心 ML 模型的必要步骤。然后,您可以使用这些知识将 DNN 部署到任何 iOS 设备上。

本文的 Jupyter 笔记本可以在 github 上获得。

链接和参考

  • 官方巨蟒网站
  • 官方网站
  • 官方 TensorFlow 网站
  • 苹果官方核心 ML 文档
  • 苹果官方 coremltools github 仓库
  • 很好的概述来决定哪个框架适合你: TensorFlow 还是 Keras
  • Aaqib Saeed 关于人类活动识别的卷积神经网络(CNN)的好文章(也使用 WISDM 数据集)
  • 另一篇文章也使用了通过 TensorFlow 实现的 WISDM 数据集和由维尼林·瓦尔科夫撰写的更复杂的 LSTM 模型

放弃

本网站上的帖子是我个人的,不一定代表我的雇主的帖子、策略或观点。

使用 Keras 和 Core ML 的人体活动识别(HAR)教程(第 2 部分)

原文:https://towardsdatascience.com/human-activity-recognition-har-tutorial-with-keras-and-core-ml-part-2-857104583d94?source=collection_archive---------9-----------------------

如何将 Keras 模型加载到您的 iOS 项目中的分步指南

Photo: a-image/Shutterstock

我之前的文章讲述了在 Python 中使用苹果的 Core ML 工具从 Keras 创建一个多维深度神经网络的核心 ML 文件(DNN)。如果你想知道如何在不创建完整的 iOS 应用程序的情况下,在 Swift 操场上快速测试这个模型,请继续阅读。本文将涵盖以下步骤:

  • 将核心 ML 模型文件加载到 Xcode 中
  • 检索生成的核心 ML 存根源和编译的核心 ML 模型
  • 创建一个 Xcode 游乐场,并导入核心 ML 存根源和编译的核心 ML 模型
  • 写几行 Swift 代码,以便对多维传感器数据进行预测

将核心 ML 文件加载到 Xcode 中

为了在 Swift 操场上使用任何 Core ML 模型,首先需要创建一个常规的 Xcode 项目(例如,单视图应用程序)。一旦项目被创建,搜索文件HARClassifier.mlmodel,这是你在我上一篇文章中作为最后一步创建的。将文件拖放到您创建的 Xcode 项目中。

Drag and drop the mlmodel file into Xcode

如果您单击 Xcode 中的HARClassifier.mlmodel,模型评估参数将与我们在 Keras 中定义的输入和输出相匹配:

  • 输入:这是一个包含 240 个条目的多数组(原始 80 x 3 矩阵的平面向量)
  • 输出:输出参数将六项活动中每一项的概率存储为字典;classLabel 参数是一个字符串,包含给定输入的最可能活动的名称

接下来,您需要两件工艺品来为您的游乐场做准备:

  • 核心 ML 存根来源:在“模型评估参数”部分上方,您将看到一个名为“模型类”的部分。核心 ML 模型的导入也创建了必要的 Swift 代码,以便在操场上使用该模型。如果单击类名 HARClassifier 旁边的箭头,您可以查看已生成的代码。
  • 核心 ML 模型的编译版本:继续构建并运行您的应用程序。一旦您的应用程序已经构建并且模拟器已经启动,您必须检索编译的.mlmodelc文件。打开取景器并按下CMD-Shift-G,然后进入以下路径~/Library/Developer/Xcode/DerivedData。导航到为您的应用程序创建的文件夹。在那里,进入文件夹Build/Products/Debug-iphonesimulator,显示程序MediumHARTutorial的包内容(或者你给你的 Xcode 项目取的任何名字)。最后,在这里你会找到文件夹HARClassifier.mlmodelc。这是模型的编译版本。

Retrieve the model class and the compiled Core ML model

有了这两件艺术品,你现在就可以创建你的 Swift 游乐场了。

创建一个新的 Swift 游乐场

返回 Xcode,创建一个新的(空白)playground 文件。在 playground 中,将编译后的核心 ML 模型添加到Resources文件夹中,将 Swift 源文件添加到Sources文件夹中。

Add model class and compiled Core ML model to the playground

在导入核心 ML 模型期间创建的存根源都有一个内部保护级别。您需要将所有三个类及其成员都改为public(文件在本文末尾引用),以便在您的游戏中使用它们。生成的三个类是:

  • 定义类型MLFeatureProvider的模型预测输入的类。
  • 定义类型MLFeatureProvider的模型预测输出的类。
  • 该类提供对核心 ML 模型的访问,主要用于通过prediction函数进行推理。

做预测

现在,是时候在 Swift 中最终做出预测了。为此,您只需要几行代码。

实际上,您可以直接从加速度计加载传感器数据,并进行与训练期间相同的归一化预处理。出于简单的原因,您可以简单地将选定的传感器序列从 Python 复制并粘贴到 XCode 中,然后处理结果。

Swift Core ML example code to make predictions for accelerometer data

XCode Playground 中的输出显示了概率最高的预测标签以及所有其他标签的概率。

Predicted label: Upstairs
Probability per label: ["Sitting": 2.0439521186688125e-09, "Jogging": 0.00010426577500766143, "Upstairs": 0.49756348133087158, "Standing": 1.2845226184804437e-12, "Walking": 0.11116743087768555, "Downstairs": 0.39116477966308594]

摘要

在前一篇文章和本文中,我们经历了在 Keras 中创建机器学习模型、将其导入 Xcode 并使用 Swift 编程语言在 iOS 中进行预测的端到端过程。操场文件和 Jupyter 笔记本(来自上一篇文章)可以在 Github 上获得。

放弃

本网站上的帖子是我个人的,不一定代表我的雇主的帖子、策略或观点。

人类可解释的机器学习的重要性

原文:https://towardsdatascience.com/human-interpretable-machine-learning-part-1-the-need-and-importance-of-model-interpretation-2ed758f5f476?source=collection_archive---------1-----------------------

可解释的人工智能(第一部分)

人类可解释机器学习和模型解释简介

介绍

本文是我针对 【可解释的人工智能(XAI)】系列文章的第一篇。由机器学习和深度学习推动的人工智能领域在过去十年中经历了一些惊人的变化。最初只是一个纯学术和研究导向的领域,我们已经看到广泛的行业采用了不同的领域,包括零售,技术,医疗保健,科学和更多。数据科学和机器学习在 21 世纪的主要目标不再只是进行实验室实验来发表研究论文,而是转变为处理和解决现实世界的问题,自动化复杂的任务,让我们的生活变得更加轻松和美好。更多时候,机器学习、统计或深度学习模型的标准工具箱保持不变。像 胶囊网络 这样的新模式确实出现了,但行业采用同样的模式通常需要几年时间。因此,在行业中,数据科学或机器学习的主要关注点更多的是 【应用】 而不是理论,在正确的数据上有效应用这些模型以解决复杂的现实世界问题至关重要。

机器学习模型本身由一种算法组成,该算法试图从数据中学习潜在的模式和关系,而不是硬编码的固定规则。因此,向业务解释模型如何工作总是会带来一系列挑战。在该行业的一些领域,特别是在保险或银行等金融领域,数据科学家最终往往不得不使用更传统的机器学习模型(线性或基于树的模型)。原因是模型的可解释性对于解释模型所采取的每一个决策是非常重要的。但是,这通常会导致牺牲性能。这就是像集成和神经网络这样的复杂模型通常给我们更好和更准确的性能的地方(因为真实的关系在本质上很少是线性的)。然而,我们最终无法对模型决策做出正确的解释。为了解决和讨论这些差距,我将写一系列文章,在这些文章中,我们将深入探索可解释的人工智能(XAI)和人类可解释的机器学习的一些挑战。

本系列的大纲

我们将在这一系列文章中涉及的一些主要领域包括。

第 1 部分:人类可解释的机器学习的重要性

  • 理解机器学习模型解释
  • 机器学习模型解释的重要性
  • 模型解释方法的标准
  • 模型解释的范围

第 2 部分:模型解释策略

  • 模型解释的传统技术
  • 传统技术的挑战和局限
  • 准确性与可解释性的权衡
  • 模型解释技术

第 3 部分:动手模型解释——综合指南

  • 关于使用最新的模型解释框架的实践指南
  • 使用 ELI5、Skater 和 SHAP 等框架的特点、概念和示例
  • 探索概念并观察它们的实际应用——特征重要性、部分相关图、替代模型、用石灰的解释和说明、SHAP 值
  • 基于监督学习示例的机器学习模型解释

第 4 部分:实践高级模型解释

  • 非结构化数据集上的动手模型解释
  • 深度学习模型的高级模型解释

如上所述,这些内容将在本系列的几篇文章中涉及,以保持简洁和有趣,这样每个人都可以从每篇文章中获得一些关键的收获。

动机

作为该行业的一名数据科学家和该领域的指导人员,我看到数据科学仍然经常被视为一个黑匣子,能够表演魔术或炼金术,为人们提供他们想要的东西。然而,残酷的现实是,如果没有对机器学习模型或数据科学管道如何工作的合理理解,现实世界的项目很少会成功。考虑现实世界中的任何数据科学项目,通常会有业务方面和技术或解决方案方面。现在,数据科学家通常致力于构建模型并为业务提供解决方案。然而,企业可能不知道模型如何工作的复杂细节。但是由于这个模型最终会为他们做很多决定,他们有权利提出这个问题,“我怎么能相信你的模型?” 或者 “你的模型到底是怎么做决策的?”回答这些问题是数据科学从业者和研究人员多年来一直在尝试的事情。

数据科学从业者会知道,存在一个典型的 模型可解释性与模型性能的权衡 。这里要记住的一点是,模型性能不是运行时或执行性能,而是模型在做出决策时的准确性。有几种模型,包括简单的线性模型,甚至是基于树的模型,它们可以很容易地解释模型做出的决定,以达到特定的洞察力或预测,但您可能需要牺牲模型的性能,因为由于高偏差(线性模型)或高方差的内在问题,它们总是不会产生最佳结果,从而导致过度拟合(完全生长的树模型)。更复杂的模型,如集成模型和最近的深度学习模型家族,通常会产生更好的性能,但被视为黑盒模型,因为很难解释模型可能如何在幕后真正做出决策。

有些人可能会说,如果某样东西(暂时)运行良好,为什么要质疑它是如何工作的呢?然而,作为人类,逻辑和推理是我们在大多数决定中坚持的东西。因此,向人工智能(AI)决策的范式转变无疑会受到质疑。在许多现实世界的场景中,有偏见的模型可能会产生非常不利的影响。这包括 预测潜在罪犯 司法判决风险评分信用评分、欺诈检测、健康评估、贷款借贷、自动驾驶以及其他许多模型理解和解释至关重要的领域。著名数据科学家和作家 Cathy O' Neil 在她广受好评的书中强调了这一点, 【数学毁灭的武器】

[## 主要的

《摧毁数学的武器》已经入围国家图书奖!书籍简介:前华尔街…

weaponsofmathdestructionbook.com](https://weaponsofmathdestructionbook.com/)

著名研究员兼作家凯特·克劳福德(Kate Crawford)在 NIPS 2017 主题演讲中谈到了机器学习中偏见的含义及其对社会的影响的这些方面, 【偏见的麻烦】

感兴趣的读者还应该看看她在《纽约时报》上的著名文章,【人工智能的白人问题】 ,她向我们展示了机器学习应用的例子,包括图像分类、犯罪风险预测、送货服务可用性以及更多对黑人社区不利的结果。所有这些现实世界的场景都暗示了模型解释应该有多重要,以及我们是否想要利用机器学习来解决这些问题。

[## 观点|人工智能的白佬问题

根据科技界一些知名人士的观点,人工智能对……构成了迫在眉睫的生存威胁

www.nytimes.com](https://www.nytimes.com/2016/06/26/opinion/sunday/artificial-intelligences-white-guy-problem.html)

在过去的一年里,我看到了在解决行业问题的同时对模型解释的需求,在我写我最近的书‘用 Python 进行实用的机器学习’时也是如此。在这段时间里,我有机会与 DataScience.comT21的优秀员工互动,他们非常清楚机器学习模型中人类可解释性的必要性和重要性。他们一直在积极寻找解决方案,并开源了流行的 python 框架Skater。在这一系列的文章中,我们将深入研究溜冰者,并做一些实际的模型解释。除此之外,我们还将全面覆盖其他模型解释框架,如【ELI5】!**

理解机器学习模型解释

机器学习只是在最近几年才在行业中得到广泛采用。因此,模型解释作为一个概念仍然主要是理论性的和主观的。

任何机器学习模型的核心都有一个响应函数,该函数试图映射和解释自变量(输入)和因变量(目标或响应)之间的关系和模式。

当模型预测或发现我们的洞察力时,它会做出某些决定和选择。模型解释试图理解和解释响应函数做出的这些决定,即什么、为什么和如何。模型解释的关键是透明性、质疑的能力以及人类理解模型决策的容易程度。模型解释的三个最重要的方面解释如下。

  1. 驱动模型预测的因素是什么?我们应该能够查询我们的模型,并找出潜在的功能交互,以了解哪些功能在模型的决策制定策略中可能是重要的。这保证了模型的的公平性。
  2. 为什么模型会做出某种决定?我们还应该能够验证和证明为什么某些关键特征会在预测过程中驱动模型做出某些决定。这保证了 问责 和模型的可靠性。
  3. 我们如何相信模型预测?我们应该能够评估和验证任何数据点,以及模型如何对其做出决策。对于关键的利益相关者来说,这应该是可演示的并且容易理解的,即模型如预期的那样工作。这保证了模型的 透明性

机器学习模型的可解释性通常也被称为人类可解释的解释(HII) 是人类(包括非机器学习专家)能够理解模型在其决策过程中所做选择(如何、为什么和什么)的程度。

当比较模型时,除了模型性能之外,如果一个模型的决策比另一个模型的决策更容易被人理解,则该模型比另一个模型具有更好的可解释性。

机器学习模型解释的重要性

当处理机器学习问题时,数据科学家往往倾向于关注模型性能指标,如准确度、精确度和召回率等(这无疑很重要!).这在大多数围绕数据科学和机器学习的在线竞赛中也很普遍。然而,指标仅仅讲述了模型预测决策的一部分。随着时间的推移,由于环境中各种因素导致的模型概念漂移,性能可能会发生变化。因此,最重要的是理解是什么驱动一个模型做出某些决定。

我们中的一些人可能会说,如果一个模型工作得很好,为什么还要深入挖掘呢?请始终记住,在现实世界中解决数据科学问题时,为了让企业信任您的模型预测和决策,他们会不断地问这个问题, “我为什么要信任您的模型?” 这很有道理。如果一个人患有癌症或糖尿病,如果一个人可能对社会构成风险,甚至如果一个客户会流失,你会对一个仅仅预测和做出决定的模型感到满意吗( 什么 )也许不是,如果我们能更多地了解模型的决策过程(为什么如何 ),我们可能会更喜欢。这让我们更加透明地了解为什么模型会做出某些决定,在某些情况下什么可能会出错,随着时间的推移,这有助于我们建立对这些机器学习模型的一定程度的信任。

本节的关键要点是,现在是我们停止将机器学习模型视为黑盒的时候了,我们不仅要尝试分析数据,还要尝试分析模型如何做出决策。事实上,通往这条道路的一些关键步骤是由著名的论文 “我为什么要相信你?”解释任何分类器的预测 作者:M. T. Ribeiro,S. Singh 和 C. Guestrin,SIGKDD 2016,其中他们引入了 LIME(局部可解释模型不可知解释)的概念,我们将在下一篇文章中详细介绍。

他们在论文中提到了一些值得记住的要点。

然而,理解预测背后的原因在评估信任时非常重要,如果一个人计划根据预测采取行动,或者在选择是否部署新模型时,信任是最基本的。

无论人类是直接使用机器学习分类器作为工具,还是在其他产品中部署模型,一个至关重要的问题仍然存在:如果用户不信任模型或预测,他们就不会使用它。

感兴趣的人也可以看看他们在 KDD 会议上关于模型解释的论文。

这是我们在本文中多次讨论过的内容,也是决定行业中数据科学项目成功与否的关键区别之一。这推动了围绕模型解释的需要和重要性的紧迫性。

机器学习模型解释方法的标准

有特定的标准可以用来对模型解释方法进行分类。克里斯托夫·莫尔纳尔(Christoph Molnar)2018 年的 《可解释的机器学习,让黑盒模型变得可解释的指南》 中提到了一个很好的指南

  • ****内在的还是事后的?内在可解释性是指利用本质上可内在解释的机器学习模型(如线性模型、参数模型或基于树的模型)。事后可解释性是指选择和训练一个黑盒模型(集成方法或神经网络),并在训练后应用可解释性方法(特征重要性、部分相关性图)。在我们的系列文章中,我们将更多地关注事后模型可解释方法。
  • ****特定于模型还是与模型无关?特定于模型的解释工具非常特定于固有的模型解释方法,这些方法完全依赖于基于每个模型的能力和特性。这可以是系数、p 值、与回归模型相关的 AIC 分数、来自决策树的规则等等。与模型无关的工具与事后方法更相关,可以用于任何机器学习模型。这些不可知的方法通常通过分析(和输入的扰动)特征输入和输出对来操作。根据定义,这些方法无法访问任何模型内部,如权重、约束或假设。
  • ****本地还是全球?这个解释的分类讲的是解释方法是解释单个预测还是整个模型行为?还是范围介于两者之间?我们将很快更多地讨论全局和局部解释。

这并不是对可解释方法进行分类的一套详尽的标准,因为这仍然是一个新兴的领域,但这可以是比较和对比多种方法的一个很好的尺度。

机器学习模型解释的范围

我们如何定义可解释性的范围和界限?一些有用的方面可以是模型的透明性、公平性和责任性。全局局部模型解释是定义模型解释范围的明确方式。

Summarizing Global and Local Interpretation (Source: DataScience.com)

全球诠释

这一切都是为了试图理解 “模型是如何做出预测的?”“模型的子集如何影响模型决策?”。为了立刻理解和解释整个模型,我们需要全局可解释性。全局可解释性是指能够根据完整数据集上的因变量(响应变量)和独立变量(预测变量)之间的条件交互来解释和理解模型决策。试图理解特性的相互作用和重要性总是理解全局解释的一个好的步骤。当然,当试图分析交互时,在超过两个或三个维度之后可视化特征变得相当困难。因此,经常查看可能影响全局知识模型预测的模块化部件和特征子集会有所帮助。全局解释需要模型结构、假设和约束的完整知识。

本地解释

这都是为了试图理解 “为什么模型为单个实例做出特定的决策?”“为什么模型会对一组实例做出具体的决策?” 。对于局部可解释性,我们不关心模型的内在结构或假设,我们把它当作一个黑盒。为了理解单个数据点的预测决策,我们特别关注该数据点,并查看该点周围的特征空间中的局部子区域,并尝试基于该局部区域理解该点的模型决策。局部数据分布和特征空间可能表现完全不同,并且给出与全局解释相反的更准确的解释。局部可解释模型不可知解释(LIME)框架是一种优秀的方法,可用于模型不可知的局部解释。我们可以使用全局和局部解释的组合来解释一组实例的模型决策。

模型透明度

这一切都是为了理解 “一个模型是如何从算法和特征中创建出来的?”。 我们知道,通常情况下,机器学习模型都是利用数据特征之上的算法来构建一种将输入映射到潜在输出(响应)的表示。模型的透明性可以试图理解更多的技术细节,如模型是如何构建的,以及什么可能影响它的决策。这可以是神经网络的权重、CNN 滤波器的权重、线性模型系数、决策树的节点和分裂。然而,由于企业可能不太精通这些技术细节,试图用不可知的局部和全局解释方法来解释模型决策有助于展示模型的透明性。

结论

模型解释是可以成就或破坏行业中真实世界机器学习项目的东西,并帮助我们向可解释的人工智能(XAI)迈进了一步。让我们努力实现人类可解释的机器学习和 XAI,为每个人揭开机器学习的神秘面纱,并帮助增加对模型决策的信任。

下一步是什么?

在本系列的第 2 部分中,我们将涉及可解释人工智能的以下方面,涉及机器学习模型解释。

  • 模型解释的传统技术
  • 传统技术的挑战和局限
  • 准确性与可解释性的权衡
  • 模型解释技术

感谢 马修【梅奥】 的编辑和转载本文于KD nuggets

感谢所有在DataScience.com的出色的人们,特别是Pramit Choudhary为我构建了一个令人惊叹的模型解释框架,Skater为我提供了这个系列的一些精彩内容。

我在我的书中涵盖了很多机器学习模型解释的例子, 《用 Python 进行实用的机器学习》 。为了您的利益,代码是开源的!

如果你对我的文章或数据科学有任何反馈、评论或有趣的见解要分享,请随时通过我的 LinkedIn 社交媒体频道联系我。

** [## Dipanjan Sarkar -数据科学家-英特尔公司| LinkedIn

查看 Dipanjan Sarkar 在世界最大的职业社区 LinkedIn 上的个人资料。Dipanjan 有 5 份工作列在…

www.linkedin.com](https://www.linkedin.com/in/dipanzan/)**

具有人工智能的类人机器听觉(1/3)

原文:https://towardsdatascience.com/human-like-machine-hearing-with-ai-1-3-a5713af6e2f8?source=collection_archive---------4-----------------------

Photo credit: Jonathan Gross

神经网络在实时音频信号处理中的应用

人工智能技术的重大突破是通过模拟人类系统实现的。虽然人工神经网络(NNs)是与实际人类神经元的功能方式仅松散耦合的数学模型,但它们在解决复杂和模糊的现实世界问题方面的应用已经非常广泛。此外,在神经网络中对大脑的结构深度进行建模,为学习更有意义的数据表示提供了广泛的可能性。

如果您错过了其他文章,请点击下面的链接了解最新情况:

背景:AI 在音频处理上的承诺
批评:CNN 和 spectrograms 做音频处理有什么问题?
第二部分 : 具有人工智能的仿人机器听觉(2/3)

在图像识别和处理方面,CNN视觉系统中复杂且更具空间不变性的细胞所带来的灵感也极大地改进了我们的技术。如果你对在音频频谱图中应用图像识别技术感兴趣,可以看看我的文章“CNN 和频谱图在音频处理中有什么问题?”

只要人类的感知能力超过机器,我们就能从理解人类系统的原理中获益。当谈到感知任务时,人类非常熟练,人类理解和人工智能现状之间的反差在机器听觉领域变得尤为明显。考虑到从人类视觉处理系统中获得灵感所带来的好处,我建议我们从具有神经网络的机器听觉中获得类似的过程。

An overview of the framework which will be proposed during this article series.

在本系列文章中,我将详细介绍与 奥胡斯大学 和智能扬声器制造商Dynaudio A/S合作开发的 AI 实时音频信号处理框架。它的灵感主要来自认知科学,认知科学试图结合生物学、神经科学、心理学和哲学的观点,以更好地了解我们的认知能力。

认知声音属性

也许声音最抽象的领域是我们人类如何感知它。虽然信号处理问题的解决方案必须在低水平的强度、频谱和时间属性的参数内操作,但最终目标通常是认知目标:以改变我们对信号所含声音的感知的方式来转换信号。

例如,如果希望通过编程来改变录制的语音的性别,那么在定义其低级特征之前,有必要用更有意义的术语来描述这个问题。说话者的性别可以被认为是一种认知属性,由许多因素构成:声音的音高和音色、发音差异、词汇和语言选择的差异以及对这些属性如何与性别相关的共同理解。

这些参数可以用较低层次的特征来描述,如强度、光谱和时间属性,但只有在更复杂的组合中,它们才能形成高层次的表示。**这形成了一个音频特征的层次结构,从中可以导出声音的含义。**代表人类声音的认知属性可以被认为是声音强度、频谱和统计属性的时间发展的组合模式。

A hierarchy of features that can be used to derive meaning from digital audio.

神经网络擅长提取数据的抽象表示,因此非常适合检测声音的认知属性。为了建立一个用于此目的的系统,让我们检查声音在人类听觉器官中是如何表示的,我们可以用它来启发用神经网络处理声音的表示。

耳蜗表现

人类的听觉始于外耳,外耳首先由耳廓组成。耳廓充当了一种频谱预处理的形式,其中传入的声音根据其相对于听者的方向而被修改。然后,声音通过耳廓的开口进入耳道,耳道进一步通过共振来修改传入声音的频谱属性,从而放大 1-6 kHz 范围内的频率[1]。

An illustration of the human auditory system.

当声波到达耳道末端时,它们会刺激耳膜,听小骨(人体内最小的骨头)附着在耳膜上。这些骨头将压力从耳道传递到内耳中充满液体的耳蜗耳蜗在引导 NNs 的声音表达方面有很大的兴趣,因为这是负责将声振动转换成人类神经活动的器官。

它是一个盘管,沿其长度被两层膜分开,这两层膜是赖斯纳膜基膜。沿着耳蜗的长度,有一排大约 3500 个内毛细胞[1]。当压力进入耳蜗时,它的两层膜被压下。基底膜在底部窄而硬,但在顶部松而宽,因此沿其长度的每个地方对特定频率的响应更强烈。

简单来说,基膜可以被认为是一个连续的带通滤波器阵列,沿着膜的长度,用于将声音分离成它们的光谱成分。

An illustration of the human cochlea.

这是人类将声压转化为神经活动的主要机制。因此,有理由假设音频的频谱表示将有利于用人工智能对声音感知进行建模。由于沿着基底膜的频率响应呈指数变化[2],对数频率表示可能被证明是最有效的。一种这样的表示可以使用伽马通滤波器组来导出。这些滤波器通常应用于模拟听觉系统中的频谱滤波,因为它们近似人类听觉滤波器的脉冲响应,该脉冲响应来自测量的听觉神经纤维对白噪声刺激的响应,称为“revcor”函数【3】。

A simplified comparison between human spectral transduction and a digital counterpart.

由于耳蜗有大约 3500 个内毛细胞,人类可以检测到长度低至大约 2-5 ms 的声音间隙[1],分成 2 ms 窗口的 3500 个伽马通滤波器的光谱分辨率似乎是在机器中实现类似人类的光谱表示的最佳参数。然而,在实际场景中,我假设较低的分辨率仍然可以在大多数分析和处理任务中实现理想的效果,同时从计算的角度来看更可行。

许多用于听觉分析的软件库可以在线获得。一个著名的例子是 Jason Heeris 的 Gammatone 滤波器组工具包。它提供了可调节的滤波器,以及使用 gammatone 滤波器对音频信号进行类似声谱图分析的工具。

神经编码

当神经活动从耳蜗移动到听觉神经和上行听觉通路时,在到达听觉皮层之前,脑干核团中应用了许多过程。

这些过程形成了一个代表刺激和感知之间接口的神经代码。关于这些核的具体内部工作的许多知识仍然是推测性的或未知的,所以我将只在它们更高的功能水平上详细描述这些核。

A simplified illustration of the ascending auditory pathway (for one ear) and its assumed functions.

人类的每只耳朵都有一组相互连接的细胞核,但为了简单起见,我只展示了一只耳朵的流程。耳蜗核是来自听觉神经的神经信号的第一个编码步骤。它由各种具有不同属性的神经元组成,用于执行声音特征的初始处理,其中一些神经元指向与声音定位相关的上橄榄,而其他神经元则指向通常与更高级特征相关的侧丘系下丘[1]。

J.J. Eggermont 在“在声音和感知之间:回顾对神经代码的搜索”中详细描述了来自耳蜗核的这种信息流如下:“腹侧[耳蜗核] (VCN)提取并增强在[听觉神经]纤维的放电模式中多路复用的频率和定时信息,并通过两条主要路径分发结果:声音定位路径和声音识别路径。VCN (AVCN)的前部主要服务于声音定位方面,其两种类型的浓密细胞为上橄榄复合体(SOC)提供输入,在此为每个频率分别绘制耳间时差(itd)和水平差(ILD)。**

声音识别路径所携带的信息是诸如元音的复杂频谱的表示。这种表现主要是由被称为“斩波器”()神经元的特殊类型单元在耳蜗腹侧核中产生的[4]。这些听觉编码的细节很难详细说明,但它们向我们表明,输入频谱的一种“编码”形式可以提高对低水平声音特征的理解,并使声音印象在 NNs 中的处理成本更低。**

频谱声音嵌入

我们可以应用无监督的自动编码器神经网络架构来尝试学习与复杂光谱相关的共同属性。就像单词嵌入,在代表声音精选特征的频谱中找到共性是可能的(或者一个更紧密浓缩的意为)。

自动编码器被训练成将输入编码成压缩表示,该压缩表示可以被重构回与输入具有高度相似性的表示。这意味着自动编码器的目标输出是输入本身[5]。如果一个输入可以在没有很大损失的情况下被重建,那么网络已经学会以这样一种方式对它进行编码,即压缩的内部表示包含足够多的有意义的信息。这种内部表现就是我们所说的嵌入。自动编码器的编码部分可以与解码器分离,以便为其他应用程序生成嵌入。

A simplified illustration of an autoencoder architecture for spectral sound embeddings.

嵌入还有一个好处,那就是它们通常比原始数据的维度更低。例如,自动编码器可以将总共有 3500 个值的频谱压缩成长度为 500 个值的向量。简而言之,这种向量的每个值可以描述更高级别的频谱因子,例如元音、刺耳或和谐度——这些只是示例,因为由自动编码器导出的统计公共因子的含义可能通常难以用简单的语言来标注。

在下一篇文章中,我们将通过增加内存来扩展这一思想,为音频频谱的时间发展产生嵌入。

这是我关于人工智能音频处理系列文章的第一部分。接下来,我们将讨论声音中感觉记忆和时间依赖性的基本概念。

如果你喜欢这篇文章,请随时关注并留下你的掌声。

参考

[1] C. J. Plack,《听觉》,第二版。心理学出版社,2014。

[2] S. J. Elliott 和 C. A. Shera,“作为智能结构的耳蜗”,智能材料。结构。,第 21 卷,第 6 期,第 64001 页,2012 年 6 月。

[3] A.M. Darling,“gammatone 滤波器的特性和实现:指南”,言语听力和语言,伦敦大学学院,1991 年。

[4] J. J. Eggermont,“在声音和感知之间:回顾对神经代码的研究。,“听到了。《研究报告》,第 157 卷,第 1-2 期,第 1-42 页,2001 年 7 月。

[5]t . p . Lilli rap 等,学习 AI 的深度架构,第 2 卷,第 1 期。2015.

具有人工智能的类人机器听觉(2/3)

原文:https://towardsdatascience.com/human-like-machine-hearing-with-ai-2-3-f9fab903b20a?source=collection_archive---------7-----------------------

Photo credit: rawpixel

记忆的重要性

嗨,欢迎回来!本系列文章详细介绍了我与奥胡斯大学和智能扬声器制造商丹拿合作开发的一个人工智能实时音频信号处理框架。

如果您错过了之前的文章,请点击下面的链接了解最新情况:

背景:AI 在音频处理上的承诺
批评:CNN 和 spectrograms 做音频处理有什么问题?
第一部分 : 具有人工智能(1/3)的仿人机器听觉

在前面的部分中,我们描绘了人类如何体验声音的基本原理,即在耳蜗中形成的光谱印象,然后由脑干核序列进行“编码”。这篇文章将探讨我们如何在产生频谱声音嵌入时将记忆与用于声音理解的人工神经网络相结合。

回声记忆

声音事件的含义在很大程度上源于频谱特征之间的时间相互作用。

这方面的一个证据是,人类的听觉系统根据时间背景以不同的方式对语音的相同音素进行编码[1]。这意味着一个音素 /e/ 在神经学上对我们来说可能意味着不同的东西,这取决于它之前的东西。

记忆对于进行声音分析至关重要,因为只有将“那一刻”的印象与之前的印象进行比较才是可能的,前提是它们确实存储在某个地方。

人类的短期记忆是由一系列整合了感觉记忆和工作记忆的成分组成的。在对声音感知的检查中,已经在人类中发现了听觉感觉记忆(有时也称为回声记忆)。c .阿兰等人。艾尔。将听觉感官记忆描述为“听觉感知中的关键第一阶段,允许听者将传入的声音信息与先前听觉事件的存储表征进行整合”【2】。

从计算上来说,我们可以把回声记忆看作是即时听觉印象的短暂缓冲。

关于回声记忆的持续时间一直存在争议。在纯音和口语元音掩蔽研究的基础上,D. Massaro 论证了大约 250 ms,而 A. Treisman 基于两耳分听实验论证了大约 4 秒[3]。为了将回声记忆的想法与神经网络相结合,我们可能不需要确定感觉存储的固定持续时间,但我们可以在几秒钟的范围内对记忆进行实验。

兜圈子

用数字光谱表示法实现感觉记忆可能相当简单。我们可以简单地分配一个循环缓冲器来存储先前时间步的预定数量的光谱。

An illustrated circular buffer for holding spectral memory (where t denotes the timestep).

循环缓冲区是一种数据结构,由一个被视为循环的数组组成,当数组长度达到后,其索引循环回 0[4]。

在我们的例子中,这可能是一个多维数组,其长度为所需的内存量,循环缓冲区的每个索引保存特定时间步长的完整频谱。计算新光谱时,会将它们写入缓冲区,如果缓冲区已满,则会覆盖最早的时间步长。

随着缓冲区的填充,两个指针被更新:一个尾指针标记最新添加的元素,一个头指针标记最老的元素,因此也是缓冲区的开始[4]。

下面是一个 Python 中循环缓冲区的例子,改编自埃里克·威瑟:

import numpy as npclass CircularBuffer():
    # Initializes NumPy array and head/tail pointers
    def __init__(self, capacity, dtype=float):
        self._buffer = np.zeros(capacity, dtype)
        self._head_index = 0
        self._tail_index = 0
        self._capacity = capacity # Makes sure that head and tail pointers cycle back around
    def fix_indices(self):
        if self._head_index >= self._capacity:
            self._head_index -= self._capacity
            self._tail_index -= self._capacity
        elif self._head_index < 0:
            self._head_index += self._capacity
            self._tail_index += self._capacity # Inserts a new value in buffer, overwriting old value if full
    def insert(self, value):
        if self.is_full():
            self._head_index += 1 self._buffer[self._tail_index % self._capacity] = value
        self._tail_index += 1
        self.fix_indices()

    # Returns the circular buffer as an array starting at head index
    def unwrap(self):
        return np.concatenate((
            self._buffer[self._head_index:min(self._tail_index, self._capacity)],
            self._buffer[:max(self._tail_index - self._capacity, 0)]
        )) # Indicates whether the buffer has been filled yet
    def is_full(self):
        return self.count() == self._capacity # Returns the amount of values currently in buffer
    def count(self):
        return self._tail_index - self._head_index

减少输入大小

为了以每时间步 5 ms 的分辨率存储完整的第二个频谱,需要容量为 200 个元素的缓冲器。这些元素中的每一个都包含一个频率幅度数组。如果需要类似人类的光谱分辨率,这些数组将包含 3500 个值。对于总共 200 个时间步长,要处理 700,000 个值。

如果传递给人工神经网络,长度为 700,000 个值的输入存在计算开销大的风险。这种风险可以通过降低光谱和时间分辨率或在内存中保持较短的光谱信息持续时间来减轻。

我们还可以从 Wavenet 架构中获得灵感,该架构利用扩展因果卷积来优化对原始样本音频中大量顺序数据的分析。正如 A. Van Den Oord 等人在中所解释的,“扩张卷积(也称为á trous,或带孔卷积)是一种卷积,其中通过跳过某个步长的输入值,在大于其长度的区域上应用滤波器” [5]。

假设最近输入的频率数据是瞬时声音分析的最大决定因素,那么扩展频谱缓冲器可能是减少计算内存大小的有用工具。

Two methods for dimensionality reduction with dilated spectral buffers (in this figure unrolled for clarity).

通过与原始缓冲区成比例地将新缓冲区中的每个时间步长扩大某个比例(例如, 2^t 的指数增加),维度可以显著减少,同时保持最近时间步长的光谱发展的高分辨率。可以通过简单地越来越向后查找单个值来从原始缓冲区获得扩展缓冲区的值,但是也可以通过提取持续时间内的平均或中值频谱来组合要折叠的时间步长的数量。

扩展光谱缓冲区背后的驱动概念是将最近的光谱印象保留在内存中,同时以有效的方式保留一些关于“大画面”上下文的信息。

下面是使用 Gammatone 滤波器组制作扩展频谱帧的简化代码片段。注意,这个例子使用离线处理,但是滤波器组也可以实时应用,将频谱帧插入到循环缓冲器中。

from gammatone import gtgram
import numpy as np

class GammatoneFilterbank:
    # Initialize Gammatone filterbank
    def __init__(self, 
                 sample_rate, 
                 window_time, 
                 hop_time, 
                 num_filters, 
                 cutoff_low):
        self.sample_rate = sample_rate
        self.window_time = window_time
        self.hop_time = hop_time
        self.num_filters = num_filters
        self.cutoff_low = cutoff_low # Make a spectrogram from a number of audio samples
    def make_spectrogram(self, audio_samples):
        return gtgram.gtgram(audio_samples,
                             self.sample_rate,
                             self.window_time,
                             self.hop_time,
                             self.num_filters,
                             self.cutoff_low) # Divide audio samples into dilated spectral buffers
    def make_dilated_spectral_frames(self, 
                                     audio_samples, 
                                     num_frames, 
                                     dilation_factor): spectrogram = self.make_spectrogram(audio_samples)
        spectrogram = np.swapaxes(spectrogram, 0, 1)
        dilated_frames = np.zeros((len(spectrogram), 
                                  num_frames, 
                                  len(spectrogram[0])))

        for i in range(len(spectrogram)):
            for j in range(num_frames):
                dilation = np.power(dilation_factor, j)

                if i - dilation < 0:
                    dilated_frames[i][j] = spectrogram[0]
                else:
                    dilated_frames[i][j] = spectrogram[i - dilation]

        return dilated_frames

Result: Two examples of dilated spectral buffers visualized as a quadrilateral mesh.

嵌入缓冲区

在人类记忆的许多模型中,选择性注意被应用在感觉记忆之后,作为一种过滤器,以防止短期记忆中的信息过载【3】。由于人类的认知资源有限,将注意力分配给某些听觉以优化精神能量的消耗是有利的。

这个过程可以通过扩展自动编码器神经网络架构来实现。使用这种架构,可以将声音的感官记忆与选择性注意力的瓶颈结合起来,方法是向其提供扩展的频谱缓冲区以产生嵌入,而不是仅提供瞬时频率信息。为了处理顺序信息,可以使用一种称为序列到序列自动编码器的特殊类型架构【6】。

序列到序列( Seq2Seq )模型通常使用 LSTM 单位将一个数据序列(例如,一个英语句子)编码为一个内部表示,其中包含该序列作为一个整体的压缩“含义”。然后,这种内部表达可以被解码成一个序列(同样的句子,但以西班牙语为例)[7]。

以这种方式嵌入声音的一个特点是,它使得使用简单的前馈神经网络来分析和处理声音成为可能,这种网络运行起来更便宜。

在训练如下图所示的网络之后,右半部分(解码部分)可以被“切断”,从而生成用于将时间频率信息编码到压缩空间中的网络。Y. Chung 等人在这一研究领域取得了良好的成果。艾尔。通过应用 Seq2Seq 自动编码器架构[6],成功地生成了描述声音记录的顺序语音结构的嵌入。随着输入数据更加多样化,也有可能产生以更通用的方式描述声音的嵌入。

A simplified illustration of a sequential autoencoder which produces temporal sound embeddings.

用 Keras 倾听

使用上述方法,我们可以用 Keras 实现 Seq2Seq 自动编码器来产生音频嵌入。我称之为监听器 网络,因为它的目的是“监听”传入的声音序列,并将其简化为更紧凑、更有意义的表示,以便我们进行分析和处理。

为了训练这个网络,使用了来自 UrbanSound8K 数据集的约 3 小时的音频。该数据集包含一组分为不同类别的环境声音剪辑。使用 Gammatone 滤波器组处理声音,并将其分割成 8 个时间步长的扩展频谱缓冲区,每个缓冲区有 100 个频谱滤波器。

*from keras.models import Model
from keras.layers import Input, LSTM, RepeatVectordef prepare_listener(timesteps,
                     input_dim,
                     latent_dim,
                     optimizer_type,
                     loss_type):
    *"""Prepares Seq2Seq autoencoder model

        Args:* ***:param*** *timesteps: The number of timesteps in sequence* ***:param*** *input_dim: The dimensions of the input* ***:param*** *latent_dim: The latent dimensionality of LSTM* ***:param*** *optimizer_type: The type of optimizer to use* ***:param*** *loss_type: The type of loss to use

        Returns:
            Autoencoder model, Encoder model
    """* inputs = Input(shape=(timesteps, input_dim)) encoded = LSTM(int(input_dim / 2), 
                   activation="relu", 
                   return_sequences=True)(inputs) encoded = LSTM(latent_dim, 
                   activation="relu", 
                   return_sequences=False)(encoded) decoded = RepeatVector(timesteps)(encoded) decoded = LSTM(int(input_dim / 2), 
                   activation="relu", 
                   return_sequences=True)(decoded) decoded = LSTM(input_dim, 
                   return_sequences=True)(decoded)

    autoencoder = Model(inputs, decoded)
    encoder = Model(inputs, encoded)

    autoencoder.compile(optimizer=optimizer_type, 
                        loss=loss_type,  
                        metrics=['acc'])

    return autoencoder, encoder*

对于我的数据,这段代码生成了下面的网络架构:

在 NVIDIA GTX 1070 GPU 上使用均方误差Adagrad 优化对这个监听器网络进行了 50 个时期的训练,达到了 42%的重建精度。训练花了一段时间,所以我很早就停止了,尽管进度似乎还没有停滞。我非常有兴趣看到这样一个具有更大数据集和更多计算能力的模型的性能。

这里当然有改进的空间,但是下面的图像显示了序列的粗略结构是在将输入压缩了 3.2 倍之后捕获的。

Some examples of original data and predictions by the autoencoder to illustrate reconstruction fidelity.

这是我关于神经网络音频处理系列文章的第二部分。在最后一篇文章中,我们将把这些概念用于创建一个分析音频嵌入的网络。

如果你喜欢这篇文章,请随时关注并留下你的掌声。

参考

[1] J. J. Eggermont,“在声音和感知之间:回顾对神经代码的探索。,"听到。《研究报告》,第 157 卷,第 1-2 期,第 1-42 页,2001 年 7 月。

[2] C. Alain、D. L. Woods 和 R. T. Knight,“人类听觉感觉记忆的分布式皮层网络”,《大脑研究》,第 812 卷,第 1-2 期,第 23-37 页,1998 年 11 月。

[3] A .温菲尔德,《工作记忆和认知资源模型的进化》,耳听。,第 37 卷,第 35S–43S 页,2016 年。

[4] “在嵌入式 C 中实现循环/环形缓冲区”,Embedjournal.com,2014。【在线】。可用:https://embed journal . com/implementing-circular-buffer-embedded-c/。

[5] A .范登奥尔德等人,“wave net:原始音频的生成模型。”

[6] Y.-A. Chung、C.-C. Wu、C.-H. Shen、H.-Y. Lee 和 L.-S. Lee,“音频词 2Vec:使用序列到序列自动编码器的音频段表示的无监督学习”,国际语音通信协会年会论文集,2016 年,第 765-769 页。

[7] F. Chollet,《Keras 中序列对序列学习的十分钟介绍》,Blog.keras.io,2018。【在线】。可用:https://blog . keras . io/a-ten-minute-introduction-to-sequence-to-sequence-learning-in-keras . html

人文专业毕业生应该考虑数据科学

原文:https://towardsdatascience.com/humanities-graduates-should-consider-data-science-d9fc78735b0c?source=collection_archive---------2-----------------------

我的职业轨迹有些不寻常。早在 2009 年,我本科毕业,获得了古典语言学位,不久后又获得了同一领域的硕士学位,之后继续攻读博士学位。和大多数人文学科的研究生一样,我的计划是在大学里研究和教授我的专业领域。

但是我没有完成。相反,我进入了工业界,在过去的五年里,我逐渐占据了更多的定量职位,从研究分析师开始,最近开始担任数据科学家的角色。虽然从学术界到数据科学的转变对于 STEM 博士来说相当普遍,但对于具有人文背景的毕业生来说,这种情况要难得多。尽管如此,我怀疑我这种转变的动机,以及使之成为可能的技能,事实上是许多人文学科研究生所共有的。这篇文章旨在帮助任何有兴趣走类似道路的人。

为什么选择数据科学

在我攻读博士学位的第一年,我开始质疑我的职业选择,在很大程度上,我的担忧可能是所有领域的研究生的典型问题:我担心找学术职位的难度,担心毕业后我是否能住在我想住的地方,担心我的研究是否会被认真对待。

但是除了这些实际问题,我也开始思考人文学科对待研究的方式,以及它的认识论基础的有效性。像学术界的许多人一样,最初吸引我从事研究的是产生知识的前景,但在我学术生涯的几年中,人文学科提供的工具集开始让我觉得不足以完成这一目标。从我当时的观点来看,我的研究过程是基于批判性阅读、反思和写作,在产生独特而有趣的视角方面是有效的,但在创造关于世界的新知识方面却不是。

对于有这种担忧的人来说,有些自然的是,我开始寻找其他可以创造知识的框架,并很快被科学的定量方法所吸引,因为它们提供了一种客观性,这是我的研究中一直缺乏的。不久之后,我被基于证据的研究和可证伪假说的想法所说服,但我也怀疑人文学科的博士学位并不是探索这类方法的最佳场所,所以我将工业视为一个成长和锻炼我的定量研究技能的地方。

数据科学只是研究

在接下来的几年里,我学习了定量研究的专用工具:应用统计学、假设检验、编码和分布式计算。我喜欢技术主题,并且在我的各种角色中找到每一个深入研究它们的借口。但是,通常情况下,我发现自己使用的最适用和最重要的技能是我在人文学科研究生时学到的。阐明研究问题,交流假设,解决研究人员的主观性和证据的不确定性问题——这些是我作为一名行业研究人员面临的最困难的挑战。

的确,我需要了解统计学,以及如何编写代码来有效地履行这些职责,但是这些知识是已知的。事实证明,伟大的数据科学家和普通的数据科学家之间的区别在于研究人员处理同样的不确定性的能力,这种不确定性最初曾驱使我从人文学科转向定量研究。换句话说,科学方法论和人文学科有着同样的认识论问题——他们只是用不同的工具来解决这些问题。

一些实用的建议

我的经历让我相信,对于一名行业数据科学家来说,研究生人文学科的工作实际上是最有用的背景之一。虽然经常有很多人关注数据科学家是统计或编码方面的专家,但这些工具只是达到目的的一种手段——对于进行伟大的数据科学来说,它们是必要的,但还不够。如果你是一名人文学科的研究生,并且对数据感兴趣,我会对你在这个领域取得成功的能力充满信心,因为你的技术水平不高。具体来说,作为人文学科研究生的经历使你成为以下领域的专家:

  1. 深入主题,自学任何东西
  2. 陈述研究问题,并用证据支持你的答案
  3. 传达你的方法的限制和假设

在我看来,这些宽泛的研究技能比任何特定定量方法的细节知识更有价值(也更稀有)。重要的是,第一点意味着人文学科的研究人员可以根据需要随时学习任何特定的方法论。也就是说,从人文科学成功过渡到数据科学需要一些基础知识。

首要任务是建立概率统计知识。把这些工具想象成文学或社会政治理论的科学等价物:它们是抽象的方法,你应用于一个特定的领域,努力回答一个特定的问题。

我不喜欢大多数新数据科学家在学习统计学时通常采取的漫无目的的方法。经常有一个错误的焦点放在学习非常特殊的模型或技术上,因此浪费了大量的时间来努力理解高度专业化的主题,同时慢慢地吸收更基本的想法。相反,我会把我所有的精力放在理解概念上,这些概念使得统计数据对那些试图证明或否定他们想法的研究者来说是强有力的。仔细阅读 p 值频率统计贝叶斯推断先验,理解这些如何应用到你的研究中。买一本书或者上一堂关于这些主题的基础课,但是不断地将你学到的东西和实际研究联系起来。

其次,获得编写代码(语言的典型选择是 PythonR ,以及 SQL )和可视化数据的基本知识。把这些看作是你进行研究所需的实用工具——在人文学科中,这就像学习一门外语或者测定一块陶器的年代一样。至于那些技巧,我认为最好通过在日常工作中使用它们来学习,而不是试图通过书本或课堂来建立一个全面的知识。从基础的在线课程开始,然后通过实践应用来提高。

真的,就是这样。在这两个领域打好基础,你就有 90%的机会成为功能数据科学家,剩下的就是边干边学了。实际上,我认为一个雄心勃勃的人文学科研究生可以在 3-6 个月内建立必要的统计和技术知识,从那里开始,问题只是找到一个可以让你继续学习的职位。我有一些资源可以让你开始另一个中型岗位这里

如果你对这些感兴趣,并且有具体的问题,请给我留言。我期待着看到更多从事数据工作的人文学科同事。

大多数人都会犯的错误

原文:https://towardsdatascience.com/humans-are-bad-at-probability-834980e719a3?source=collection_archive---------3-----------------------

在 11 月的第一周,美国总统大选之前,你认为克林顿获胜的可能性有多大?

在一个标准轮盘上,球落在红点上的几率是多少?

在俄亥俄州五月的任何一天,下雪的可能性有多大?

众所周知,概率思维很难。

如果你和大多数人一样(包括我自己),你对上面三个问题的回答可能分别接近 100%、50%和 0%。然而,考虑到美国第 45 任总统、轮盘赌上绿点的存在以及俄亥俄州在 5 月份多次降雪的事实,我们发现我们上面的“肯定会发生”、“抛硬币”和“不会发生”的预测不太准确。

你在这里并不孤单。

人类是如何思考的:

阿曼达·考克斯(Amanda Cox),《纽约时报》的编辑(我个人的数据可视化英雄),在我读研究生的时候,在俄亥俄州做了一次演讲。她提到人们不擅长概率性思维。特别是,她提到人类真的只考虑由 0、50 和 100%组成的概率度量

Illustration of Amanda Cox’s description of the “human probability measure.” (Made using TikZ LaTeX package.)

当考克斯说人类是这样思考的时候,她的意思是我们通常把接近 50%的概率解释为 50%的可能性。例如,如果有人听说一名 NBA 球员的罚球命中率为 60%,他/她可能会说该球员投篮命中的可能性与投篮不中的可能性差不多。如上图所示,中间有黄色箭头;任何接近 50%的东西都会被简化为 50%。

任何显著大于 50%的可能性,我们都认为是确定的事情,称之为 100%可能。一个股票新手看到一份报告说谷歌的股票有 90%的可能会上涨,他可能会把大量的钱投入到这只股票中,认为他/她在这笔交易中不会有任何损失。这用顶部向上的绿色箭头表示;我们将所有远高于 50%的概率映射为“确定”或“几乎确定”。

任何远低于 50%的可能性,我们都认为它永远不会发生,所以我们认为特定事件发生的概率是 0%。这在上图中用红色箭头表示;我们经常认为这些事件“几乎不可能,不值得考虑。”

这听起来似乎过于简单,但它惊人地成立。例如,想想下雨的可能性:

  • 如果你查看天气应用程序,发现明天下雨的可能性为 80%,你可能会认为肯定会下雨,所以你一定要带上雨伞。
  • 如果应用程序告诉你下雨的几率是 40%,你就是在扔硬币决定下雨。我们这些厌恶风险的人会抢伞;你们中的那些人…嗯,像我一样,不会。
  • 如果你读到下雨的可能性是 10%,你认为不会下雨,所以你甚至懒得在明天早上的清单上加上“雨伞”。

人类无时无刻不在评估事物。即使作为一名数据科学家,我也会进行四舍五入和估算,最终得到非常不精确的结果……所以这很正常,对吗?

嗯,是的。当我们从概率转向实际预测时,问题就出现了。

如果你的天气预报员说有 90%的可能性至少会有一英尺厚的雪,当只有一场小雪降临你的街道时,你可能会感到沮丧。我们将这 90%的预测视为必然,然后当这些预测变成我们认为几乎不可能的方式时,我们会感到委屈。

内特·西尔弗对概率的辩护

内特·西尔弗上周在推特上颇有争议地纠正了罗恩·福涅尔关于概率本质的观点。

Nate Silver vs. Ron Fournier Tweetstorm, April 23, 2017.

为了让你了解最新情况,Silver 发布了一篇关于詹姆斯·科米对 2016 年美国总统选举的影响的文章。Fournier 对此提出异议,认为 FiveThirtyEight 预测了克林顿的胜利,因此做出了“不正确”的预测。西尔弗反复回应说,福涅尔不是在进行概率性思考。

许多美国人对这次选举措手不及。根据纽约时报的结果总统预测,所有预测都相当确定希拉里将赢得选举。(补充说明:这一页上的可视化效果令人难以置信,我强烈建议看一看。)

New York Times’ The Upshot 2016 Presidential Predictions, November 8, 2016.

专家不是特别受欢迎——尤其是当他们的预测出错的时候。他们使得克林顿的胜利似乎不可避免。所以我们很容易挑他们的毛病,争辩说他们“错了”我们也有账单要付,有工作要做;我们怎样才能解析这些预测呢?

人类应该如何思考:

有两种解释事件发生概率的适当方法,这两种方法都是有效的:

  • 从长远来看,这种事件发生的频率有多高?
  • 你认为这件事会发生到什么程度?

第一种方法(称为频率主义方法)将通过说“如果选举一再发生,我们预计克林顿将赢得每 100 次选举中的 85 次”,或者大约每 6 次中的 5 次,来解读 NYT 的克林顿获胜概率。

第二种方法(称为贝叶斯方法)将通过说“纽约时报有 85%的把握克林顿将赢得选举”来解释 NYT 对克林顿获胜的概率这种方法更加主观,引起了贝叶斯反对者的愤怒。然而,这种方法并不依赖于 2016 年选举会像频繁主义者方法要求的那样一遍又一遍发生的想法。

虽然有大量关于解释概率的文献(“贝叶斯”和“频率主义者”这两个术语可能会引发数据科学爱好者和统计学课程幸存者的一些记忆),但你会注意到,这两种解释都没有说“特朗普不可能获胜”。

这里最重要的一点是,从概率跳到预测时要小心谨慎。据说 85%确定的事情并不意味着它是“确定的事情”

问问克林顿国务卿就知道了。

我要感谢我的朋友兼同事约瑟夫·尼尔森的编辑。你应该在媒介上认出他;他的帖子比我的好。

有人类在身边很方便

原文:https://towardsdatascience.com/humans-are-handy-to-have-around-4e6b7a7acff7?source=collection_archive---------4-----------------------

作为影子机器人公司的首席技术架构师,我一直在寻找令人兴奋的方法,让非机器人专家更容易抓取和操纵。示范教学是解决这一问题的众多方法之一。

Teaching by demonstration: folding paper. Research from the CITEC group at Bielefeld University.

这个想法很简单,你向你的机器人展示如何做某事——在我的例子中——如何抓住一个给定的物体。机器人将从演示中学习,完善它所展示的内容,直到它“工作”良好。

就我的目的而言,梦想的目标是展示一个足够好的抓取:手动塑造机器人手围绕物体,然后让机器人自己尝试几次,直到抓取真正稳定。这通常被称为一次性示范学习。

在这个故事中,我将集中在一个非常简单的方法来解决这个问题,使用贝叶斯优化。

抓取被认为是一种数学功能

贝叶斯优化是你工具箱中一个非常有用的工具,可以用来优化黑盒函数。有多种方法可以考虑抓取物体的问题。其中之一是将其视为一个函数优化问题:给定我的输入——例如,我每个关节的关节角度——我如何才能获得最高的输出——即最稳定的抓力。

Considering the grasp problem as a black box optimisation problem

客观地看,将抓取视为一个优化问题就像试图寻找风景中的最高峰一样。在抓取时,我经常寻找一个足够高且相当宽的峰,而不是一个又高又窄的峰。如果我的峰值太窄,那么我将很难准确地处于那个配置中,所有的不确定性加起来甚至是最先进的机器人。

In grasping, I’m often looking for peak #2 instead of peak #1. It is much easier to reach that peak in an uncertain world.

粗暴的方法

在我的抓取案例中,让我们记住我想找到最高的——也是最宽的——山峰,但是我不知道风景是什么样子。正如你在下面看到的,估算这一景观的一个非常简单的方法是在空间的任何地方取样。这意味着用关节目标的每一种可能的组合来抓取物体,并获得相关的抓取鲁棒性。即使它能很好地工作,但它肯定不是最佳方法。

Brute force sampling an unknown landscape. From left to right: my black box landscape / Brute sampling the landscape in a grid to estimate my landscape / The actual landscape with the stable region we are looking for at the top left.

在我当前的问题中,我也可以利用人类所展示的理解能力。以此为起点,我可以缩小搜索范围。如下图所示,我将只在附近寻找。如果我仍然在考虑一个蛮力的方法,这将意味着我需要少得多的样本来猜测我的风景的形状。

Restricting my search space.

更加智能地采样

尽管上面描述的搜索区域在我的图上看起来很小,但你必须记住我是在一个高维空间中:我有很多关节。所以探索那个地区会花很多时间。我们需要的是一种更好的方式来采样我的空间。

贝叶斯抽样是一种经过充分研究的方法,它可以最大限度地收集每次取样的信息。主要的想法是收集尽可能多的关于峰值的信息,同时不要花太多时间在抓地力不好的地方取样。

在这个方法中,我还可以调整在探索开发上花费了多少努力。更多地关注开发——正如你在左图中看到的那样——将在峰值周围收集更多的数据。因此,这留下了更多的不确定性:我可能会错过一些峰值,但我最稳定的抓地力的联合目标将非常精确。如果我转而关注于探索——右边的图表——我将在我的空间周围收集更多的数据,减少我在任何地方的不确定性。但是我最稳定的把握的联合目标将会不那么精确。

Exploitation — on the right — vs. exploration — on the left. Red dots are samples taken, blue line is the actual function, green line is the approximation I built, blue surfaces represent the uncertainty. Source: bayesian-optimization library.

完善模拟中的把握

在模拟中运行优化非常类似于我用来收集数据集以预测抓取质量的过程。在模拟中,我用贝叶斯过程给我们的联合目标抓住我的对象,然后举起对象,并记录一个客观的抓住质量。这种抓握质量与手掌和物体之间距离的变化成比例。这是一个非常简单的想法:如果我移动手,并且抓握稳定,则物体随之移动!

对于贝叶斯优化的每一次迭代,我都使用新的联合目标进行采样。我的黑盒函数的输出是从摇动物体测量的抓握质量。这给了我一个新的黑盒函数值,减少了给定区域的不确定性!

在这个过程的最后,我们有了比最初更强有力的把握。我在 Shadow 的同事甚至在真实的机器人上测试了抓地力,正如你在下面看到的那样,它非常稳定。

Testing the refined grasp on the real robot — an early prototype of our Smart Grasping System.

如果你想看看用于此的代码,你可以在 github 上找到

最后的话

如果我可以很容易地在模拟中导入对象,这个过程会非常好。在模拟层面上还有很多工作要做,才能有一个更接近真实机器人的模拟。这是一个很大的挑战,尤其是当你处理抓取和操作问题的时候。

这种优化也可以在真实的机器人上运行。为此,我需要能够在真实的机器人上复制我的客观抓握质量,这不是一个简单的任务。一旦抓地力预测算法工作良好,虽然…

利用人类的智慧来帮助机器人做得更好是推动事情向前发展的一个很好的方式。这项工作的大部分是由在 Shadow 实习的帕万完成的。谢谢帕万!

随时连接 上推特

可微分神经计算机(DNCs)——自然文章思考

原文:https://towardsdatascience.com/humphrey-sheil-differentiable-neural-computers-dncs-nature-article-thoughts-bd22939c2d97?source=collection_archive---------5-----------------------

2016 年 10 月 17 日

当我们将人工神经网络与冯·诺依曼 CPU 架构相比较时,人工神经网络(ann)中工作记忆的添加是一个明显的升级,并且是去年 NIPS 的 RAM(推理、注意力、记忆)研讨会中出现的一个(挤满了人)。显而易见和建筑然而是两回事..

谷歌 Deepmind 最近发表的关于可分化神经计算机(DNCs)的论文代表了在人工神经网络中添加工作记忆的旅程中又迈出了重要的一步,因此值得更深入地研究一下。

这是一个变化的时代

为了向新晋的诺奖得主鲍勃·迪伦致敬,我们用他 1964 年的经典书名来引起人们对目前神经网络格局重构的惊人变化的关注。

Movidius 被英特尔收购——他们的口号“物联网视觉传感”为他们的重点提供了线索——他们的 VPU 或视觉处理单元可以执行 TensorFlow 或 Caffe 神经网络模型。

英特尔自己正在为新的 x86 指令准备 Linux 内核,致力于在 CPU 而不是 GPU 上运行神经网络(英特尔在这一领域已经落后英伟达很长时间了)。

就采用和公共性能而言,英伟达仍然是明确的硬件领导者——他们在深度学习上下了很大的赌注,在今年的 GTC 2016 上,它是大会的基石——从 DGX-1CUDA 8/cud nn 5 . x版本。

最后,我们知道 Google 有他们自己的 TPU(张量处理单元),但不太了解它们,也不知道它们如何达到 GPU 或 CPU。

简而言之,硬件正在变形,以更有效地运行更大的神经网络,并使用更少的功率。现在每个主要的软件公司都与学术机构有联系,并积极致力于将深度学习/神经计算应用到他们的平台和产品中。

这种水平的硬件和软件活动在神经计算领域是前所未有的,而且没有减弱的迹象。那么,民主党全国委员会的文件如何在所有这些活动中发挥作用,如果有的话?

可微分神经计算机

那么,什么是 DNC 呢?分解这张纸,我们得到以下要点:

  • 本质上,DNC“只是”一个递归神经网络(RNN)。
  • 然而,该 RNN 被允许读取/写入/更新存储器(M)中的位置——RNN 存储大小为 W 的数据的向量或张量,其中 M 具有大小为 W 的 N 行,因此 M = N*W
  • DNC 使用可区分注意力来决定从哪里读取/写入/更新内存中的现有行。这是一个关键点,因为这现在使得诸如随机梯度下降(SGD)的充分理解的学习算法能够用于训练 DNC。
  • 存储体 M 是关联的——实现使用余弦相似性,从而支持部分匹配和精确匹配。
  • 还有另一个数据结构(名为 L ),它独立于内存 m。L 用于通过记住内存读取和写入的顺序来提供临时上下文和链接。因此“L”只是一个链表,它允许 DNC 记住它向“M”读取或写入信息的顺序。

最后,我发现在论文中提到认知计算/生物合理性很有趣(在这个领域并不常见——20 世纪 90 年代连接主义与计算主义辩论的遗留物——多次提到 DNC 和海马体之间的相似性,或者突触如何编码时间上下文和链接。

下图摘自 Deepmind 的博客文章,清楚地显示了 RNN、读写头、N*W 内存(M)和编码 M,l 中的时间关联的链表

韦斯顿等人的记忆网络呢?

脸书的韦斯顿等人也一直在这一领域努力工作。下图来自他们 2016 年 6 月的 Arxiv 论文,这篇论文是追溯到 2014 年的一系列内存网络工作的最新成果,或许内存组件受到了早期关于 WSABIE 的工作的启发/激励。

Nature 论文更好地阐述了他们解决方案的通用性(涵盖文档分析和理解、对话、图形规划等。),但这并不一定意味着的方法更好。

影响和相关性

在我看来,DNCs / RAM 代表了自 LSTM 以来循环架构的最大进步。内存的增加,加上定义明确的机制来区分并训练它,显然提高了 rnn 执行更复杂任务的能力,如规划,正如关于 bAbl 数据集或伦敦地铁任务的论文所证明的那样。

业务应用程序可以充分利用 DNC 和类似的架构。规划或更好地理解大型文档的能力对于决策支持系统、数据分析、项目管理和信息检索具有重大意义。不难想象,比如 ElasticSearch 和 Solr 的 DNC 插件,或者微软 Project Server 的 DNC 版。

将软件支持与对张量中心运算的新兴本机 CPU 指令集支持相结合,再加上正在进行的 GPU 改进和 TPUs,神经计算的未来将越来越光明。

未来工作?

wino grad 的 SHRDLU 被广泛认为是人工智能的一个高点,于 1972 年达到,自那以来没有实质性的改进或复制(梁,2015 幻灯片 100–105)。《自然》杂志文章第三页引用的迷你 SHRDLU 方块拼图实验是否指向 Deepmind 的下一个实质性研究领域——提高 1972 年以来 SHRDLU 的性能?

最初发表于humphreysheil.com

飓风佛罗伦萨——建立一个简单的风暴路径预测模型

原文:https://towardsdatascience.com/hurricane-florence-building-a-simple-storm-track-prediction-model-1e1c404eb045?source=collection_archive---------10-----------------------

Hurricane Florence (2018) — As seen from International Space Station (Credit: NASA)

飓风佛罗伦萨2018 大西洋飓风季的第一个主要飓风。8 月 30 日,从佛得角附近的源头开始,佛罗伦萨行进了近 4100 英里,于美国东部时间 9 月 14 日上午 7 点 15 分左右在北卡罗来纳州莱特斯维尔海滩附近登陆。这种缓慢移动的风暴最初被预测为 4 级飓风,阵风 140 英里/小时,然后以 1 级风暴的形式登陆。尽管减弱为 1 级风暴,佛罗伦萨仍然有足够的风速造成重大的生命损失,家庭和社区的破坏,财产损失,以及北卡罗来纳州沿海的其他经济损失。根据穆迪分析,佛罗伦萨的初步损失估计在 170-220 亿美元之间。由于佛罗伦萨历史上的降雨和洪水的影响仍在继续,预计佛罗伦萨的成本将大幅上调是合理的。

自 8 月 30 日成立以来,国家飓风中心 (NHC)一直在跟踪佛罗伦萨的路径,并发布关于飓风当前和预计路径的报告和建议。准确预测飓风的路径使我们能够制定减灾战略,最大限度地减少飓风的经济影响,拯救生命。NHC 保留了一份不同复杂程度和结构的预测模型列表,可以用来预测飓风的路径。

在这项研究中,我们将使用大西洋飓风数据库( HURDAT2 )建立一个简单的风暴路径预测模型。然后,我们将使用开发的模型对飓风佛罗伦萨路径进行集合预测,并将模型结果与佛罗伦萨经过的实际路径进行比较。在我们深入研究模型之前,让我们首先加载数据并进行一些探索性的数据分析。

Snapshot of Processed HURDAT Dataset

探索性数据分析

低频率-高强度风暴:Hurd at 数据集有 1792 个命名风暴。按类别绘制风暴计数显示频率分布遵循指数/负二项式分布。虽然有 1485 个 1 级风暴,但只有四个风暴的风速达到 5 级(>155 英里/小时)。

Count of Storms by Category

季节性:北大西洋季节通常发生在 6 月 1 日至 11 月 30 日之间。绘制飓风的季节分布图显示,9 月是最活跃的月份,在某些情况下,飓风季节早在 1 月就开始了。

Count of Storms by Month

周期性:平均每个季节有近 10 次风暴发生,2005 年是最活跃的季节,有 28 次风暴。数据显示,在过去的几十年里,飓风的频率和强度都有明显的增加。气候变化是我们在 2017 年目睹的飓风严重性增加和聚集效应的原因吗?绘制 10 年和 25 年的移动平均线显示了几十年的振荡。

Count & Moving Averages on Storm Frequency by Year

风暴成因:影响热带风暴发展的主要因素有:(1)温暖的海表温度,(2)大气不稳定,(3)高湿度,(4) 科里奥利力,(5)低垂直风切变,(6)预存扰动。从 HURDAT 数据集推断,大多数风暴起源于大西洋温暖的水域和 10 度以上的纬度。赤道纬度 10 度以内的地区不会受到科里奥利力的影响,科里奥利力是热带气旋形成的一个重要因素。

历史风暴轨迹:在 HURDAT 数据集中绘制历史风暴轨迹显示了飓风在热带地区生成后向西传播。北大西洋飓风的顺时针旋转和全球信风使飓风沿着副热带高压脊向西北方向移动。

登陆风暴:在大西洋盆地形成的风暴中,只有三分之一真正登陆。有时,飓风可以多次登陆,这取决于它们可能遵循的不可预测的轨迹(环形和发夹弯)。例如,卡特里娜飓风(AL122005)在佛罗里达州的哈兰代尔海滩首次登陆时为 1 级风暴,在密西西比州的格尔夫波特第二次登陆时为 3 级飓风。

Path of Storms Named “Katrina” in the HURDAT dataset

风速与气压:风速和气压是 HURDAT 数据库中提供的两个附加属性。等值线图显示风速和气压呈反向相关。

Wind Speed (left) and Pressure (right) Contour Maps

马尔可夫转移模型

构建马尔可夫转移模型有五个步骤:

  1. 创建覆盖建模领域的网格网络
  2. 将历史风暴轨迹覆盖在网格上,并计算转移概率矩阵
  3. 给定起源点,使用步骤 2 中开发的转移概率矩阵,预测风暴的下一个位置
  4. 使用步骤 3 中的预测位置来预测下一时间步的位置
  5. 重复步骤 4,重复预定的次数

2-D Histogram of Historical Location of Storms Overlaid on Computation Grid

验证模型

在使用该模型生成佛罗伦萨飓风的风暴轨迹之前,让我们验证一下安德鲁飓风(1992 年)的模型。下图显示了 Andrew 的实际路径(黑线),以及马尔可夫转移模型生成的路径集合(大小=10)。模拟轨迹形成的包络线与飓风安德鲁经过的实际路径吻合得很好。

Historical & Simulated Storm Tracks for Andrew (1992)

预测飓风佛罗伦萨的路径

大多数起源于佛得角的风暴向北弯曲,错过了美国。飓风佛罗伦萨(路径如下所示)采取了不同寻常的轨迹,没有向北弯曲,而是缓慢向西移动,在北卡罗来纳州登陆。

Actual Path and Wind Speed of Hurricane Florence (2018)

这项研究中开发的马尔可夫转移模型被用来预测佛罗伦萨从其起源点可能采取的合理路径。运行了十个模拟的集合,结果轨迹显示在下图中。第八次模拟的结果相当好地模拟了佛罗伦萨的路径和登陆位置。总之,马尔可夫转移模型是一种简单(有趣)的方法,可以用最少的数据(仅仅是起源点)来预测飓风的路径。

Historical & Simulated Storm Tracks for Florence (2018)

简单越好?—奥卡姆剃刀

这当然是一个非常简单的路径预测模型。但是简单总是更好吗?为了回答这个问题,为了提醒 2018 年大西洋飓风季节,我将使用这个简单的模型来预测任何新飓风的路径,并将结果与复杂的全球环流模型公布的轨迹进行比较。

要了解我们如何使用深度学习进行风暴路径预测,请参见我最新的博客:

[## 使用深度学习的飓风路径预测

每年 6 月 1 日到 11 月 30 日之间的时间窗标志着北大西洋飓风季节。在此期间…

medium.com](https://medium.com/@kap923/hurricane-path-prediction-using-deep-learning-2f9fbb390f18)

哈维飓风保险技术案例研究;视觉智能正在改变索赔响应时间。

原文:https://towardsdatascience.com/hurricane-harvey-insurtech-case-study-visual-intelligence-is-transforming-claim-response-times-3275042fbd8d?source=collection_archive---------6-----------------------

Hurricane Harvey as seen from the International Space Station

过去几周,前所未有的风暴袭击了美国和加勒比海地区,造成的损失估计高达数百亿美元。

根据美国国家海洋和大气协会(NOAA)的数据,自 1980 年以来,仅美国就经历了 212 次自然灾害,总损失达 1.2 万亿美元。

作为一名对金融科技感兴趣的风险投资者,我看到相当多的创新型保险科技初创企业希望成为保险业的下一个大事件。这些企业几乎没有一家专注于改善索赔管理。这是为什么呢?

或许索赔被认为是保险业最不“性感”的一面,如果你愿意的话,这是一种必要的邪恶。优秀的保险公司知道索赔经历是保险最重要的部分之一。毕竟,保险是在发生事故时赔偿损失的承诺。

自然灾害是残酷的。它们使人们变得脆弱和暴露,保险公司的快速解决方案对客户体验至关重要,有助于留住客户,还能节省保险公司的时间和资金。

说起来容易,但在哈维和伊尔玛飓风这样的大规模事件发生后,对索赔做出动态响应可不是一件容易的事。在相当长的一段时间内,人们通常不可能进入这些地区,此时风暴潮已经平息,索赔可能更难评估。

一家为保险公司积极应对这一挑战的公司是 Geospatial Insight 。venture one最近宣布对他们进行增长型股权投资,我和他们在英国的团队在一起。他们刚刚提供了关于飓风哈维的令人难以置信的详细视觉情报,使保险公司和他们的企业客户能够了解基层的情况,并对索赔迅速做出反应。

自然灾害发生后,保险公司可以通过采用视觉智能服务来应对三大挑战:

1)事件可能导致的大致总索赔额。

2)受事件影响的区域的准确地图,以防止欺诈性索赔。

3)索赔的近因与事件直接相关。

围绕机器学习、大数据和无人机等先进技术的可能性有很多炒作,但我很少看到它们如何结合起来带来好处的切实例子,所以这里有一个现实生活中的例子。

哈维飓风案例研究

8 月 25 日,4 级飓风哈维在德克萨斯州洛克波特附近登陆。

哈维造成了灾难性的洪水,在一些地区降雨量超过 50 英寸(美国热带气旋的记录)。哈维在 72 小时内覆盖了 20,000 多平方英里,转移了 30,000 人。

情境分析

第一步是对受灾地区进行初步评估,并对预期的保险客户需求进行快速审查。大休斯敦人口密集的住宅和商业区被设定。

大数据采集、处理&分析

尽管哈维在周五登陆,但在接下来的几天里,暴雨天气仍在持续。据估计,截至周三 30 日,令人难以置信的 24.5 万亿加仑的雨水从墨西哥湾倾泻到休斯顿和德克萨斯州南部。

为了获得尽可能全面的了解,对各种数据集进行了整理,包括地形数据、卫星图像、来自社交媒体的无人机镜头以及独立委托的轻型飞机和专业高分辨率相机图像。

该团队使用从空中和社交网络收集的数据来校准用于生成哨兵足迹的阈值。然后,Geospatial Insight 使用专有算法将检测到的积水区域聚类为洪水淹没区域

为了了解哈维对住宅和商业建筑的可能影响,我们将多个数据集结合起来,以深入了解洪水的范围。下面的彩色编码图像显示了不同的数据源。

蓝色来自美国国家海洋和大气协会(NOAA)的图像和使用 Midas 倾斜相机系统进行的航空勘测。

红色的是哨兵 1 号雷达卫星,它可以穿透云层识别积水区域。

黄色的小口袋来自 Geospatial Insight 的社交媒体抓取工具,用于查找事件的照片和视频,然后可以对这些照片和视频进行映射,以根据视频证据构建范围。通常,该团队使用他们的全球许可无人机运营商网络,按照商定的 SLA 使用无人机绘制洪水地区的地图,然而,由于紧急服务使用该空域进行救援等,无人机在此期间被禁止在休斯顿上空飞行。

像下面的例子这样的镜头被识别出来,然后飞行路线和洪水范围被专业地绘制出来。

为什么洪水如此严重?

你可以清楚地看到休斯顿西部的两个大型蓝色水库,10 号州际公路北部的 Addicks 和南部的 Barker。它们旨在保护休斯顿免受洪水的侵袭,两个大坝都通向布法罗湾。水库周围都是公园和住宅区,到周一晚上,水位已经达到创纪录的水平,在阿迪克斯(北部)测得 105 英尺,在巴克(南部)测得 99 英尺。

当地官员希望通过在周二和周三缓慢释放阿迪克大坝和巴克大坝的水来防止溢出。然而,风暴潮是如此之大,工程师们不得不提前通过大坝闸门放水,否则可能会溢出并对房屋造成进一步破坏。周一早上早些时候,已经向家庭发出了疏散警告,然而,周日晚上决定释放压力,许多居民被困在由此产生的海浪中。

利用视觉智能加速索赔

为了提供快速处理保险索赔所需的情报,地理空间洞察团队需要首先理解大量的非结构化数据。

不仅是各种图像源,还有保险客户的客户信息和企业责任数据,如员工的家庭住址,以映射受影响的客户和员工。

这些数据被快速映射,多个图像源被应用为图层,以允许企业客户通过地理空间洞察专用客户门户访问和理解信息。

上图显示了用黄色标识的索赔位置点的客户端门户。

高分辨率卫星图像可能是一个很好的指标,但它们是自上而下的视图,因此很难准确了解财产的损坏程度。需要倾斜角度的图像来帮助在广阔的区域内对此进行量化,因此 Geospatial Insight 委托了一架配备 Midas 5 相机的轻型飞机来绘制受灾最严重地区的高分辨率图像。

下图展示了这款相机如何能够同时捕捉四个方向的倾斜角度(以及俯视图)。

利用这种技术,可以对大面积地区进行高分辨率成像,然后绘制成地图,提供东、西、南、东、西四个方向的倾斜图像,以便准确分析已确定的索赔地点。

凭借这种分辨率和大量数据,地理空间洞察团队可以识别洪水的证据,如房屋外的残留水、沉积物和废物,即使洪水已经排干。下图是一个展示家居用品被处理的例子。你可以清楚地看到,与那些被风暴潮毁坏的游泳池相比,凸起的游泳池仍然保持干净和蓝色。

灾后重建

可悲的是,休斯顿的许多居民似乎没有保险,面临着在没有任何形式的保险赔付的情况下重建他们的生活。对于那些有保障的人来说,快速获得资金将会有所不同。

通过采用上述部署的技术,保险公司可以在帮助居民、企业和社区尽快恢复元气方面发挥重要作用。

— — — — — — — —

关于公司的更多信息,你可以访问www.geospatial-insight.com或者给我发消息,我很乐意为你介绍这个团队。

混合模糊名称匹配

原文:https://towardsdatascience.com/hybrid-fuzzy-name-matching-52a4ec8b749c?source=collection_archive---------8-----------------------

介绍

我的工作场所使用大规模数据库,其中包含关于人的数据。对于数据库中的每个人,我们都有一个唯一的标识符,它由人的名字、姓氏和邮政编码组成。我们在数据库中保存了大约 500 万人,如果人名有一点变化,基本上可能会有重复。例如,罗布·罗森和罗伯特·罗森(邮政编码相同)将被视为两个不同的人。我想指出的是,如果我们为同一个人获得额外的时间,我们只需更新记录的时间戳,因此没有必要进行这种重复数据删除。此外,我还要感谢我的同事 Jonathan Harel,他在这个项目的研究中帮助了我。

问题是

我用不同的方法清理数据库。我将描述最有趣的一个,它在这种情况下对数据库进行了很好的重复数据消除。这里我们只尝试匹配两个拥有相同邮政编码的标识符。对于数据库的很大一部分,我们保存性别数据和年龄数据,但是这些信息经常丢失。所以我基本上只剩下真实的名字了。那么我怎么确定两个名字是同一个人的呢?

救援用的机器学习

这说起来容易做起来难。这里可以用来输入到机器学习模型中的特征到底是什么?

有些功能相对直观,有些则需要彻底研究。起初,我显然是在考虑某种字符串相似性(针对拼写错误等)。),也可能是我有名字和名字的昵称的情况(如 Ben/Benjamin)。我进行了数据探索,看看我是否能加强我的想法或找到名字相似性的其他想法。这是一个好的开始,但我需要更多。经过大量的研究,我找到了下面这些名字相似的例子:

Name Similarities

特征抽出

假设我有两个邮政编码相同的人,我想给他们的“接近”程度打分。如前所述,在某些情况下,我有年龄和/或性别的数据,但通常情况并非如此。当然,这也作为特征输入到模型中。所以对于这些想法中的每一个,我需要提取它们相应的特征(因此我选择了这个名字:“混合”):

  • 对于昵称,我收集了多个名字和昵称的大型列表,然后用这些数据创建了一个 Python 字典。给定两个名字,first_name1 和 first_name2,以及昵称字典,我构建了以下函数,该函数创建一个二元特征,如果一个人的名字是另一个人名字的昵称,则该特征标记为 1:
def is_nickname(first_name1, first_name2, nickname_dict):
    first_name1_dict_vals = nickname_dict.get(first_name1)
    first_name2_dict_vals = nickname_dict.get(first_name2)
    if first_name1_dict_vals:
        if first_name2 in first_name1_dict_vals:
            return 1
    if first_name2_dict_vals:
        if first_name1 in first_name2_dict_vals:
            return 1
    return 0
  • 想法 e.k. 也是基于脚本所做的测试的特性,以检查在某个比较中情况是否为真(或者“相对真实”,我们将在下面的代码中看到)。例如,以下代码检查两个全名的组成部分之间的相似性:
# Out of order components ('Diaz | Carlos Alfonzo', 'Carlos Alfonzo # | Diaz') / first_name_last_name_swap  ('jesse | jones', 'jones |  # jesse')full_name1_splits = re.split("\W+|_", full_name1)
full_name2_splits = re.split("\W+|_", full_name2)out_of_order_components_score = 
len(Counter(full_name2_splits) & Counter(full_name1_splits)) /           float(max(len(full_name1_splits), len(full_name2_splits)))
from pyjarowinkler.distance import get_jaro_distance
import editdistancejaro_score = get_jaro_distance(name1, name2)
levenshtein_distance_score = editdistance.eval(name1, name2)
  • 为了语音相似性,我最终确定了 NYSIIS双变音算法。这些算法背后的想法是,它们为英语单词创建一种编码。然后,我使用两种不同编码之间的字符串距离(这里特别是 Levenshtein 距离)。例如,双变音输出主要编码和第二编码。姓名 Catherine 和 Kathryn 的编码是这样的:

Double Metaphone Algorithm Example

  • 为了使用 NYSIIS 算法提取语音相似性特征,我使用了以下代码(在该算法中,每个给定的名字只有一种编码):
import editdistance
import fuzzynysiis_score = editdistance.eval(fuzzy.nysiis(name1), fuzzy.nysiis(name2))

有人有标签吗?

您现在可能已经在想:“这是一个分类问题吗?如果有,他从哪里有标注的数据?”

嗯,我不…实际上我自己给数据加了标签。我提取了匹配的案例(例如 Jennifer Williams/Jenny Williams;标记为 1),是“接近”匹配的情况(例如,唐·安德森/丹尼尔·安德森;标记为 0),并从数据中添加一个大的随机样本进行标记。“接近”匹配允许我建立一个健壮的模型,该模型可以很好地区分真实匹配和接近但实际上不匹配的匹配。这不是一件愉快的事,但它让这个项目变得可行:)

建立模型

我现在准备训练一个模型。当然,我已经将数据分割为一个训练(分割它也是为了超参数优化)和测试集。我最关心的是精确度。让我们回忆一下精度是什么:

Wikipedia

这样做的原因是,在两个实际上不是同一个人的人之间匹配比错过两个实际上是同一个人的人之间的匹配要糟糕得多。除内部使用外,我们拥有的数据用于向数据合作伙伴导出。因此,出于商业原因,我们倾向于尽可能减少误报。

我决定选择不需要对其功能进行任何缩放的模型,所以我主要尝试了 Random Forest、GBM 和 XGBoost。我还使用 sklearn 的 GridSearchCV 进行了超参数优化:

*import* numpy *as* np
*from* sklearn.ensemble *import* RandomForestClassifier
*from* sklearn.model_selection *import* GridSearchCV# Number of trees
n_estimators = [int(x) *for* x *in* np.linspace(start=5, stop=30, num=5)]
# Number of features to consider at every split
max_features = ['auto', 'sqrt']
# Maximum number of levels in tree
max_depth = [int(x) *for* x *in* np.linspace(3, 20, num=3)]
max_depth.append(None)
# Minimum number of samples required to split a node
min_samples_split = [2, 5, 10]
# Minimum number of samples required at each leaf node
min_samples_leaf = [1, 2, 4]
# Method of selecting samples for training each tree
bootstrap = [True, False]# Create the random grid
random_grid = {'n_estimators': n_estimators,
               'max_features': max_features,
               'max_depth': max_depth,
               'min_samples_split': min_samples_split,
               'min_samples_leaf': min_samples_leaf,
               'bootstrap': bootstrap}

grid_search = GridSearchCV(RandomForestClassifier(random_state=0), param_grid=random_grid, scoring='precision', n_jobs=-1, verbose=5)
grid_search.fit(train_features, y_train)

注意,您可以改变 GridSearchCV 来根据精度分数进行优化,从而改变“score”参数。

初步结果

在第一次运行优化的模型后,我在测试集上获得了 0.85 的精度分数。这很好,但我仍然希望在这里接近完美。由于我的模型可以输出一个概率,我试图找到提高精度的最佳阈值。由于召回大幅减少,这里有一个权衡。我可以把门槛降低很多,但最终的匹配数接近于零。

我决定分析我的模型出了什么问题,检查是否有什么东西联系了大多数或者所有的假阳性。我发现,在很多情况下,年龄的影响太大了(注意:数据是在过去几年中收集的,因此预计年龄不会完全相同),例如:

False-Positive Example

那我在这里能做什么?我告诉模特他犯了一个大忌。我该怎么做?就像在现实世界中一样,我会一次又一次地告诉模型那是错的。我拿了大量的案例,其中年龄相似,并且其中一个名字是相同的(就像上面看到的)。这个思路可以认为类似于主动学习的概念。

决赛成绩

这对模型产生了巨大的影响。我设法在测试集上提高到 0.99 的精度,同时保持 0.8 的召回率。

在整个数据库上运行时,该模型发现了大约 50 毫米的匹配项,对数据库进行了 10%的重复数据删除!我当然没有检查所有这些匹配,但我随机选择了几千个,发现这里的精度也是大约 0.99。以下是一些很酷的配对例子:

Matches Achieved

超参数在起作用!第一部分—激活功能

原文:https://towardsdatascience.com/hyper-parameters-in-action-a524bf5bf1c?source=collection_archive---------0-----------------------

Sigmoid activation function in action!

介绍

这是一系列帖子的第一篇,旨在以清晰简洁的方式直观地展示训练神经网络的一些基本活动部分:超参数。

动机

深度学习是关于超参数!也许这是一种夸张,但对不同超参数对训练深度神经网络的影响有一个良好的理解肯定会让你的生活更容易。

在研究深度学习时,你可能会发现大量关于正确设置网络超参数重要性的信息: 激活函数、权重初始化器、优化器、学习速率、小批量 ,以及网络架构本身,如 隐藏层数每层中单元数

所以,你学习所有的最佳实践,你建立你的网络,定义超参数(或者只是使用它的默认值),开始训练并监控你的模型的 损失指标 的进度。

也许实验没有你预期的那么顺利,所以你对它进行迭代调整网络,直到你找到对你的特定问题有用的一组值。

寻找更深层次的理解(无意双关!)

你有没有想过引擎盖下到底发生了什么?我做了,事实证明一些简单的实验可能会对这个问题有所帮助。

激活功能 为例,本帖题目。你我都知道,激活函数的作用是引入一个非线性,否则整个神经网络可以简单地被一个相应的 仿射变换 (即一个线性变换,比如旋转缩放倾斜,后跟一个平移

一个只有 线性 激活 (即不激活!)将很难处理像这样非常简单的分类问题(每条线有 1,000 个点,为在-1.0 和 1.0 之间等距分布的 x 值生成):

Figure 1: in this two-dimensional feature space, the blue line represents the negative cases (y = 0), while the green line represents the positive cases (y= 1).

如果网络唯一能做的事情是执行仿射变换,这可能是它能够提出的解决方案:

Figure 2: linear boundary — doesn’t look so good, right?

显然,这还远远不够!更好的解决方案的一些例子有:

Figure 3: Non-linearities to the rescue!

这是 非线性激活函数 带来的三个很好的例子!你能猜出哪个图像对应于一个 ReLU 吗?

非线性边界(或者它们是?)

这些非线性边界是如何形成的?嗯,非线性的实际作用是扭曲和旋转特征空间,以至于边界变成… 线性

好了,现在事情变得越来越有趣了(至少,我第一次看到这个很棒的克里斯·奥拉的博客帖子时是这样认为的,我从这个博客中获得了写这篇文章的灵感)。所以,我们再深入调查一下吧!

下一步是建立最简单的神经网络来解决这个特殊的分类问题。在我们的特征空间(x1x2)中有两个维度,网络有一个单独的隐层,有两个单元,所以当涉及到隐层的输出时我们保留维度的数目( z1**

****Figure 4: diagram of a simple neural network with a single 2-unit hidden layer

到此为止,我们仍然在仿射变换的领域上……所以,是时候用一个 非线性激活函数 了,用希腊字母 sigma 表示,从而产生了激活值** ( a1a2 )**

这些激活值代表了我在本节第一段提到的扭曲和旋转特征空间。这是使用【This 形作为 激活功能 时的预览图:

****Figure 5: two-dimensional feature space: twisted and turned!

如承诺的那样,边界是线性的!顺便说一下,上面的图对应于原始特征空间上具有非线性边界的最左边的解决方案(图 3** )。**

神经网络的基本数学概述

为了确保你和我在同一页上,我在下面向你展示由神经网络执行的非常基本的矩阵算法的四种表示,直到隐藏层,应用 激活函数 之前(即,只是一个仿射变换xW + b )

Basic matrix arithmetic: 4 ways of representing the same thing in the network

应用 激活功能 的时间,在网络图上用希腊字母 sigma 表示。

Activation function: applied on the results of the affine transformations

瞧!我们从输入到隐藏层的激活值

在 Keras 实施网络

对于这个简单网络的实现,我使用了 Keras 顺序模型 API 。除了不同的 激活功能 之外,每个被训练的模型都使用完全相同的超参数:

  • ***权重初始值***:Glorot(Xavier)法线(隐藏层)和随机法线(输出层);
  • 优化器 :随机梯度下降(SGD);
  • 学习率:0.05;
  • 小批量:16;
  • 隐藏层数:1;
  • 单位数 (在隐藏层):2。

鉴于这是一个二进制分类任务,输出层有一个 单单元 有一个s 形** 激活函数损失二进制交叉熵给出。**

Code: simple neural network with a single 2-unit hidden layer

激活功能正在发挥作用!

现在,对于有趣的部分— 在网络训练时可视化扭曲的特征空间,每次使用不同的 激活函数:sigmoidtanhReLU

除了显示特征空间中的变化,动画还包含:

  • 阴性(蓝线)和阳性病例(绿线)的预测概率直方图,错误分类的病例显示在红条中(使用阈值= 0.5);
  • ****精度平均损耗的线图;
  • ****数据集中每个元素的损失直方图

乙状结肠的

让我们从最传统的 激活函数sigmoid开始,尽管现在,它的使用仅限于分类任务中的输出层。

****

****Figure 6: sigmoid activation function and its gradient

从图 6 的中可以看到,一个的 sigmoid 激活函数的输入值挤压到的范围(0,1) (同样的范围概率可以取,这也是它在输出层用于分类任务的原因)。此外,请记住,任何给定层的激活值都是下一层的输入,给定 sigmoid 的范围,激活值将是以 0.5** 为中心的**,而不是零(通常是归一化输入的情况)。****

也可以验证其梯度峰值为 0.25(对于 z = 0),并且当| z |达到值 5 时已经接近零。

那么,使用一个 sigmoid 激活函数 n 如何为这个简单的网络工作呢?让我们来看看动画:

Sigmoid in action!

有几点需要注意:

  • 时期 15–40:可以注意到水平轴上发生典型的s 形挤压;**
  • 历元 40–65**:变换后的特征空间停留在一个平台上,在纵轴上有一个“加宽”;**
  • epoch 65 :此时,阴性病例(蓝线)全部被正确分类,尽管其关联概率仍然分布到 0.5;而边缘上的阳性病例仍为误分类**;**
  • 时期 65–100**:前述的加宽变得越来越强烈,几乎覆盖了所有的特征空间,而损失稳步下降;
  • 第 103 期**:由于扩大,所有阳性病例现在都位于适当的边界内,尽管仍有一些概率勉强超过 0.5 阈值;
  • 纪元 100–150**:现在垂直轴上也发生了一些挤压,损失下降到似乎是一个新的平稳状态,除了一些积极的边缘情况,网络对其预测相当有信心****

因此,**s 形激活功能 成功分离两条线,但是 损耗 缓慢下降,同时在停滞处停留相当一部分训练时间。****

我们能否用一个不同的激活功能 做得更好?******

双曲正切

tanh

Figure 7: tanh activation function and its gradient

图 7 中可以看到, tanh 激活功能输入值挤压到范围(-1,1) 。因此,由于以零为中心,激活值已经(在某种程度上)是下一层的归一化输入。******

关于梯度,它有一个大得多的峰值 1.0(同样,对于 z = 0),但是它的下降甚至更快,接近于零到值 |z |低至 3。这是所谓的消失梯度问题的根本原因,它导致网络的训练越来越慢。****

现在,对于相应的动画,使用 tanh 作为 激活函数 :

Tanh in action!

有几点需要注意:

  • 时段 10–40:横轴上有一个tanhsquashing*发生,虽然不太明显,而损耗停留在一个平台上;*****
  • 时期 40–55:在 损失 上仍然没有改善,但是在纵轴上有一个变换后的特征空间的加宽
  • 第 55 期:此时,阴性病例(蓝线)都被正确分类为,尽管其关联概率仍然分布到 0.5;而边缘上的阳性病例仍为误分类****
  • 时期 55–65:前述的加宽很快到达几乎所有特征空间再次被覆盖的点,而损失突然下降;****
  • 纪元 69 :由于“扩大”,所有阳性病例现在都位于适当的边界内,尽管仍有一些概率勉强高于 0.5 阈值;****
  • 时期 65–90:现在垂直轴上也发生了一些挤压,损耗持续下降,直到达到新的平稳状态,网络对所有预测显示出高置信度;********
  • 时期 90–150:在这一点上,预测的概率只有很小的提高。

好了,好像好一点了……这个 tanh 激活功能 达到了正确分类对于所有情况更快,随着 损耗 也下降更快(就是下降的时候),但是它也在停滞期花费了很多时间。

如果我们摆脱所有的挤压会怎么样?**

热卢

ReactivatedLlinearUnits,简称 ReLUs ,是目前 激活函数 的常见选择。一个 ReLU 解决了消失渐变的问题,这在它的两个前辈中很常见,同时也是计算渐变最快的。****

********

Figure 8: ReLU activation function and its gradient

正如你在图 8 中看到的, ReLU 是一个完全不同的怪兽:它不会将值“挤压”到一个范围内——它只是保留正值并将所有的负值变成零

使用 ReLU 的好处是它的渐变要么是 1(正值),要么是 0(负值)——不再有消失渐变!这种模式导致网络的更快收敛

另一方面,这种行为会导致所谓的“死神经元”,也就是说,神经元的输入始终为负,因此,其激活值始终为零。

最后一个动画的时间,与前两个有很大的不同,由于 ReLU 激活功能 中的挤压缺席:**

ReLU in action!

有几点需要注意:

  • 时段 0–10:亏损从一开始就稳步下降
  • 历元 10 :此时,阴性案例(蓝线)全部被正确分类,尽管其关联概率仍然分布到 0.5;而边缘上的阳性病例仍为误分类;****
  • 时期 10–60:损失下降直至达到稳定状态,时期 52** 以来,所有情况已经被正确分类,并且网络已经对所有预测展现出高置信水平**;****
  • 时期 60–150:在这一点上,预测的概率只有很小的提高。

嗯,难怪 ReLUs 是如今激活功能事实上的标准。 损失 使从一开始就稳步下降,只有稳定在接近零的水平,在中所有情况下达到正确分类的时间约为花费 tanh 的 75%。**

摊牌

动画很酷(好吧,我有偏见,是我做的!),但是不太方便在特征空间上比较每一个不同的 激活函数总体效果。所以,为了便于你比较,它们并排在这里:**

Figure 9: linear boundaries on transformed feature space (top row), non-linear boundaries on original feature space (bottom row)

那并排 准确度损耗 曲线呢,这样我也可以对比一下训练速度?当然,我们开始吧:

Figure 10: accuracy and loss curves for each activation function

最后的想法

我用来说明这篇文章的例子是尽可能简单的,动画中描述的模式仅仅是为了给你一个大概的概念关于每一个 激活函数的底层机制。********

况且我用我的 初始化权重 得到了幸运(也许用 42 做种子是个好兆头?!)并且所有三个网络都学会了在 150 个训练时期内对所有情况进行正确分类。事实证明,训练对初始化非常敏感,但这是以后文章的主题。

尽管如此,我真心希望这篇文章和它的动画能给你一些见解甚至一些“啊哈!”了解这个令人着迷的话题的时刻,这个话题就是深度学习

更新(2018 年 5 月 10 日)

现在你可以自己复制剧情和动画了:-)我已经发布了一个包——deep replay——在 GitHub 及其对应的帖子上查看一下。

感谢 Jakukyo 弗列尔,你还可以查看这篇帖子的中文版

修正了图 10 中的错别字:中间的图显示的是 tanh ,而不是 sigmoid。

如有任何想法、意见或问题,请在下方留言或联系我 推特

超参数在起作用!DeepReplay 简介

原文:https://towardsdatascience.com/hyper-parameters-in-action-introducing-deepreplay-31132a7b9631?source=collection_archive---------1-----------------------

Photo by Immo Wegmann on Unsplash

介绍

在我之前的帖子中,我邀请你去好奇当你训练一个神经网络的时候,在引擎盖下到底发生了什么。然后我研究了 激活函数 的作用,用动画说明了它们对 特征空间 的影响。

现在,我邀请在调查中发挥积极作用!

原来这些情节动画引起了相当多的关注。所以我决定组织我的代码,把它构造成一个合适的 Python 包,这样就可以绘制你自己的深度学习模型

你会问,它们看起来怎么样?好吧,如果你还没有查看最初的帖子,这里有一个快速浏览:

This is what animating with DeepReplay looks like 😃

所以,事不宜迟,我为你呈现… 深度回放

深度回放

这个包被称为 DeepReplay ,因为这正是它允许你做的事情:重放训练你的深度学习模型的过程,绘制动画制作它的几个方面。

这个过程很简单,由五个步骤组成:

  1. 这一切都从创建一个回调的实例开始!
  2. 然后,一切照旧:构建并训练你的模型。
  3. 接下来,将收集的数据加载到重放中。
  4. 最后,创建一个图形,然后将可视化效果附加到它上面。
  5. 剧情和/或动画吧!

让我们逐一完成这些步骤!

1.创建回调的实例

回调应该是 ReplayData 的一个实例。

回调将模型输入( Xy )以及 文件名组名 作为参数,用于存储收集的训练数据。

要记住两件事:

  • 对于玩具数据集,在你的模型拟合中使用相同的 Xy 就可以了。这些是将要绘制的示例-因此,如果使用较大的数据集,您可以选择数据集的随机子集来保持合理的计算时间。
  • 数据存储在一个 HDF5 文件中,你可以多次使用 同一个文件 超过,但是永远不要同一个组 !如果你尝试使用同一个组名运行它两次,你会得到一个错误

2.构建并训练您的模型

就像我说的,一切照常,这里没什么可看的…只是不要忘记在装配时将您的回调实例添加到回调列表中!

3.将收集的数据加载到重放中

所以,给整件事起名字的部分…是时候重播它了!

应该够简单了:创建一个 Replay 的实例,提供 文件名 和您在步骤 1 中选择的 组名

4.创建一个图形并附加可视化效果

实际上,这是事情变得有趣的一步。只需使用 Matplotlib 创建一个图形,就像示例中的图形一样简单,或者像 subplot2grid 允许您创建的图形一样复杂,并开始从您的 Replay 对象向图形附加可视化效果

上面的例子建立了一个 特征空间 基于层的输出命名,暗示性地, 隐藏

但是有五种类型的可视化可用:

  • 特征空间 :表示 扭曲旋转特征空间 的图形,对应一个隐藏层的输出(目前只支持 2 单元隐藏层),包括二维输入的网格线

  • 判定边界 :表示 原始特征空间 的二维网格图,连同 判定边界 (目前仅支持二维输入);

  • 概率直方图 : 两个得到的输入的分类概率的直方图,每个类别一个,对应模型输出(目前只支持二元分类);

  • 损失和度量 :损失和选择的度量的线图,计算所有作为回调参数传递的输入;

  • 损失直方图 :对作为回调参数传递的所有输入计算的损失的直方图(目前仅支持二进制交叉熵损失)。

5.绘制和/或制作动画!

对于这个例子,用一个单个 可视化,就可以直接使用它的 剧情动画 方法。这些方法将分别返回一个图形和一个动画,然后您可以将它们保存到文件中。

如果您决定使用多个同时可视化,有两个辅助方法返回合成的情节和动画,分别是:compose _ plotscompose _ animations

为了说明这些方法,这里有一个要点,它来自我在最初的帖子中使用的“示例。有四个可视化和五个图( 概率直方图两个图,用于阴性和阳性情况)。

本帖开头的动画 GIF 其实就是这个构图动画的结果!

限制

此时,你大概注意到了,两个最酷的可视化, 特征空间 决策边界 ,都被限制在两个维度

我还计划在三维中添加可视化支持,但大多数数据集和模型要么有更多输入要么有更多单元的隐藏层。

所以,这些是你的选择:

  • 2D 输入,2 单元隐藏层: 特征空间 带可选网格(查看激活函数示例);
  • 3D+输入,2 单元隐藏层: 特征空间 ,但无网格;
  • 2D 输入,隐藏层用 3+单位: 决定边界 用可选网格(查看圆圈示例);
  • 没有什么是二维的:嗯…总有一个解决方法,对吗?

围绕多维度工作

我们想要实现什么?因为我们只能做二维图,我们想要二维输出——很简单。

如何获得二维输出?增加一个额外隐藏层两个单位当然!好的,我知道这是次优*,因为它实际上是在修改模型(我提到过这是一个变通办法吗?!)。然后我们可以使用这个额外图层的输出进行绘图。*

你可以查看 月亮 或者 UCI Spambase 笔记本,查看添加一个额外的隐藏层并绘制它的示例。

继续进行,风险自负:-)

不管怎样,我们对这个模型做了什么?通过添加一个额外的隐藏层,我们可以认为我们的模型有两个组件*:一个 编码器 和一个 解码器 。让我们稍微深入一点:*

  • 编码器:编码器从输入一直到我们的额外隐藏层。让我们把它的二维输出看作是特征*并把它们叫做 f1f2 。*
  • 解码器:在这种情况下,解码器只是一个简单明了的逻辑回归*,它接受两个输入,比如说 f1f2 ,并输出一个分类概率。*

让我试着用一个网络图来说得更清楚些:

Encoder / Decoder after adding an extra hidden layer

这是什么?一个 9 维输入,一个有 5 个单元的原始隐藏层,一个有两个单元的额外隐藏层,其对应的两个输出(特征)和一个单个单元输出层。

那么,在输入的过程中会发生什么?让我们看看:

  1. 输入( x1x9* )被馈入 编码器 部分的模型。*
  2. 隐**层曲折层投入。隐藏层的输出也可以被认为是特征**(这些将是图中单元h1H5*的输出),但是这些被假定为 n 维,因此不适合绘图。到目前为止,一切如常。*****
  3. 然后是额外的隐藏层。它的权重矩阵具有形状 (n,2) (在图中, n = 5 并且我们可以在*和 e 节点之间计数 10 个箭头)。如果我们假设一个 线性激活函数 ,这一层实际上是在执行一个仿射变换,将点从一个 n 维映射到一个二维特征空间。这些是我们的功能,【F2】编码器的输出* 部分。******
  4. 既然我们假设一个 线性激活函数 用于额外的隐藏层,那么 f1f2 将被直接馈送到 解码器 (输出层),也就是说,馈送到一个具有的单个单元这是一个简单明了的逻辑回归。

这一切意味着什么?意味着我们的模型也在学习一个 潜在空间两个潜在因素 ( f1f2 )现在!很奇特,是吧?!不过,不要被这些术语的花哨所吓倒……这基本上意味着模型学会了将信息最好地压缩为两个特征,给定手头的任务——二进制分类。****

这是 自动编码器 的基本原理,主要区别在于自动编码器的任务是重建其输入,而不是以任何方式对其进行分类。

最后的想法

我希望这篇文章能吸引你尝试一下深度回放

如果你为不同的数据集,或者使用不同的网络架构或超参数,想出了好看又酷的可视化,请评论部分分享它。如果有足够的兴趣,我正在考虑开始一个画廊页面。

有关 DeepReplay 包的更多信息,如安装、文档、示例和笔记本(你可以使用 Google Colab 来玩),请访问我的 GitHub 资源库:

**** [## DVD godoy/deep replay

深度回放-深度回放-生成可视化效果,如我的“超参数运行!”系列!

github.com](https://github.com/dvgodoy/deepreplay)

祝你的模型动画制作愉快!😃

如果你有什么想法、评论或问题,请在下方留言或联系我 推特 ****

超参数在起作用!第二部分—权重初始值设定项

原文:https://towardsdatascience.com/hyper-parameters-in-action-part-ii-weight-initializers-35aee1a28404?source=collection_archive---------0-----------------------

Photo by Jesper Aggergaard on Unsplash

介绍

这是我关于超参数系列的第二篇文章。在这篇文章中,我将向你展示正确初始化你的深度神经网络的权重重要性。我们将从一个简单的初始化方案开始,解决它的问题,就像消失 / 爆炸渐变,直到我们(重新)发现两个流行的初始化方案:Xavier/GlorotHe

我假设你已经熟悉了一些关键概念(Z 值、激活函数及其梯度),我在本系列的第一篇帖子中已经提到过。

说明这篇文章的情节是用我的包 DeepReplay 生成的,你可以在 GitHub 上找到它,并在这篇文章上了解更多。

动机

在我寻求更深入地理解每一个不同的超参数对训练深度神经网络的影响时,是时候研究一下权重初始化器了。

如果您曾经搜索过这个特定的主题,您可能会遇到一些常见的初始化方案:

  • 随机
  • 泽维尔 / 格洛特

如果你挖得更深一点,你可能还会发现,如果激活函数是一个 Tanh ,那么应该使用 Xavier / Glorot 初始化,如果激活函数是一个 ReLU ,那么推荐使用 He 初始化

顺便说一下,澄清一些事情: Xavier GlorotYoshua Bengio 是“ 理解训练深度前馈神经网络 的困难”论文的作者,该论文概述了将作为其第一作者的开头( Xavier 或最后( Glorot )的初始化方案。因此,有时这种方案将被称为 Xavier 初始化、和其他一些时候(如在 Keras 中),它将被称为 Glorot 初始化。不要被这个迷惑,因为我是第一次知道这个话题。

弄清楚这一点后,我再问你一次:你有没有想过引擎盖下到底发生了什么?为什么初始化这么重要?初始化方案之间的差异是什么?我的意思是,不仅是他们对方差应该是什么的不同定义,而且是在训练一个深度神经网络时使用其中一个的总体效果!

在深入研究之前,我想给它应有的信任:这些情节在很大程度上受到了安德烈·皮卢尼奇关于同一主题的令人敬畏的帖子的启发。

好了,现在让我们开始吧!

设置

确保您使用的是 Keras 2.2.0 或更新版本-旧版本有一个问题,生成的权重集的方差低于预期!

在这篇文章中,我将使用一个具有 5 个隐藏层100 个单位的模型,以及一个典型的二进制分类任务中的单个单位输出层(即使用 sigmoid 作为激活函数,使用二进制交叉熵作为损失)。我将这个模型称为模块模型,因为它有相同大小的连续层。我使用以下代码来构建我的模型:

Model builder function

块状模型

这是块模型的架构,不考虑我将用来构建图的激活函数和/或初始化器。

输入

输入是从 10 维球中抽取的1000 个随机点(这看起来比实际上的更好,你可以把它想象成一个有 1000 个样本的数据集,每个样本有 10 个特征)这样样本就有了零均值单位标准差

在该数据集中,位于球半径一半内的点被标记为阴性情况 (0),而剩余的点被标记为阳性情况 (1)。**

Loading 10-dimensional ball dataset using DeepReplay

朴素初始化方案

开始的时候,有一个 sigmoid 激活函数随机初始化的权重。而且训练是,收敛是,成绩是不好。****

但是,为什么呢?****

那时,通常的程序是*从一个正态分布(零均值,单位标准偏差)中抽取随机值*,然后将它们乘以一个小数字,比如说 0.01 。结果是一组标准偏差约为 0.01 的砝码。这导致了一些问题…

在进入更深的钻头之前(只是一个钻头,我保证!)进入为什么这是一个坏的初始化方案的数学原因,让我展示在带有 sigmoid 激活功能的模块模型中使用它的结果:

Code to build the plots! Just change the initializer and have fun! 😃

Figure 1. BLOCK model using sigmoid and naive initialization — don’t try this at home!

这个好看吧?你能发现所有正在变坏的东西吗?

  • Z 值**(记住,这些是应用激活功能之前的输出)和激活都在窄范围内;
  • 梯度几乎为零
  • 左栏的奇怪的分布是怎么回事?!

不幸的是,如果我们选择尝试和训练它,这个网络可能不会很快学到很多东西。为什么是?因为它的渐变消失了

我们甚至还没有开始培训过程!这是纪元 0** !那么,到目前为止发生了什么?让我们看看:**

  1. 使用简单方案** ( 右上子情节)初始化**权重****
  2. 1000 个样本被用于通过网络的正向传递,并为所有层(输出层不包括在图中)生成了 Z 值 ( 左上子图)和激活** ( 左下子图)**
  3. 针对通过网络反向传播的和真实标签计算损失,生成所有层的梯度(右下方子图******

就是这样!单遍通过网络!

接下来,我们应该相应地更新权重,然后重复这个过程,对吗?但是,等等…如果梯度几乎为零,那么更新后的权重将几乎与相同,对吗?

****是什么意思?这意味着我们的网络几乎毫无用处,因为它无法在合理的时间内学习任何东西(即,更新其权重以执行所提议的分类任务)。

欢迎来到消失渐变的极端案例!

你可能会想:“是的,当然,标准差太低了,不可能像那样工作”。那么,尝试不同的怎么样,比如说, 10x 或者 100x 大

标准偏差大 10 倍= 0.10

Figure 2. BLOCK model using 10x bigger standard deviation

好了,这看起来好一点了… Z 值激活合适的范围内,倒数第二个隐藏层的渐变显示出一些改善,但是仍然朝着初始层消失

也许把变得更大可以修正渐变,让我们看看…

标准偏差大 100 倍= 1.00

Figure 3. BLOCK model using 100x bigger standard deviation

好的,看起来我们在消失渐变问题中有了 som e progress ,因为所有层的范围变得彼此更加相似。耶!但是** …我们毁了Z 值激活……现在 Z 值显示出太宽的范围,迫使激活几乎变成二进制模式。**

尝试不同的激活功能

如果你读了我关于超参数的第一篇文章,你会记得一个 Sigmoid 激活函数有一个基本的问题,就是以 0.5 为中心的。所以,让我们继续遵循神经网络的进化路径,使用一个 Tanh 激活函数来代替!****

Figure 4. BLOCK model using Tanh and naive initialization

用来自正态分布的小随机值替换 Tanh 激活函数的 Sigmoid ,同时保持初始初始化方案将我们带到了另一种消失渐变的情况(它可能看起来,毕竟,它们沿着所有层都是** 相似的,但是检查一下比例、渐变),伴随着消失的 Z 值消失的激活(只是为了明确,这两个是而不是真正的术语)!肯定,不是该走的路!**

让我们一直使用一个大的标准差,然后看看结果如何(是的,我把最好的留到最后……)。

Figure 5. BLOCK model using Tanh and a BIG standard deviation

在这个设置中,我们可以观察到爆炸渐变的问题。看到渐变值如何随着我们从最后一个隐藏层到第一个隐藏层越来越大了吗?此外,就像使用 Sigmoid 激活函数时发生的一样, Z 值具有太宽的范围激活在大多数情况下都崩溃为零或一个。还是那句话,不好!

并且,如承诺的那样,获胜者是… Tanh 标准差 0.10

Figure 6. BLOCK model looking good!

为什么这个一个是赢家?让我们来看看它的特点:

  • 首先,梯度沿着所有层合理地相似** (并且在适当的比例——大约比权重小 20 倍)**
  • 第二, Z 值合适的范围 (-1,1)内,并且沿着所有层相当相似(尽管一些收缩是明显的)****
  • 第三,激活没有折叠成二进制模式,并且沿着所有层合理地相似(再次,有一些收缩)****

如果你还没有注意到,在所有层上相似是一件大事!简而言之,这意味着我们可以在网络的末端堆叠另一层,并期待类似的分布Z 值激活,当然还有梯度。在我们的网络中,我们绝对做而不是折叠消失爆炸的行为,不,先生!****

但是,所有层的相似是结果,而不是原因……正如你可能已经猜到的,关键是权重标准偏差!****

因此,我们需要一个初始化方案,它使用最佳可能标准偏差来抽取随机权重!进入泽维尔·格洛特约舒阿·本吉奥

Xavier / Glorot 初始化方案

Glorot 和 Bengio 设计了一个初始化方案,试图保持所有获胜特征被列出,即渐变Z 值激活沿着所有层相似。另一种说法是:保持所有层的变化相似。

你可能会问,他们是怎么把这个拉出来的?一会儿我们会看到,我们只需要做一个真正的** 简要的回顾一下方差的一个基本性质。**

非常简要地回顾一下

假设我们有 x 值(来自前一层的输入激活值)和 W 权重。两个独立变量的乘积的方差由以下公式给出:

那么,我们假设 xW 都有零均值。上面的表达式变成了两个方差 xW 的简单乘积。

这里有两点很重要:

  1. 输入应该有零均值**以保持在第一层,因此总是缩放和居中您的输入!
  2. Sigmoid 激活函数对此提出了一个问题,因为激活值的平均值为 0.5,不是 !关于如何补偿的更多细节,请查看这个帖子

鉴于第二点,坚持使用 Tanh 才有意义,对吗?所以,这正是我们要做的!现在,是时候将这些知识应用到一个小例子中了,所以我们到了(希望如此!)得出与 GlorotBengio 相同的结论。

Figure 7. Two hidden layers of a network

微小的例子

这个例子由两个完全连接的隐藏层组成, XY,(我把通常的约定抛到九霄云外,以保持数学符号最少!).

我们只关心连接这两层的权重以及激活渐变差异

对于激活,我们需要在网络中通过一个转发通道。对于渐变,我们需要反向传播

Figure 8. Tanh activation function

并且,为了保持数学简单,我们将假设激活函数在等式中是线性的(而不是 Tanh ),这意味着激活值是与 Z 值相同的。****

虽然这看起来有点夸张,但是图 8 向我们展示了在区间[-1,1] 中,Tanh 大致是线性的,所以结果应该成立,至少在这个区间内。

Figure 9. Forward Pass

前进传球

因此,不使用矢量化方法,我们将挑出一个单元、 y1 ,并计算它。

图 9 提供了所涉及零件的清晰图片,即:

  • 三个单元在前一层** ( 扇入)**
  • 重量 ( w11w21w31 )
  • 我们要计算的单位方差为,y1****

假设 xW独立同分布,我们可以对 y1 :方差进行一些简单的数学运算

还记得关于差异简要回顾吗?是时候好好利用它了!

好了,快到了!记住,我们的目标是保持方差沿着所有层相似。换句话说,我们应该致力于使*x 的方差**与y 的方差相同。***

对于我们的单个单元, y1 ,这可以通过选择其连接权重方差为:

并且,对于所有隐藏层 XY 之间的连接权重,我们有:

顺便说一下,如果我们从一个正态 分布中抽取随机权重,这就是要使用的方差

如果我们想用一个均匀分布怎么办?我们只需计算(对称的)下限和上限,如下所示:

完事了吗?!还没有…不要忘了反向传播,我们也想保持的渐变沿着所有的层(它的方差,更精确)。****

Figure 10. Backward Pass

反向传递(反向传播)

还是那句话,我们挑出一个单位, x1 ,用于后向传递。****

图 10 提供了所涉及零件的清晰图片,即:

  • 以下五层 ( 扇出)
  • 重量 ( w11w12w13w14w15 )
  • 我们要计算梯度相对于它的 x1方差的单位****

基本上,我们将做出相同的假设,并遵循与正向传递中相同的步骤。对于梯度** s 相对于 x1方差,我们可以用同样的方法计算出来:******

再次利用我们在简要回顾中学到的知识:**

并且,为了保持沿所有层的梯度方差相似,我们发现其连接权重所需的方差为:****

好了,我们已经走了很长一段路了!中的“扇出”的逆运算给出了正向传递权重的期望方差,而“扇出的逆运算给出了( )的期望方差!)用于反向传播的权重。********

但是…如果“扇入”和“扇出”有非常不同的值呢?

协调向前和向后传球

无法决定选择哪一个,“扇入”或“扇出”,来计算你的网络权重方差?没问题,就拿平均值吧!

因此,我们最终得出了权重方差的表达式,如 GlorotBengio 所示,用于正态分布:

并且,对于均匀分布,我们相应地计算极限:

****恭喜!你(重新)发现了 Xavier / Glorot 初始化方案

但是,仍然有一个小的细节,你应该选择一个正态分布来提取权重吗…

截断正态和 Keras 方差标度

当谈到神经网络的权重时,我们希望它们整齐地分布在零附近,甚至更重要的是,我们不希望有任何异常值!所以,我们截断它!****

截断是什么意思?只要去掉任何比两倍标准差远的值!因此,如果您使用标准偏差 0.1 ,截尾正态分布将绝对没有低于-0.2 或高于 0.2** 的值(如图 11** 左侧图)。****

事情是这样的,一旦你切掉了正态分布的尾部,剩下的值有一个稍微低一点的标准差…准确的说是原始值的 0.87962566103423978。

在 Keras 2 . 2 . 0 之前的版本中,截断正态分布的这种差异在方差缩放初始化器中没有考虑,而这是 Glorot 和 he 初始化器的基础。因此,在更深层次的模型中,基于均匀分布的初始化器可能会比它的正常对应物表现得更好,正常对应物会遭受一层又一层缓慢缩小的方差…

到今天为止,这不再是一个问题,我们可以在图 11 的右侧图中观察到补偿截断的效果,其中方差缩放初始值的分布明显更宽。****

Figure 11. Truncated normal and Keras’ Variance Scaling

求一些剧情!

非常感谢你陪我看完了更多的数学部分。你的耐心将会得到丰厚的回报!

让我们看看 Glorot 初始化器(正如它在 Keras 中被调用的)如何执行,使用正常统一分布。

Figure 12. BLOCK model with Glorot Normal initializer

Figure 13. BLOCK model with Glorot Uniform initializer

看起来我们有两个赢家了!

还记得我们之前的赢家吗,在图 6** 中使用朴素初始化方案标准差 0.1 的 BLOCK 模型?结果非常相似,对吧?**

事实证明,根据 Glorot 初始化方案,当“扇入”和“扇出”等于 100 时,我们使用的 0.1 标准偏差正是正确的值。这是而不是使用截尾正态分布,虽然…

所以,这个初始化方案解决了我们的消失爆发渐变的问题…但是它是否适用于不同于 Tanh 的激活函数?让我想想…

整流线性单元(ReLU)激活功能

我们能坚持使用相同的初始化方案,而使用 ReLU 作为激活函数吗?

Figure 14. BLOCK model with ReLU and Glorot Normal initializer — they don’t mix well…

答案是:没有

回到起点…我们需要一个新的改进的初始化方案。进入等人,带着他们的“ 钻研整流器 ”论文…

初始化方案

幸运的是,我们在(重新)发现 Glorot 初始化方案时得到的一切仍然有效。只有一个微调我们需要做… 将权重的方差乘以 2 !真的,这就是全部的代价!

Figure 15. ReLU activation function

很简单,对吧?但是,为什么是

原因也很简单: ReLUZ 值(负一)的一半变成,有效地去除了差异的大约一半。因此,我们需要将权重的方差加倍来补偿它。

既然我们知道 Glorot 初始化方案保留了方差** ( 1 ),那么如何补偿对于 ReLU ( 2 )的方差减半效应?结果( 3 )不出所料,是将方差翻倍。**

因此,与正态分布一起使用的权重方差的表达式为:

并且,对于均匀分布,我们相应地计算极限:

****恭喜!你(重新)发现了 He 初始化方案

但是 …那么反向传播呢?难道我们不应该再次使用两个“粉丝的平均值吗?实际上,没有也不需要了。等人在他们的论文中指出,对于常见的网络设计,如果初始化方案在正向传递期间缩放激活值,那么对于反向传播 以及也是如此!此外,它以两种方式工作,所以我们甚至可以使用扇出,而不是扇入**。****

现在,是更多剧情的时候了!

Figure 15. BLOCK model with ReLU and He Normal initializer

Figure 16. BLOCK model with ReLU and He Uniform initializer

再来两个获奖者!当谈到 Z 值的分布时,它们看起来非常相似!至于渐变,它们现在看起来比我们用Tanh/Glorotduo 的时候多了一点vanish…这是否意味着 Tanh / GlorotReLU / He 更好?我们知道这是不是真的…

但是,那么,为什么它的渐变图 16** 上看起来不那么好看呢?嗯,再一次,别忘了看一下刻度!即使梯度方差随着我们通过网络反向传播而减少,其值也无处靠近的消失(如果你记得图 4 ,情况正好相反——沿层的方差*相似,但它).*******

因此,我们不仅需要沿着所有层的相似的变化,还需要一个合适的渐变比例比例非常重要,因为它将与学习率一起定义多快更新权重****更新。如果坡度太小,则学习(即权重更新)将极慢。****

你会问,有多小才算太小?一如既往,它取决于 …重量大小*。所以,过小是不是绝对度量,而是相对度量。*

如果我们计算梯度的方差和相应权重方差之间的比率(或其标准差,就可以大致比较不同初始化方案学习速度及其底层分布(假设学习速率不变)。****

所以,是时候…

摊牌——普通对制服,格洛特对贺!

说实话,GlorotvsHe其实就是指TanhvsReLU这场比赛的答案我们都知道(剧透预警!): ReLU 胜

普通** vs 制服呢?让我们来看看下面的情节:**

Figure 17. How big are the gradients, after all?

赢家是……制服!很明显,至少对于我们的特定块模型和输入,使用均匀分布比使用正态分布产生相对更大的****梯度。****

此外,正如所料,使用 ReLU 比使用 Tanh 产生相对更大的梯度**。对于我们的特定示例,这对于第一层不成立,因为其在中的扇形仅为 10 (输入的尺寸)。如果我们使用 100 维输入,那么 ReLU梯度也会比该层的****

而且,即使看起来一样有点"消失"当使用 ReLU 时,只要看一下图 17 最右边的紫色小条…我将简单初始化的*和 Sigmoid 激活的网络滑入了情节*****

Ratio: standard deviation of gradients over standard deviation of weights

综上所述,对于一个 ReLU 激活的网络,使用均匀分布He 初始化方案是一个不错的选择;-)**

有很多很多方法可以分析选择特定初始化方案的影响…我们可以尝试不同的网络架构(如“漏斗”或“沙漏”形状),更深的网络,改变标签的分布(因此,损失)…我尝试了很多组合,他/统一总是优于其他初始化方案,但这篇文章已经太长了!

最后的想法

这是一篇 looong 的帖子,尤其是对于一个如此理所当然的话题,如重量* 初始者!但是我觉得,一个人要真正理解它的重要性,就应该遵循步骤,碰到导致现在使用的方案发展的问题。***

尽管作为一名从业者,你知道用于初始化你的网络的"正确的"组合,我真的希望这篇文章能够给你一些洞察真正发生了什么,最重要的是,为什么* 那个特定组合是"正确的"一:-)***

如果你有什么想法、评论或者问题,请在下方留言或者联系我 推特

基于 Keras 的超参数优化

原文:https://towardsdatascience.com/hyperparameter-optimization-with-keras-b82e6364ca53?source=collection_archive---------0-----------------------

为深度学习模型找到正确的超参数可能是一个繁琐的过程。不一定要。

TL;速度三角形定位法(dead reckoning)

有了正确的流程,就不难为给定的预测任务找到最先进的超参数配置。在三种方法中——手动、机器辅助和算法——本文将重点讨论机器辅助。本文将介绍我是如何做到这一点的,证明这种方法是可行的,并提供对它为什么可行的理解。主要原则是简单。

关于性能的几句话

关于性能的第一点涉及到作为测量模型性能的方法的准确性(和其他更健壮的度量)的问题。以 f1 成绩为例。如果你有一个 1%肯定的二进制预测任务,那么一个让所有事情都为 0 的模型将接近完美的 f1 分数和准确性。这可以通过对 f1 分数处理极限情况的方式进行一些改变来处理,例如“全零”、“全一”和“无真阳性”但这是一个很大的话题,超出了本文的范围,所以现在我只想说明,这个问题是让系统超参数优化工作的一个非常重要的部分。我们在这个领域有很多研究,但研究更多地集中在算法上,而不是基本面。事实上,你可以拥有世界上最复杂的算法——通常也非常复杂——根据毫无意义的指标做出决策。这对处理“现实生活”中的问题不会有太大的帮助。

不要犯错误;即使我们得到了正确的性能指标(是的,我在叫喊),我们也需要考虑在优化模型的过程中会发生什么。我们有一个训练集,然后我们有一个验证集。一旦我们开始查看验证结果,并开始在此基础上进行更改,我们就开始偏向验证集。现在我们得到了训练结果,这是机器偏差的产物,我们得到了验证结果,这是我们偏差的产物。换句话说,我们得到的模型并不具有一个很好的广义模型的性质。相反,它偏离了一般化。所以记住这一点非常重要。

关于更先进的全自动(无监督)超参数优化方法的关键点在于首先解决这两个问题。一旦这两个问题解决了——是的,有办法做到这一点——最终的指标将需要作为一个单一的分数来实现。然后,该分数成为超参数优化过程被优化的度量。否则,世界上没有任何算法会有所帮助,因为它会优化我们所追求的东西。我们又在找什么?将完成预测任务所阐述的任务的模型。不仅仅是一个模型用于一种情况(这在涉及该主题的论文中经常出现),而是所有类型的模型,用于所有类型的预测任务。这就是像 Keras 这样的解决方案所允许我们做的,任何使用像 Keras 这样的工具来实现过程自动化的尝试都应该接受这个想法。

我用了什么工具?

对于本文中的所有内容,我使用 Keras 作为模型,Talos 是我构建的超参数优化解决方案。好处是它公开了 Keras,而没有引入任何新的语法。它让我可以在几分钟内完成过去需要几天才能完成的事情,而不是痛苦的重复。

你可以自己试试:

pip install talos

或者在这里看代码/文件

但是我想分享的信息,以及我想表达的观点,与一个工具无关,而是与过程有关。你可以按照你喜欢的任何方式遵循同样的程序。

自动化超参数优化和相关工具的一个更突出的问题是,您通常会远离您习惯的工作方式。与所有复杂问题一样,成功的预测任务无关超参数优化的关键在于拥抱人机合作。每一个实验都是一个学习更多关于实践(深度学习)和技术(在这个例子中是 Keras)的机会。这个机会不应该以牺牲过程自动化为代价而被错过。与此同时,我们应该能够去掉这一过程中明显多余的部分。想象一下在 Jupyter 中执行 shift-enter 几百次,并在每次迭代之间等待一两分钟。总之,在这一点上,我们的目标不应该是以全自动的方式找到正确的模型,而是尽量减少给人带来负担的程序冗余。机器自己运转,而不是机械地操作机器。我不是一个一个地分析各种模型配置的结果,而是想以千为单位或者以十万为单位进行分析。一天有 80000 多秒,在那段时间里可以覆盖很多参数空间,而不用我做任何事情。

我们开始扫描吧

为了举例,我将首先提供我在本文所涉及的整个实验中使用的代码。我使用的数据集是 威斯康星乳腺癌 数据集。

一旦定义了 Keras 模型,就该决定初始参数边界了。然后,字典以这样一种方式被输入到处理过程中,即单个排列被挑选一次,然后被忽略。

根据我们希望包含在扫描中的损失、优化器和激活,我们需要首先从 Keras 导入这些函数/类。接下来,模型和参数准备好了,就该开始实验了。

请注意,我不会分享更多的代码,因为我所做的只是更改了参数字典中与以下部分提供的见解相关的参数。为了完整起见,在文章的最后,我将分享一个包含代码的笔记本的链接。

因为在第一轮实验中有许多排列(总共超过 180,000 个),所以我随机选取了总数的 1%,这样我们就剩下 1,800 个排列了。

在这种情况下,我正在用一台 2015 年的 MacBook Air 跑步,看起来我正好有时间见一个朋友,喝杯咖啡(或两杯)。

超参数扫描可视化

对于这篇文章,使用威斯康星州乳腺癌数据集,我已经建立了实验,假设没有关于最佳参数或数据集的知识。我通过删除一列并转换所有其他列来准备数据集,以便每个特征的平均值为 0,标准偏差为 1。

在最初运行 1800 个排列后,是时候看看结果并决定如何限制(或改变)参数空间了。

一个简单的等级顺序关联显示 lr(学习率)对我们的性能度量有最强的影响,在这种情况下是 val_acc(验证准确性)。对于这个数据集,val_acc 是可以的,因为有很多正值。对于假阳性之间存在显著差异的数据集,准确性不是一个好的衡量标准。似乎隐藏层、学习率和辍学率都与 val_acc 显著负相关。一个简单的网络将在这项任务中做得更好。对于正相关,时代的数量是唯一突出的。让我们靠近一点看。在下图中,我们在 x 轴上显示了时期(50、100 和 150),在 y 轴上显示了 val_acc,在列中显示了学习率,在色调中显示了辍学。这种趋势似乎大体上如相关性所暗示的那样;较小的辍学者比较大的辍学者表现更好。

另一种观察漏失的方法是通过核密度估计。这里我们可以看到,在压差为 0 或 0.1 的情况下,val_acc 稍有增加的趋势,而 val_acc 较低的趋势(约为 0.6)。

下一轮扫描的第一个行动项目是完全消除较高的辍学率,并关注 0 到 0.2 之间的值。接下来让我们更仔细地看看学习率。请注意,学习率在优化器之间被标准化为一个范围,其中 1 表示该优化器的 Keras 默认值。

情况相当清楚;较小的学习速率对两种损失函数都很有效,并且这种差异在 logcosh 中尤其明显。但是因为二进制交叉熵在所有学习速率水平上都明显优于其他水平,所以在实验的剩余部分,它将是我们选择的损失。尽管如此,仍然需要进行健全性检查。如果我们看到的不是对训练数据的过度拟合呢?如果 val_loss 到处都是,而我们只是看着画面的一面而忘乎所以,怎么办?简单的回归分析表明事实并非如此。除了一些异常值,所有东西都很好地打包在左下角我们想要的地方。趋势是训练和验证损失都接近于零。

我认为现在我们知道的已经足够了;是时候设置下一轮实验了!作为参考,下一个实验的参数空间如下所示:

除了细化学习速率、放弃和批量大小的界限,我还添加了 kernel_initializer 的 uniform。请记住,在这个阶段,目标是了解预测任务,而不是过于专注于寻找解决方案。这里的关键点是,除了了解具体的预测挑战之外,还要进行实验并了解整个过程。

第 2 轮—增加对结果的关注

最初,我们越少关注结果(更多关注过程),就越有可能获得好的结果。就像下棋一样;如果一开始你太专注于赢得比赛,你就不会专注于开局和中局。竞技棋局赢在残局,基于打好开局和中局。如果一切顺利,超参数优化过程中的第二次迭代就是中间。我们还没有完全专注于赢得比赛,但它有助于着眼于奖励。在我们的例子中,来自第一轮的结果(94.1%的验证准确性)表明,对于给定的数据集和设置的参数边界,存在要进行的预测。

这种情况下,这里的预测任务就是说乳腺癌是良性的还是恶性的。这种类型的预测是一件大事,因为假阳性和假阴性都很重要。预测错误会对这个人的生活产生一些负面影响。如果你感兴趣,有一堆关于这个数据集的论文,以及其他一些相关信息,你都可以在这里找到。

第二轮的结果是 96%的验证准确性。下面的相关性表明,在这一点上唯一突出的是纪元的数量,所以对于第三轮,这是我要改变的一件事。

如果你只看相关性,就有在更大的图景中遗漏某些东西的危险。在超参数优化中,重要的是给定参数中的单个值,以及它们与所有其他值的相互联系。既然我们已经消除了 logcosh 损失函数,并且在参数空间中只有一个损失(binary_crossentropy ),我想了解一下不同的优化器在各个时期的上下文中是如何执行的。

这就像这种相关性所暗示的时代(现在在 x 轴上)。因为 RMSprop 在 100 和 150 中表现不佳,所以让我们在下一轮也放弃它。

在继续之前,让我们非常简要地考虑一个与超参数优化相关的基本问题,作为优化挑战。我们想要达到的目标是什么?答案可以用两个简单的概念来概括:

  • 最佳预测
  • 结果熵

最佳预测是指我们有一个既精确又通用的模型。结果熵是熵尽可能接近零(最小)的地方。结果熵可以理解为一个结果集内所有结果之间相似性的度量(一轮经历 n 次排列)。理想的情况是,预测最佳值为 1,这是 100%的预测性能和 100%的通用性,得到的熵为 0。这意味着无论我们在超参数空间内做什么,每次都只能得到完美的结果。由于几个原因,这是不可行的,但是有助于记住优化超参数优化过程的目标。回答这个问题的另一种方式是通过三个层次的考虑;

  1. 预测任务,目标是找到为该任务提供解决方案的模型
  2. 超参数优化任务,目标是找到预测任务的最佳模型(用最少的努力)
  3. 超参数优化任务优化任务,其目标是找到最佳方法,以最佳方法找到预测任务的最佳模型

你可能会问,这是否会导致我们无限前进,在优化器之上还需要优化器,答案是肯定的。在我看来,超参数优化问题之所以有趣,是因为它引导我们找到了“构建模型的模型”问题的解决方案但是这将使我们远离本文的范围。

考虑到第二个方面,尤其是第三个方面,我们需要考虑该过程的计算效率。我们浪费的计算资源越少,我们就有越多的计算资源来寻找第一和第二方面的最佳结果。从这个角度考虑下面的图表。

从把资源分配到我们需要的地方的意义上来说,第二轮 KDE 看起来要好得多。它们在 x 轴上更接近于 1,并且很少向 0“溢出”。无论扫描的计算资源是什么,它们都在做重要的工作。这里的理想图像是一条 x 值为 1 的直线。

第 3 轮—概括和绩效

让我们开门见山吧。峰值验证准确率现在是 97.1%,看起来我们正朝着正确的方向前进。我犯了一个错误,仅仅增加了 175 个历元作为最大值,并且基于下面的;看来我们必须走得更远。至少在这种配置下。这让我想到…也许在最后一轮,我们应该尝试一些令人惊讶的东西。

正如在前言中所讨论的,考虑一般化也很重要。每当我们看到结果,我们的洞察力就会开始影响实验。最终结果是,我们开始得到不太通用的模型,这些模型可以很好地处理验证数据集,但可能无法很好地处理“真实”数据集。在这种情况下,我们没有很好的方法来测试这种偏差,但至少我们可以采取措施,以我们所拥有的来评估伪泛化的程度。先看训练和验证准确性。

即使这并没有给我们一个肯定的确认,有一个很好的概括的模型,事实上,它离它还差得很远;回归分析结果好不了多少。那我们再来看亏损。

就更好了。事情看起来不错。对于最后一轮,我将增加历元的数量,但我也将尝试另一种方法。到目前为止,我只有非常小的批量,这需要很多时间来处理。在第三轮中,我只包括了批次大小 1 到 4。接下来,我将投入 30 左右,看看会有什么效果。

关于提前停止的几句话。Keras 通过提前停止功能提供了一种非常方便的使用回调的方法。你可能已经注意到了,我没有用那个。一般来说,我会推荐使用它,但它并不像我们到目前为止所做的那样微不足道。以不限制您找到最佳可能结果的能力的方式获得正确的设置并不简单。最重要的方面与度量有关;我希望首先创建一个自定义指标,然后使用它作为我的早期停止模式(而不是使用 val_acc 或 val_loss)。也就是说,早期停止和一般的回调提供了一种非常强大的方式来增加您的超参数优化过程。

第 4 轮—最终结果出来了

在深入研究结果之前,让我们再来看一个上一轮结果的图像。这次是五维的。我想看到其余的参数——内核初始化器、批量大小、隐藏层和时期——都在同一张图片上,与验证准确性和损失进行比较。第一准确性。

基本上是不分上下,但有些事情确实很突出。第一件事是,如果一个隐藏层值(色调)下降,在大多数情况下,它的一个隐藏层。对于批量大小(列)很难说,对于内核初始化器(行)也是如此。接下来让我们看看 y 轴上的验证损失,看看我们是否能从中了解更多。记住,这里我们寻找的是较小的值;我们试图用每个参数排列来最小化损失函数。

统一内核初始化器在保持所有时期、批量大小和隐藏层变化的损失方面做得很好。但是因为结果有点不一致,所以我会保留两个初始化器直到最后。

获胜者是…

获胜的组合是来自最后一刻的想法,尝试更大的批量以节省时间和更少的时期):

小批量的最高结果是验证准确率为 97.7%。使用较大批量的方法,还有一个好处是模型收敛得非常快。在这篇文章的最后,我会提供一个视频,你可以自己看。老实说,一旦我看到更大的批量是如何工作的,我就建立了一个单独的测试。设置它只花了不到一分钟的时间,因为我需要改变的只是批量大小(对于这个较小的时期),扫描在 60 分钟内完成。关于情节,没有什么可看的,因为几乎所有的结果都接近 100%。还有一件事我想分享,因为它从一个不同于我们已经讨论过的角度,与熵的概念有关。熵可以是评估过度拟合的有效方法(因此是泛化的代理)。在这种情况下,我使用 KL 散度分别针对训练损失和准确度来测量 val_loss 和 val_acc 熵。

过程总结

  • 尽可能简单而广泛地开始
  • 试着尽可能多地了解实验和你的假设
  • 对于第一次迭代,尽量不要太关注最终结果
  • 确保您的绩效指标是正确的
  • 请记住,性能是不够的,因为它会使您偏离通用性
  • 每次迭代应该减少参数空间和模型复杂性
  • 不要害怕尝试,这毕竟是一个实验
  • 使用你能理解的方法,例如清晰直观的描述性统计

这里是最后一轮的代码完成笔记本。还有我答应过的视频…

感谢您的宝贵时间!如果你还有几秒钟,请分享。并在寻找最佳参数的过程中享受乐趣!

基于遗传算法的 XGBoost 超参数整定

原文:https://towardsdatascience.com/hyperparameter-tuning-in-xgboost-using-genetic-algorithm-17bd2e581b17?source=collection_archive---------9-----------------------

简介

维基百科中定义的遗传算法,其灵感来自于查尔斯·达尔文提出的自然选择过程。在更一般的术语中,我们可以理解自然过程以及它如何与遗传算法相关联,使用下面的描述:

我们从初始群体开始,它将具有某些特征,如图 1 所示。该初始群体将在特定环境中进行测试,以观察该群体中的个体(父母)基于预定义的适合度标准表现如何。在机器学习的情况下,适合度可以是任何性能度量——准确度、精确度、召回率、F1 分数、auc 等等。基于适应值,我们选择表现最好的父母(“适者生存”),作为幸存的群体(图 2)。

(Image by author)

(Image by author)

现在幸存群体中的父母将通过结合两个步骤来交配产生后代:交叉/重组和突变。在杂交的情况下,来自交配父母的基因(参数)将被重组,以产生后代,每个孩子从每个父母那里继承一些基因(参数)(图 3)。

(Image by author)

最后,在突变的情况下,基因(参数)的一些值将被改变以保持遗传多样性(图 4)。这使得自然/遗传算法通常能够得到更好的解决方案。

(Image by author)

图 5 显示了第二代人口,包括幸存的父母和孩子。我们保留幸存的双亲,以便保留最佳适应度参数,以防后代的适应度值不如双亲。

(Image by author)

遗传算法模块为XGBoost:

我们将创建一个为 XGBoost 定制的遗传算法模块。以下是 XGboost 的描述:

XGBoost 是一个优化的分布式梯度增强库,旨在高效灵活便携。它在梯度提升框架下实现机器学习算法。

该模块将具有遵循四个步骤的函数:(I)初始化,(ii)选择,(iii)交叉,和(iv)变异,类似于上面讨论的内容(该代码的一小部分灵感来自帖子这里)。

初始化:

第一步是初始化,参数被随机初始化以创建群体。它类似于图 1 所示的第一代人口。下面的代码显示了初始化过程,其中我们生成了一个包含参数的向量。对于 XGBoost,我们选择了 7 个参数进行优化:learning_rate、n_estimators、max_depth、min_child_weight、subsample、colsample_bytree 和 gamma。这些参数的详细描述可以在这里找到。

def initilialize_poplulation(numberOfParents):
    learningRate = np.empty([numberOfParents, 1])
    nEstimators = np.empty([numberOfParents, 1], dtype = np.uint8)
    maxDepth = np.empty([numberOfParents, 1], dtype = np.uint8)
    minChildWeight = np.empty([numberOfParents, 1])
    gammaValue = np.empty([numberOfParents, 1])
    subSample = np.empty([numberOfParents, 1])
    colSampleByTree =  np.empty([numberOfParents, 1])for i in range(numberOfParents):
        print(i)
        learningRate[i] = round(random.uniform(0.01, 1), 2)
        nEstimators[i] = random.randrange(10, 1500, step = 25)
        maxDepth[i] = int(random.randrange(1, 10, step= 1))
        minChildWeight[i] = round(random.uniform(0.01, 10.0), 2)
        gammaValue[i] = round(random.uniform(0.01, 10.0), 2)
        subSample[i] = round(random.uniform(0.01, 1.0), 2)
        colSampleByTree[i] = round(random.uniform(0.01, 1.0), 2)

    population = np.concatenate((learningRate, nEstimators, maxDepth, minChildWeight, gammaValue, subSample, colSampleByTree), axis= 1)
    return population

参数的限制要么基于 XGBoost 文档中描述的限制,要么基于合理的猜测(如果上限设置为无穷大)。我们首先为每个参数创建一个空数组,然后用随机值填充它。

亲代选择(适者生存)

在第二步中,我们使用初始群体训练我们的模型,并计算适应值。在这种情况下,我们将计算 F1 分数。

def fitness_f1score(y_true, y_pred):
    fitness = round((f1_score(y_true, y_pred, average='weighted')), 4)
    return fitness#train the data annd find fitness score
def train_population(population, dMatrixTrain, dMatrixtest, y_test):
    fScore = []
    for i in range(population.shape[0]):
        param = { 'objective':'binary:logistic',
              'learning_rate': population[i][0],
              'n_estimators': population[i][1], 
              'max_depth': int(population[i][2]), 
              'min_child_weight': population[i][3],
              'gamma': population[i][4], 
              'subsample': population[i][5],
              'colsample_bytree': population[i][6],
              'seed': 24}
        num_round = 100
        xgbT = xgb.train(param, dMatrixTrain, num_round)
        preds = xgbT.predict(dMatrixtest)
        preds = preds>0.5
        fScore.append(fitness_f1score(y_test, preds))
    return fScore

我们将定义我们想要选择多少个父节点,并根据它们的适合度值用所选择的父节点创建一个数组。

#select parents for mating
def new_parents_selection(population, fitness, numParents):
    selectedParents = np.empty((numParents, population.shape[1])) #create an array to store fittest parents

    #find the top best performing parents
    for parentId in range(numParents):
        bestFitnessId = np.where(fitness == np.max(fitness))
        bestFitnessId  = bestFitnessId[0][0]
        selectedParents[parentId, :] = population[bestFitnessId, :]
        fitness[bestFitnessId] = -1 #set this value to negative, in case of F1-score, so this parent is not selected again
    return selectedParents

交叉

遗传算法 ,)的情况下,有多种方法定义交叉,如单点、两点和 k 点交叉,均匀交叉和有序列表交叉。我们将使用均匀交叉,其中孩子的每个参数将基于某种分布从父母中独立选择。在我们的例子中,我们将使用来自 numpy 随机函数的“离散均匀”分布。

'''
Mate these parents to create children having parameters from these parents (we are using uniform crossover method)
'''
def crossover_uniform(parents, childrenSize):

    crossoverPointIndex = np.arange(0, np.uint8(childrenSize[1]), 1, dtype= np.uint8) #get all the index
    crossoverPointIndex1 = np.random.randint(0, np.uint8(childrenSize[1]), np.uint8(childrenSize[1]/2)) # select half  of the indexes randomly
    crossoverPointIndex2 = np.array(list(set(crossoverPointIndex) - set(crossoverPointIndex1))) #select leftover indexes

    children = np.empty(childrenSize)

    '''
    Create child by choosing parameters from two parents selected using new_parent_selection function. The parameter values
    will be picked from the indexes, which were randomly selected above. 
    '''
    for i in range(childrenSize[0]):

        #find parent 1 index 
        parent1_index = i%parents.shape[0]
        #find parent 2 index
        parent2_index = (i+1)%parents.shape[0]
        #insert parameters based on random selected indexes in parent 1
        children[i, crossoverPointIndex1] = parents[parent1_index, crossoverPointIndex1]
        #insert parameters based on random selected indexes in parent 1
        children[i, crossoverPointIndex2] = parents[parent2_index, crossoverPointIndex2]
    return children

突变

最后一步将是通过随机选择一个参数并以一个随机量改变它的值,在孩子中引入多样性。我们还将引入一些限制,以便将改变的值限制在一定的范围内。跳过这些约束可能会导致错误。

def mutation(crossover, numberOfParameters):
    #Define minimum and maximum values allowed for each parameterminMaxValue = np.zeros((numberOfParameters, 2))

    minMaxValue[0:] = [0.01, 1.0] #min/max learning rate
    minMaxValue[1, :] = [10, 2000] #min/max n_estimator
    minMaxValue[2, :] = [1, 15] #min/max depth
    minMaxValue[3, :] = [0, 10.0] #min/max child_weight
    minMaxValue[4, :] = [0.01, 10.0] #min/max gamma
    minMaxValue[5, :] = [0.01, 1.0] #min/maxsubsample
    minMaxValue[6, :] = [0.01, 1.0] #min/maxcolsample_bytree

    # Mutation changes a single gene in each offspring randomly.
    mutationValue = 0
    parameterSelect = np.random.randint(0, 7, 1)
    print(parameterSelect)
    if parameterSelect == 0: #learning_rate
        mutationValue = round(np.random.uniform(-0.5, 0.5), 2)
    if parameterSelect == 1: #n_estimators
        mutationValue = np.random.randint(-200, 200, 1)
    if parameterSelect == 2: #max_depth
        mutationValue = np.random.randint(-5, 5, 1)
    if parameterSelect == 3: #min_child_weight
        mutationValue = round(np.random.uniform(5, 5), 2)
    if parameterSelect == 4: #gamma
        mutationValue = round(np.random.uniform(-2, 2), 2)
    if parameterSelect == 5: #subsample
        mutationValue = round(np.random.uniform(-0.5, 0.5), 2)
    if parameterSelect == 6: #colsample
        mutationValue = round(np.random.uniform(-0.5, 0.5), 2)

    #indtroduce mutation by changing one parameter, and set to max or min if it goes out of range
    for idx in range(crossover.shape[0]):
        crossover[idx, parameterSelect] = crossover[idx, parameterSelect] + mutationValue
        if(crossover[idx, parameterSelect] > minMaxValue[parameterSelect, 1]):
            crossover[idx, parameterSelect] = minMaxValue[parameterSelect, 1]
        if(crossover[idx, parameterSelect] < minMaxValue[parameterSelect, 0]):
            crossover[idx, parameterSelect] = minMaxValue[parameterSelect, 0]    
    return crossover

实施

我们将实现上面讨论的模块,在数据集上进行训练。数据集来自 UCI 机器学习库。它包含一组 102 个分子,其中 39 个被人类识别为具有可用于香水的气味,69 个没有所需的气味。该数据集包含这些分子的 6,590 个低能构象,包含 166 个特征。我们正在做最少的前置处理,作为本教程理解遗传算法的目标。

# Importing the libraries
import numpy as np
import pandas as pd
import geneticXGboost #this is the module we crated above
import xgboost as xgbnp.random.seed(723)# Importing the dataset
dataset = pd.read_csv('clean2.data', header=None)X = dataset.iloc[:, 2:168].values #discard first two coloums as these are molecule's name and conformation's namey = dataset.iloc[:, 168].values #extrtact last coloum as class (1 => desired odor, 0 => undesired odor)# Splitting the dataset into the Training set and Test set
from sklearn.model_selection import train_test_split
X_train, X_test, y_train, y_test = train_test_split(X, y, test_size = 0.20, random_state = 97)# Feature Scaling
from sklearn.preprocessing import StandardScaler
sc = StandardScaler()
X_train = sc.fit_transform(X_train)
X_test = sc.transform(X_test)#XGboost Classifier#model xgboost
#use xgboost API now
xgDMatrix = xgb.DMatrix(X_train, y_train) #create Dmatrix
xgbDMatrixTest = xgb.DMatrix(X_test, y_test)

我们有 8 个父母开始,我们选择 4 个最合适的父母交配。我们将创建 4 代并监控适应度(F1 分数)。下一代中有一半的父母将是从上一代中选出的最适合的父母。这将允许我们保持最好的健康分数至少与上一代相同,以防孩子的健康分数更差。

numberOfParents = 8 #number of parents to start
numberOfParentsMating = 4 #number of parents that will mate
numberOfParameters = 7 #number of parameters that will be optimized
numberOfGenerations = 4 #number of genration that will be created#define the population sizepopulationSize = (numberOfParents, numberOfParameters)#initialize the population with randomly generated parameters
population = geneticXGboost.initilialize_poplulation(numberOfParents)#define an array to store the fitness  hitory
fitnessHistory = np.empty([numberOfGenerations+1, numberOfParents])#define an array to store the value of each parameter for each parent and generation
populationHistory = np.empty([(numberOfGenerations+1)*numberOfParents, numberOfParameters])#insert the value of initial parameters in history
populationHistory[0:numberOfParents, :] = populationfor generation in range(numberOfGenerations):
    print("This is number %s generation" % (generation))

    #train the dataset and obtain fitness
    fitnessValue = geneticXGboost.train_population(population=population, dMatrixTrain=xgDMatrix, dMatrixtest=xgbDMatrixTest, y_test=y_test)
    fitnessHistory[generation, :] = fitnessValue

    #best score in the current iteration
    print('Best F1 score in the this iteration = {}'.format(np.max(fitnessHistory[generation, :])))#survival of the fittest - take the top parents, based on the fitness value and number of parents needed to be selected
    parents = geneticXGboost.new_parents_selection(population=population, fitness=fitnessValue, numParents=numberOfParentsMating)

    #mate these parents to create children having parameters from these parents (we are using uniform crossover)
    children = geneticXGboost.crossover_uniform(parents=parents, childrenSize=(populationSize[0] - parents.shape[0], numberOfParameters))

    #add mutation to create genetic diversity
    children_mutated = geneticXGboost.mutation(children, numberOfParameters)

    '''
    We will create new population, which will contain parents that where selected previously based on the
    fitness score and rest of them  will be children
    '''
    population[0:parents.shape[0], :] = parents #fittest parents
    population[parents.shape[0]:, :] = children_mutated #children

    populationHistory[(generation+1)*numberOfParents : (generation+1)*numberOfParents+ numberOfParents , :] = population #srore parent information

最后,我们得到最佳分数和相关参数:

#Best solution from the final iterationfitness = geneticXGboost.train_population(population=population, dMatrixTrain=xgDMatrix, dMatrixtest=xgbDMatrixTest, y_test=y_test)
fitnessHistory[generation+1, :] = fitness#index of the best solution
bestFitnessIndex = np.where(fitness == np.max(fitness))[0][0]#Best fitness
print("Best fitness is =", fitness[bestFitnessIndex])#Best parameters
print("Best parameters are:")
print('learning_rate', population[bestFitnessIndex][0])
print('n_estimators', population[bestFitnessIndex][1])
print('max_depth', int(population[bestFitnessIndex][2])) 
print('min_child_weight', population[bestFitnessIndex][3])
print('gamma', population[bestFitnessIndex][4])
print('subsample', population[bestFitnessIndex][5])
print('colsample_bytree', population[bestFitnessIndex][6])

现在让我们想象一下每一代人在健康方面的变化(下图)。虽然我们已经从高 F1 分数(~0.98)开始,但在随机产生的初始群体中的两个亲本中,我们能够在最终一代中进一步改进它。初始群体中父母一方的最低 F1 值为 0.9143,最终世代中父母一方的最高 F1 值为 0.9947。这表明我们可以通过遗传算法的简单实现来改进 XGBoost 中的性能指标。最终代码可以在我的 github 账号找到。它还包含允许您观察每一代中各种参数的变化的代码。

(Image by author)

Python 中随机森林的超参数调优

原文:https://towardsdatascience.com/hyperparameter-tuning-the-random-forest-in-python-using-scikit-learn-28d2aa77dd74?source=collection_archive---------0-----------------------

改进随机森林第二部分

因此,我们建立了一个随机森林模型来解决我们的机器学习问题(也许通过遵循这个端到端指南),但我们对结果并不太满意。我们有什么选择?正如我们在这个系列的第一部分的中看到的,我们的第一步应该是收集更多的数据并执行特征工程。收集更多的数据和特征工程通常在投入的时间和提高的性能方面有最大的回报,但是当我们用尽所有数据源时,是时候继续进行模型超参数调整了。这篇文章将关注使用 Scikit-Learn 工具优化 Python 中的随机森林模型。虽然这篇文章建立在第一部分的基础上,但它完全独立,我们将涵盖许多广泛适用的机器学习概念。

One Tree in a Random Forest

我在本文中包含了 Python 代码,这是最有启发性的。完整的代码和数据可以在 Github 页面上找到。

超参数调谐的简要说明

思考超参数的最佳方式就像可以调整以优化性能的算法的设置,就像我们可能转动 AM 收音机的旋钮以获得清晰的信号一样(或者你的父母可能有!).虽然模型参数是在训练期间学习的,例如线性回归中的斜率和截距,但是超参数必须由数据科学家在训练之前设置。在随机森林的情况下,超参数包括森林中决策树的数量以及分割节点时每棵树考虑的特征的数量。(随机森林的参数是用于分割在训练期间学习的每个节点的变量和阈值)。Scikit-Learn 为所有模型实现了一组合理的默认超参数,但这些参数并不能保证对某个问题是最优的。最好的超参数通常不可能提前确定,而调整模型是机器学习从科学转向基于试错的工程的地方。

Hyperparameters and Parameters

超参数调整更多地依赖于实验结果而不是理论,因此确定最佳设置的最佳方法是尝试许多不同的组合来评估每个模型的性能。然而,仅在训练集上评估每个模型会导致机器学习中最基本的问题之一:过拟合

如果我们为训练数据优化模型,那么我们的模型将在训练集上得分很高,但是将不能推广到新数据,例如在测试集中。当一个模型在训练集上表现很好,但在测试集上表现很差时,这被称为过度拟合,或者本质上是创建一个非常了解训练集但不能应用于新问题的模型。这就像一个学生背了课本上的简单问题,却不知道如何在杂乱的现实世界中应用概念。

过度拟合模型在训练集上可能看起来令人印象深刻,但在实际应用中却毫无用处。因此,超参数优化的标准程序通过交叉验证解决过拟合问题。

交互效度分析

交叉验证(CV)技术最好用最常用的方法 K 倍 CV 举例说明。当我们处理机器学习问题时,我们确保将我们的数据分成训练集和测试集。在 K-Fold CV 中,我们进一步将我们的训练集分成 K 个子集,称为折叠。然后,我们迭代拟合模型 K 次,每次在第 K-1 个褶皱上训练数据,并在第 K 个褶皱上评估(称为验证数据)。例如,考虑拟合 K = 5 的模型。第一次迭代我们在前四次折叠上训练,在第五次折叠上评估。第二次我们在第一、第二、第三和第五次折叠时进行训练,在第四次折叠时进行评估。我们重复这个过程 3 次以上,每次评估不同的折叠。在训练的最后,我们对每个折叠的性能进行平均,以得出模型的最终验证指标。

5 Fold Cross Validation (Source)

对于超参数调整,我们对整个 K-Fold CV 过程进行多次迭代,每次都使用不同的模型设置。然后,我们比较所有的模型,选择最好的一个,在完整的训练集上训练它,然后在测试集上进行评估。这听起来是一个非常乏味的过程!每当我们想要评估一组不同的超参数时,我们必须将我们的训练数据分成 K 份,并训练和评估 K 次。如果我们有 10 组超参数,并且使用 5 重 CV,则代表 50 个训练循环。幸运的是,与机器学习中的大多数问题一样,有人已经解决了我们的问题,并且可以在 Scikit-Learn 中自动实现 K-Fold CV 的模型调整。

Scikit-Learn 中的随机搜索交叉验证

通常,我们对最佳超参数只有一个模糊的概念,因此缩小搜索范围的最佳方法是评估每个超参数的大范围值。使用 Scikit-Learn 的 RandomizedSearchCV 方法,我们可以定义一个超参数范围网格,并从网格中随机采样,对每个值组合执行 K 倍 CV。

在我们进入模型调整之前,简单回顾一下,我们正在处理一个监督回归机器学习问题。我们试图使用过去的历史天气数据来预测我们城市(华盛顿州西雅图市)明天的温度。我们有 4.5 年的训练数据,1.5 年的测试数据,并使用 6 个不同的特征(变量)来进行预测。(要查看数据准备的完整代码,请参见笔记本)。

让我们快速检查一下特性。

Features for Temperature Prediction

  • temp_1 =前一天的最高温度(华氏度)
  • 平均值=历史平均最高温度
  • ws_1 =前一天的平均风速
  • temp_2 =两天前的最高温度
  • 朋友=来自我们“信任的”朋友的预测
  • 年份=日历年

在以前的帖子中,我们检查了数据以检查异常,我们知道我们的数据是干净的。因此,我们可以跳过数据清理,直接进入超参数调优。

为了查看可用的超参数,我们可以创建一个随机森林并检查默认值。

from sklearn.ensemble import RandomForestRegressorrf = RandomForestRegressor(random_state = 42)from pprint import pprint# Look at parameters used by our current forest
print('Parameters currently in use:\n')
pprint(rf.get_params())**Parameters currently in use:

{'bootstrap': True,
 'criterion': 'mse',
 'max_depth': None,
 'max_features': 'auto',
 'max_leaf_nodes': None,
 'min_impurity_decrease': 0.0,
 'min_impurity_split': None,
 'min_samples_leaf': 1,
 'min_samples_split': 2,
 'min_weight_fraction_leaf': 0.0,
 'n_estimators': 10,
 'n_jobs': 1,
 'oob_score': False,
 'random_state': 42,
 'verbose': 0,
 'warm_start': False}**

哇,这是一个相当压倒性的名单!我们如何知道从哪里开始?一个好地方是 Scikit-Learn 中关于随机森林的文档。这告诉我们最重要的设置是森林中的树的数量(n_estimators)和考虑在每个叶节点进行分裂的特征的数量(max_features)。我们可以去阅读关于随机森林的研究论文,并尝试将最佳超参数理论化,但更有效地利用我们的时间只是尝试各种各样的值,看看什么有效!我们将尝试调整以下一组超参数:

  • n_estimators =前集中的树的数量
  • max_features =分割结点时考虑的最大要素数
  • max_depth =每个决策树中的最大级别数
  • min_samples_split =分割节点前放置在节点中的最小数据点数
  • min_samples_leaf =叶节点中允许的最小数据点数
  • bootstrap =数据点采样方法(有或没有替换)

随机超参数网格

要使用 RandomizedSearchCV,我们首先需要创建一个参数网格,以便在拟合过程中进行采样:

from sklearn.model_selection import RandomizedSearchCV# Number of trees in random forest
n_estimators = [int(x) for x in np.linspace(start = 200, stop = 2000, num = 10)]
# Number of features to consider at every split
max_features = ['auto', 'sqrt']
# Maximum number of levels in tree
max_depth = [int(x) for x in np.linspace(10, 110, num = 11)]
max_depth.append(None)
# Minimum number of samples required to split a node
min_samples_split = [2, 5, 10]
# Minimum number of samples required at each leaf node
min_samples_leaf = [1, 2, 4]
# Method of selecting samples for training each tree
bootstrap = [True, False]# Create the random grid
random_grid = {'n_estimators': n_estimators,
               'max_features': max_features,
               'max_depth': max_depth,
               'min_samples_split': min_samples_split,
               'min_samples_leaf': min_samples_leaf,
               'bootstrap': bootstrap}pprint(random_grid)**{'bootstrap': [True, False],
 'max_depth': [10, 20, 30, 40, 50, 60, 70, 80, 90, 100, None],
 'max_features': ['auto', 'sqrt'],
 'min_samples_leaf': [1, 2, 4],
 'min_samples_split': [2, 5, 10],
 'n_estimators': [200, 400, 600, 800, 1000, 1200, 1400, 1600, 1800, 2000]}**

在每次迭代中,算法将选择特征的不同组合。总共有 2 * 12 * 2 * 3 * 3 * 10 = 4320 个设置!然而,随机搜索的好处是,我们不是在尝试每一种组合,而是随机选择大范围的值进行采样。

随机搜索训练

现在,我们实例化随机搜索,并像任何 Scikit-Learn 模型一样拟合它:

# Use the random grid to search for best hyperparameters
# First create the base model to tune
rf = RandomForestRegressor()
# Random search of parameters, using 3 fold cross validation, 
# search across 100 different combinations, and use all available cores
rf_random = RandomizedSearchCV(estimator = rf, param_distributions = random_grid, n_iter = 100, cv = 3, verbose=2, random_state=42, n_jobs = -1)# Fit the random search model
rf_random.fit(train_features, train_labels)

RandomizedSearchCV 中最重要的参数是 n_iter,它控制要尝试的不同组合的数量,以及 CV,它是用于交叉验证的折叠数(我们分别使用 100 和 3)。更多的迭代将覆盖更宽的搜索空间,更多的 cv 折叠将减少过度拟合的机会,但提高每个将增加运行时间。机器学习是一个需要权衡的领域,性能与时间是最基本的因素之一。

我们可以通过拟合随机搜索来查看最佳参数:

rf_random.best_params_**{'bootstrap': True,
 'max_depth': 70,
 'max_features': 'auto',
 'min_samples_leaf': 4,
 'min_samples_split': 10,
 'n_estimators': 400}**

根据这些结果,我们应该能够缩小每个超参数的取值范围。

评估随机搜索

为了确定随机搜索是否产生了更好的模型,我们将基础模型与最佳随机搜索模型进行比较。

def evaluate(model, test_features, test_labels):
    predictions = model.predict(test_features)
    errors = abs(predictions - test_labels)
    mape = 100 * np.mean(errors / test_labels)
    accuracy = 100 - mape
    print('Model Performance')
    print('Average Error: {:0.4f} degrees.'.format(np.mean(errors)))
    print('Accuracy = {:0.2f}%.'.format(accuracy))

    return accuracybase_model = RandomForestRegressor(n_estimators = 10, random_state = 42)
base_model.fit(train_features, train_labels)
base_accuracy = evaluate(base_model, test_features, test_labels)**Model Performance
Average Error: 3.9199 degrees.
Accuracy = 93.36%.**best_random = rf_random.best_estimator_
random_accuracy = evaluate(best_random, test_features, test_labels)**Model Performance
Average Error: 3.7152 degrees.
Accuracy = 93.73%.**print('Improvement of {:0.2f}%.'.format( 100 * (random_accuracy - base_accuracy) / base_accuracy))**Improvement of 0.40%.**

我们取得了 0.4%的不引人注目的精度改进。不过,根据应用程序的不同,这可能是一个显著的优势。我们可以通过使用网格搜索来集中在随机搜索中找到的最有希望的超参数范围上,从而进一步改进我们的结果。

交叉验证网格搜索

随机搜索允许我们缩小每个超参数的范围。既然我们知道了集中搜索的位置,我们就可以显式地指定要尝试的每种设置组合。我们使用 GridSearchCV 来完成这项工作,这种方法不是从分布中随机抽样,而是评估我们定义的所有组合。要使用网格搜索,我们根据随机搜索提供的最佳值制作另一个网格:

from sklearn.model_selection import GridSearchCV# Create the parameter grid based on the results of random search 
param_grid = {
    'bootstrap': [True],
    'max_depth': [80, 90, 100, 110],
    'max_features': [2, 3],
    'min_samples_leaf': [3, 4, 5],
    'min_samples_split': [8, 10, 12],
    'n_estimators': [100, 200, 300, 1000]
}# Create a based model
rf = RandomForestRegressor()# Instantiate the grid search model
grid_search = GridSearchCV(estimator = rf, param_grid = param_grid, 
                          cv = 3, n_jobs = -1, verbose = 2)

这将尝试 1 * 4 * 2 * 3 * 3 * 4 = 288 种设置组合。我们可以拟合模型,显示最佳超参数,并评估性能:

# Fit the grid search to the data
grid_search.fit(train_features, train_labels)grid_search.best_params_**{'bootstrap': True,
 'max_depth': 80,
 'max_features': 3,
 'min_samples_leaf': 5,
 'min_samples_split': 12,
 'n_estimators': 100}**best_grid = grid_search.best_estimator_
grid_accuracy = evaluate(best_grid, test_features, test_labels)**Model Performance
Average Error: 3.6561 degrees.
Accuracy = 93.83%.**print('Improvement of {:0.2f}%.'.format( 100 * (grid_accuracy - base_accuracy) / base_accuracy))**Improvement of 0.50%.**

看起来我们已经达到了最大的性能,但是我们可以从之前的结果中进一步细化网格,再试一次。代码和以前一样,只是网格不同,所以我只给出结果:

**Model Performance
Average Error: 3.6602 degrees.
Accuracy = 93.82%.****Improvement of 0.49%.**

性能的小幅下降表明我们已经达到了超参数调优的收益递减。我们可以继续,但回报最多也是微乎其微。

比较

我们可以对用于提高性能的不同方法进行一些快速比较,显示每种方法的回报。下表显示了我们所做的所有改进的最终结果(包括第一部分的改进):

Comparison of All Models

Model 是模型的(非常缺乏想象力的)名称,accuracy 是百分比精度,error 是以度为单位的平均绝对误差,n_features 是数据集中的要素数,n_trees 是森林中决策树的数量,time 是以秒为单位的训练和预测时间。

这些模型如下:

  • 平均值:通过预测测试集中每天的历史平均最高温度来计算原始基线
  • 一年:使用一年的数据训练的模型
  • four_years_all:使用 4.5 年的数据和扩展特征训练的模型(详见第一部分)
  • four_years_red:使用 4.5 年的数据和最重要特征的子集训练的模型
  • best_random:交叉验证随机搜索的最佳模型
  • first_grid:交叉验证的第一次网格搜索的最佳模型(被选为最终模型)
  • second_grid:第二次网格搜索的最佳模型

总体而言,收集更多的数据和特征选择将误差降低了 17.69%,而超参数进一步将误差降低了 6.73%。

Model Comparison (see Notebook for code)

就程序员工时而言,收集数据需要大约 6 个小时,而超参数调优需要大约 3 个小时。就像生活中的任何追求一样,在某个点上追求进一步的优化是不值得努力的,知道什么时候停止和能够继续下去一样重要(抱歉,变得如此哲学化)。此外,在任何数据问题中,都有所谓的贝叶斯错误率,这是一个问题中绝对最小的可能错误。贝叶斯误差,也称为可再现误差,是潜在变量、影响我们无法测量的问题的因素以及任何物理过程中的固有噪声的组合。因此,创造一个完美的模型是不可能的。尽管如此,在这个例子中,我们能够通过超参数调整显著改进我们的模型,并且我们涵盖了许多广泛适用的机器学习主题。

训练可视化

为了进一步分析超参数优化的过程,我们可以一次更改一个设置,并查看对模型性能的影响(本质上是进行一个受控实验)。例如,我们可以创建一个包含一定数量的树的网格,执行网格搜索 CV,然后绘制结果。绘制训练和测试误差以及训练时间将允许我们检查改变一个超参数如何影响模型。

首先,我们可以看看改变森林中树木数量的影响。(有关训练和绘图代码,请参见笔记本)

Number of Trees Training Curves

随着树的数量增加,我们的误差减少到一定程度。将树的数量增加到超过 20(我们的最终模型有 100)在准确性方面没有太大的好处,并且训练时间持续增加。

我们还可以检查分割节点的特征数量曲线:

Number of Features Training Curves

随着保留的特征数量的增加,模型的准确性也如预期的那样增加。训练时间也增加了,尽管并不显著。

结合定量统计,这些视觉效果可以让我们很好地了解我们使用不同超参数组合所做的权衡。虽然通常没有办法提前知道什么设置会工作得最好,但这个例子展示了 Python 中的简单工具,这些工具允许我们优化我们的机器学习模型。

一如既往,我欢迎反馈和建设性的批评。可以在 wjk68@case.edu 找到我

调谐超参数(二):火花的随机搜索

原文:https://towardsdatascience.com/hyperparameters-part-ii-random-search-on-spark-77667e68b606?source=collection_archive---------4-----------------------

在本系列的第二部分中,我将继续我的超参数优化策略,这一次我想从 Spark 的角度更仔细地看看。该系列的每个部分都可以单独阅读,请随意查看第一部分

随机搜索和分布式机器学习框架

不管你的算法设计得多好,数学可能有多美,如果客户需要在大量数据上相对较短的训练时间,你最好找到一种方法来提供!

幸运的是,分布式计算是随机搜索果冻的花生酱。让我们提醒一下为什么随机搜索网格搜索效率高?

最大的敌人是维度的诅咒。对于附加的超参数,以及它们各自选择的值,会成倍增加搜索时间。与其固定搜索空间的值,还不如对其进行采样。为了理解这一点,让我们看一下图 1。摘自原文

Figure 1: Grid Search vs Random Search

正如我们所见,在搜索中经常出现的情况,一些超参数比其他的更具决定性。在网格搜索的情况下,尽管采样了 9 次试验,实际上我们只试验了一个重要参数的 3 个不同值。在随机搜索的情况下,9 次试验将测试 9 个不同的决定性参数值。

因为超参数配置的每个样本都是彼此独立绘制的,所以我们可以看到并行化是多么容易!于是,火花来了!

火花

Spark 是一个流行的开源框架,用于在集群上进行分布式计算,提供了一个广泛的库,用于操作数据库、流、分布式图形处理,最重要的是本讨论中的机器学习,即 Spark MLlib。

由于微软 Azure 机器学习团队的工作,Spark MLlib 最近获得了巨大的推动,该团队发布了 MMLSpark 。从实用机器学习的角度来看,MMLSpark 最显著的功能是访问极端梯度增强库 Lighgbm ,这是大多数数据科学概念证明的快速制胜方法。

既然每个数据科学家最喜欢的库都可以在集群上训练,我们只差一个合适的超参数调整框架了。遗憾的是,最初的 Spark MLlib 只有一个网格搜索的实现。MMLSpark 提供了带随机搜索的超调,但遗憾的是采样只有统一

实际上…

均匀采样是一个很好的步骤,但对于许多超参数来说不是最佳的。在 Lightgbm 等极端梯度推进算法的情况下,学习率和正则化超参数浮现在脑海中。这些参数应该在对数尺度上采样,而不是在一个间隔内均匀采样。

那么我们如何黑 Spark MLlib 来满足我们的需求呢?

下面让我们先来看看 Spark 中的关键成分。

正如我们所看到的,超参数值的网格被定义为 ParamMap 类型的数组,来自 ParamGridBuilder 类的一个实例。因此,为了保持与 Spark 的 CrossValidator 兼容,让我们继续并重新定义 build()addGrid 方法。

我们不是在网格中添加一个超参数值列表,而是定义一个分布,稍后我们将从该分布中抽取配置样本。

Breeze是一个流行的用于数值处理的 scala 库,在 breeze.stats.distributions 中有各种各样的分布。
例如,在逻辑回归的情况下,我们可能希望定义以下采样空间:****

一方面,我们希望从分布中取样,另一方面,在一组分类选择的情况下,我们应该能够设置一组选择。

我们可以提出以下解决方案,

现在让我们对 LightGBM 进行最后一次测试,

我们走吧!

更多例子的代码可以在 这里 找到。

我写了更多精彩的东西!

@ 调整超参数(第一部分):成功减半

@tensor flow 中的自定义优化器

@XG boost 回归预测区间

参考资料:

  1. J.Bergstra 和 Y. Bengio,超参数优化的随机搜索,2011 年
  2. https://spark.apache.org/星火
  3. https://github.com/Azure/mmlspark
  4. 微风,https://github.com/scalanlp/breeze
  5. J.Bergstra,R. Bardenet,Y. Bengio,B. Kégl,超参数优化算法
  6. github:https://github.com/benoitdescamps/Hyperparameters-tuning

永远不要从假设开始

原文:https://towardsdatascience.com/hypothesis-testing-decoded-for-movers-and-shakers-bfc2bc34da41?source=collection_archive---------2-----------------------

谎言,该死的谎言,还有 STAT101

设置假设检验是交际舞;它的步骤是动作-动作-世界-世界。有很好的狐步舞节奏。不幸的是,大多数人一开始就搞砸了。以下是如何正确地跳舞。

第一步:写下默认动作

统计学是一门在不确定的情况下改变你想法的科学,所以首要任务是弄清楚你要做什么除非数据说服你放弃。

如果你保持无知,你会做什么?

这就是为什么一切都从一个身体动作/决定开始,如果你没有收集到任何(更多)证据,你就承诺去做。这叫做你的 默认动作

入门是行动,而不是信念。

我问你的是,“如果你走开并且对这些信息一无所知,你实际上会做什么

**“收集数据”不是一个合适的答案。我在敦促你告诉我,如果我现在强迫你选择,你会选择哪个选项。(抱歉我吼了。)

第二步:写下可供选择的行动

你将保持你的决定二元,被框定为做事情不做事情。哪个不是你默认的就是你的 替代动作

If binary feels too basic, the amazing variety of shapes on your screen speaks volumes of the power of binary options put together. When you need to make a more complex decision, you can compound several hypothesis tests. Let’s start with one at a time.

第一部分不是关于信仰

入门是行动,而不是信念。我不是问你你认为你知道什么,因为作为一个好的常客(又名经典统计学家,大多数 STAT101 课程中教授的哲学的追随者)你在做分析之前不会相信任何事情。

没什么。你什么都不相信。和我一起说。

当谈到这一点时,贝叶斯主义者是不同的,但如果你感到正义的贝叶斯愤怒,因为你在哲学上与这里的逻辑不一致,深呼吸,把这当成了解你的敌人的一课。我们很快就会谈到贝叶斯生活方式。

目前,关于您正在处理哪种统计数据的线索是在行话中流传的。如果你听到“ 置信区间 ”或“ p 值 ”,你好常客。如果你听到“ 可信区间 ”或者“事前”或者“事后”(这不是什么无礼的话,我保证),你好贝叶斯。如果第一种更熟悉,那是因为大多数教育项目在教授贝叶斯思维之前/而不是贝叶斯思维。

处理无信息

对于数字迷来说,选择哪个动作作为你的默认动作并不是一个问题。这是 MBA 的事情,是团队决策者的职权范围。你是在密室里沉思的时候根据商业意识做出这个决定的。

选择默认操作需要商业头脑,这是团队决策者的职责。

我在问你,如果你保持无知,你更愿意做什么,所以你不需要数据来回答我的问题,尽管你可能会发现之前的分析鼓舞人心探索性数据分析 (EDA)是一种引导式冥想,如果你愿意的话。这是帮助决策者通过这一部分的工具。如果你想更深入地了解分析师和决策者是如何合作的,请阅读这篇文章。**

EDA 非常有用…如果你买得起的话。价格是你使用的所有数据,因为在你进入统计部分之前,它必须从轨道被核化。对于没有足够数据的团队来说,从推论中排除任何数据都是非常昂贵的。他们完全受他们的决策者的智力广度和头脑风暴能力的支配。

谨慎行事

想象一个关于推出新产品的决策。决策者中典型的选择是稳扎稳打: 不要启动 it,除非数据给你一个充分的理由按下绿色按钮。如果你没有数据,你会高兴地封存这个项目。也许这是一个错误,但是嘿——你可以心安理得。你选择了默认的方式,使得坚持它是错误中较小的一种。

默认的行动是你在无知下觉得合意的选项。

其他社会认为默认相当明显的例子有无罪-直到被证明有罪(默认=如果没有证据就不定罪),测试新药物(默认=如果没有证据就不批准),以及科学发表(默认=如果没有证据就不发表)。

如果没有默认,就不需要花里胡哨的统计。

虽然真正的冷漠在人类动物中相当罕见,但如果你真的愿意在没有数据的情况下抛硬币,那么你就不需要统计。如果你的想法没定下来,那是无法改变的。往前走,改为读这个。统计推断是针对 不确定性 下的决策。如果你已经有了答案,回家吧。

坦率地说,第一步包括在没有任何信息的情况下框定你的决定,我希望你看到决策者的培训比数学家的培训更相关。

处理全部信息

舞蹈的下一步有点奇怪。STAT101 教你,就像它不是一件小事,但它是一个非常激烈的精神飞跃。你的工作是想象世界上所有可能的状态。是的,你听到了。

这是最艰难的决策任务之一。对于非琐碎的例子(比你在课堂上看到的婴儿例子稍微复杂一点的东西),要做好它确实需要大量的精神训练、创造力、灵活性和专注力。

你的工作是想象世界上所有可能的状态。

一旦你想象了所有可能的平行世界,是时候把它们放入两个桶中的一个了:让我们称桶 1 为“我乐意采取默认行动的世界”,桶 2 为“所有其他的世界”

步骤 3:描述零假设(H0)

如果你不喜欢 Bucket 1 的 10 字名称,它的技术名称是 空假设

统计课教你检验 T21 假设,而不是形成假设。它们往往是在那些考试中为你预先准备好的。

你可能听过对零假设的简略描述,比如“现状”、“无聊的那个”或者“我们不想证明的东西”所有这些都是微妙的不准确,懒惰的事情,一个教授可能会教一个一年级的大学生不值得信赖的心智成熟。但是我相信 能够处理哲学上的古怪,所以现在你知道零假设描述了你乐意选择默认行为的所有宇宙。出于对我们要求决策者处理的心理体操的尊重,让我们默哀片刻。

不是每个人都有缩小视野所需的心理灵活性。明智地选择你的决策者。

让我们快速回顾一下我们的现状。这里的要点是,你已经设置好了事情,所以只要你什么都不知道,你只知道一点点,或者你绝对确定你是一个零假设宇宙的公民,你就致力于做你的默认动作。

假说就像蟑螂。当你看到一个,它永远不会只是一个。附近总有更多的藏身之处。

第四步:描述备选假设(H1)

桶 2 是 的替代假设 你把所有的剩菜都放在那里。当空值为假时,一切都可能为真。这两个假设是数学上的补充,也就是说没有第三个桶。

简而言之,另一个假设就是你对此的答案:

“怎样才能改变你的想法?”

Action (default) -action-worlds-worlds: the dance is complete.

我们已经准备好添加数据,那么接下来要做什么呢?

改变你想法的科学

在它们之间,你的假设涵盖了所有的可能性。它们不重叠。如果我用数据说服你!—你生活在另一个假设世界中……我的天啊,你还在考虑默认动作做什么?停下来。这不是一个快乐的选择。

如果数据让你相信你生活在另一个假设的世界里,那就改变行动。

你最好将默认动作切换到 替代动作 :不做默认。这可能会演变成一系列其他决定,但有一件事是肯定的:你不会碰上违约。数据改变了你的想法!**

主动与被动

这个决策背景的很大一部分是,从一开始,行动对你来说就是 而不是 一样。你像一个常客应该的那样完全开放,但这并不意味着你不认为无知下的某个行为更明智或更道德。这是关键。如果这两个动作对你来说是一样的,读这个代替。

默认行为是你被动接受的行为,而另一种行为是你需要被主动说服去做的事情。

处理部分信息

如果你对你的数据只有部分的了解,你将不得不处理不确定性。这就是花里胡哨的概率计算的用武之地。它们可以归结为一句话,每次都是一样的,我们将在下一章的中看到。

关键是你永远也不会确定哪个世界是你的世界。这就是为什么选择正确反映你价值观的默认行为是很重要的。怎么查?如果你把事情框对了,一个类型 I 错误应该比一个类型 II 错误感觉更糟。换句话说:

错误地离开你舒适的舒适区(默认动作)的想法应该比错误地坚持它的想法更痛苦。

如果这不是真的,那你就没有真正诚实地面对自己。让我们从头再来一遍!

没有魔法能把不确定性变成确定性。

行动最响亮

为了能够建立统计假设,你必须知道你的默认动作是什么。当你从别处开始时,整个事情就会分崩离析。

不幸的是,错误地选择你的默认动作是那些学习数学却没有吸收任何哲学的人的常见错误。这也是一个团队的症状,在这个团队中,决策者在行动中失踪,而数字书呆子们集体出局。

错误地选择默认动作是一个令人痛苦的常见错误。到处都是!

一个让自己注定失败的方法是从假设开始,而不是从行动开始。这是课堂练习结构的遗留问题(因为统计课不会教你决策者的角色,这些事情几乎总是由教授为你做的),但在现实生活中,这相当于出师不利。你将在剩下的时间里投入所有的努力,如果 faceplant 刚出大门,岂不是很可惜?

总是从默认操作开始。

如果你渴望这些例子形式的想法(和外星人!),这里读上。****

如果你更喜欢一个没有统计细微差别的基本例子,读读 这个

Don’t faceplant right out of the gate by starting with the hypotheses, always start with the default action.

感谢阅读!喜欢作者?

如果你渴望阅读更多我的作品,这篇文章中的大部分链接会带你去我的其他思考。不能选择?试试这个:

** [## 我们为什么信任科学家?

现在是时候重新思考我们对事实和虚构的假设了

blog.usejournal.com](https://blog.usejournal.com/why-do-we-trust-scientists-98c24e3b9f0e)

比起读书更喜欢 YouTube?试试我的 AI 课程!

如果你在这里玩得开心,并且你正在寻找一个为初学者和专家设计的有趣的应用人工智能课程,这里有一个我为你制作的娱乐课程:

Enjoy the entire course playlist here: bit.ly/machinefriend

喜欢作者?与凯西·科兹尔科夫联系

让我们做朋友吧!你可以在 TwitterYouTubeSubstackLinkedIn 上找到我。有兴趣让我在你的活动上发言吗?用这个表格联系。**

现实生活中的假设检验

原文:https://towardsdatascience.com/hypothesis-testing-in-real-life-47f42420b1f7?source=collection_archive---------0-----------------------

用数学解决现实世界的问题

Photo by JESHOOTS.COM on Unsplash

每天你都在测试想法、食谱、新路线,这样你就可以更快或更少的交通到达目的地…

然而,重要的问题是这个想法/配方/路线比你之前的那个好吗?

现在是星期五晚上,你想看电影。有三部电影吸引了你的眼球,但你并不确定它们是好是坏。

在当今这个时代,你是那种仍然依赖家人和朋友推荐的人。所以,你让他们给这些电影评级,并准备好处理数据。

The beauty of dummy data 😀

即使看起来你的朋友对表情电影有点怀疑,你也需要检查每个评分分布,以便更多地了解你朋友投票的主要趋势。

收视率为星际**

评分为的表情符号电影**

  • 2 个单位的中位数;
  • 平均值约为 2.2 个单位;
  • 标准偏差约为 0.59 个单位;

《星球大战:最后的绝地武士》的收视率

  • 5 个单位的中位数;
  • 平均值约为 4.5 个单位;
  • 标准偏差约为 0.62 个单位;

这太棒了!但实际上它并没有告诉你比你已经知道的更多的东西:表情符号电影可能没有那么吸引人,星际大战和星球大战之间有明显的竞争…

为了弄清你的朋友对哪部电影评价最高,你决定进行一些 统计测试 并比较三种评价分布。

假设检验

假设检验,或称统计假设检验,是一种用于比较两个数据集或数据集样本的技术。这是一种统计 推断方法所以,在测试的最后,你会得出一个结论——你会推断出一些东西——关于你正在比较的东西的特征。

就你周五晚上的电影选择而言,你想从三种可能中挑选一部最佳电影。

你应该使用哪种测试?

为了回答这个问题,首先你需要知道遵循什么分布。因为,不同的测试假设数据遵循特定的分布。

您已经计算了一些统计数据——评级数据——均值、中值和标准差——但是您的数据是什么样的呢?

最著名的分布之一就是所谓的钟形曲线正态分布 。在此分布中,数据以平均值为中心,您可以通过钟形曲线的峰值来识别该平均值。在这种情况下,它也对应于中间的值,即中值。

根据标准偏差,正态分布的数据点分布在平均值/中值周围。

Example of a dataset that follows a Normal Distribution with mean 0 and standard deviation of 1

在这个正态分布的例子中,很容易看到大多数值都以零为中心,即分布的平均值和中值,并且曲线的两侧以 1 个单位的增量从平均值向外移动。

电影收视率服从正态分布吗?

令人欣慰的是,统计学家已经考虑过识别你的数据的形状。他们创造了一个简单的方法来找出答案:分位数-分位数图,也叫 Q-Q 图。

A dataset that follows a Normal Distribution and the Q-Q plot that compares it with the Normal Distribution

Q-Q 图有助于可视化两个概率分布的分位数。分位数只是一种简单的方式来说明你正在把分布分成相等的部分。例如 quart iles,将分配分成四等份,4 等份。

这个 Q-Q 剧情怎么看?

在上面的例子中,我们已经知道数据集遵循正态分布。

Q-Q 图想要直观地表示的是,如果两个数据集遵循相同的分布,它们将大致沿着红色对角线对齐。对应于数据集的蓝点偏离对角线越多,对应于要比较的分布,两个分布之间的差异就越大。

因此,为了弄清楚每个电影评级数据集遵循什么样的分布,您可以使用 Q-Q 图将它们与正态分布进行比较。

Distribution of each movie rating and corresponding Q-Q plot vs Normal Distribution

第一个想到的可能是这看起来一点都不像我期待的 Q-Q 剧情!嗯,算是吧。**

数据点沿着对角线分布,但是,它不完全沿着红线的原因是因为评级是离散值,而不是连续值。这就是为什么我们看到,例如,在《星球大战》的评级中,一些蓝点与值 4 水平对齐,在红线的顶部,然后,再往上,一些点与值 5 对齐。

因此,您可以证明它遵循正态分布,因为,尽管是以离散的、逐步的方式,数据遵循对角线。

既然您已经发现您的评级遵循正态分布,那么是时候进行统计测试了。

还没有。

在考虑使用什么测试之前,你需要

  1. 定义你的假设;
  2. 设置统计测试的显著性水平。

那你挑统计测试就好了!

1.定义你的假设

假设检验通常由以下部分组成

  • 零假设 (H0,读作“H 零”):陈述所有事物保持不变。没有现象被观察到,或者在你比较的事物之间没有关系;
  • 替代假设 (H1,读“H one”):陈述零假设的反面。你所比较的事物之间有一些变化或观察到的关系

对于你周五的电影之夜,你真正想知道的是一部电影是否明显比其他的好。在这种情况下,你可以根据你的朋友对每部电影的平均评价来建立你的假设。

可以解读为零假设* (H0): 电影 A 的均值等于电影 B 的均值替代假设 (H1): 电影 A 的均值不等于电影 B 的均值*

2.设置统计测试的显著性水平

统计测试的目标是试图证明存在一个可观察到的现象。

统计测试的目标是试图拒绝零假设,即没有可观察到的变化或行为

它可能是证明显示患者健康改善的治疗、具有较大人群特征的样本或被认为不同的两个数据集,即它们不可能来自同一人群。所以,在测试的最后,你要有信心拒绝零假设。

这导致定义测试的显著性水平。

它被描述为一种概率,用希腊字母 alpha 表示,它指定了当零假设实际上为真时拒绝零假设的概率,即,您无法观察到问题中的现象或变化。

我认为显著性水平是为你的测试设定质量标准,以便能够得出准确的结论。

在你周五晚上寻找电影的过程中,没有找到一部好电影看的后果很小:一些潜在的浪费时间,和一点挫败感。但是,您可以看到在临床试验等场景中设置适当的显著性水平的重要性,在这些场景中,您正在测试一种新药或治疗方法。

通常使用的显著性水平是 1%和 5%。

对于这个电影夜选,我们可以定在 5%,即α= 0.05。

用什么统计检验?

知道数据遵循正态分布,并且您想要比较您朋友的评分平均值,一个特殊的统计测试浮现在脑海中。

学生的 t-Test

这种统计检验通常用于验证两个数据集之间是否存在显著差异。正如我前面提到的,首先您必须保证两个数据集都具有以下特征

  • 遵循正态分布;
  • 是相互独立的。

让我们假设你的朋友在给每部电影评分时没有偏见,以便给予完全独立的评分。

从我们到目前为止所看到的,你很好地使用学生的 t 测试!

为了验证其中一部电影是否明显优于另一部,你可以进行一个独立双样本 t 检验。这个测试也必须是一个双尾测试,因为我们试图捕捉一个普遍的显著差异,或者更低或者更高。想想正态分布图的“尾部”。

准备好运行 t 测试了吗?等等,还没有!

您所有的朋友对不同的电影进行了评级,但是,正如您之前所验证的,每部电影的评级分布都有不同的标准差。这意味着每个分布都有不同的方差。

因为分布的方差是不一样的,你必须使用一个稍微不同的测试,韦尔奇的 t-测试。

韦尔奇 t 检验

这也被称为不等方差 t 检验。这是对学生 t 检验的一种改进,仍然要求数据呈正态分布。但是,在计算测试时,它会考虑这两个差异。

分子考虑了两个均值之间的差异,由 X1 和 X2 表示,而分母考虑了方差,由 s 和每个数据集的大小 N 表示。

在周五晚上的电影示例中,两部电影的数据集大小将是相同的,因为你所有的朋友都对这三部电影进行了评级。但是通过 Welch 的 t-test,我们确保在验证评级之间是否存在显著差异时,每个评级分布的方差都被考虑在内。

使用 Welch 的 t-Test,对于每一对分布中的每一个,您计算出测试统计量,它是每个统计软件在您运行测试时生成的。

现在,显著性水平又回到了行动上,因为您已经准备好对数据做出结论了。

除了测试统计数据,您选择的软件还将为您提供 p 值。p 值也表示为概率,是在假设零假设为真的情况下,观察到与检验统计值一样极端的值的概率。

在这个周五电影之夜的场景中,p 值将是平均评分比我们比较的评分高或低的概率。

你现在有了拼图的所有部分!

您运行了测试,获得了测试统计数据和 p 值,现在您可以使用 p 值和显著性水平来确定数据集之间是否存在统计显著性差异。

用你选择的统计软件处理所有数据,你会得到以下结果

星际大战表情符号电影

  • 检验统计~= 15.07
  • p 值= 1.833202972237421e-25

表情符号电影 vs 星球大战:最后的绝地

  • 检验统计~= -18.54
  • p 值= 3.4074007278724943e-32

看看上面测试统计的绝对值,考虑到它们是如此之大,你可以得出结论,这两部电影之间有显著的差异。

将显著性水平与每个 p 值进行比较,您可以安全地拒绝零假设,即这些电影的平均评级之间没有差异。

这适用于星际大战表情符号电影表情符号电影大战星球大战:最后的绝地,因为在这两种情况下,p 值都远远小于我们在运行测试之前设置的 0.05 的显著性水平。

你刚刚得出结论,表情符号电影的平均评分(2.2 单位)与《星际穿越》(4.35 单位)和《星球大战》(4.5 单位)相比,实际上有很大差异。

鉴于后面几部电影的平均评分明显更高,你可以放心地将表情符号电影从你的候选名单中排除。

现在只剩下两位选手了…

星际大战 vs 星球大战:最后的绝地

  • 检验统计~=-1.35
  • p 值= 0.18046156732197555

从这些结果中,你不能证明这两部电影之间有统计学上的显著差异。如果你还记得,他们的平均评级非常接近——4.35 比 4.5 单位。

尽管说零假设是真的很有诱惑力,而且这两种方法没有区别,但你不能。

你能说的是,你没有足够的经验证据来否定零假设。

如果你想遵守统计学的规则,你需要一个技术上的联系😀🤓

作为决胜局,你可以询问公正的第三方的意见,或者只看平均评分最高的一方。

感谢阅读!

每年的这个时候我都会变得多愁善感

原文:https://towardsdatascience.com/i-always-get-sentimental-analysis-this-time-of-year-1d4865ba5f8a?source=collection_archive---------10-----------------------

Python 中的 NLP &情感分析!

圣诞快乐,我们来谈谈吝啬鬼。狄更斯对老人关于时空连续体午夜幻觉的描绘,呼应了我们自己一年一度的泪眼朦胧的假日反思。或者…随便吧。也许是对过去假期的回忆——回忆家庭聚会、童年礼物和更简单的时光。也许是当前的气氛——空气中的寒冷(或者在亚特兰大,气温的巨大波动)、拥挤和喧嚣(或者在亚特兰大,交通)。或者也许,只是也许,事实是我渴望有一天定性分析,特别是自然语言处理(NLP),实际上是一种创造有意义见解的有用工具。

😯☃️😤🎄😒🎅🙊☃️

什么是自然语言处理?根据维基神的说法,它是“一个与计算机和人类语言之间的交互有关的子领域,特别是如何给计算机编程以处理和分析大量自然语言数据。”干净利落。我为什么关心…?

定性数据是下一场革命

过去情感的幽灵

量化数据是 soooo 2010,老弟。作为分析师和程序员,我们基本上掌握了数字。有无数的科学家、统计学家和商业大师,他们 1)比我聪明得多,2)不知疲倦地努力发明下一个“工具”,让数字运算和数豆子变得更容易、更好、更性感。我想起了第一次打开 Tableau 时,它是如何震撼了我的心灵。我思考 Excel 已经走了多远。我想到了用 Python 和 r 创建的数十亿个库。每天都有新的和旧的出现。显然,我并不是说我们已经完成了定量分析。我只是说,我们现在越来越多地使用非结构化的数据库、图像、声音,当然还有文本。

我们的话语很重要。很多。我花了无数个小时分析美国各地医院的定性数据。这主要是在情绪分析的保护伞下。在这些数据中,大部分都存在未开发的改进潜力。是金子,杰瑞。为什么是黄金?调查评论形式的文本通常支持、验证并在许多方面取代我们淹没在其中的定量数据。此外,它还存在于组织的各个层面:领导、中层管理者、一线员工和客户——也就是病人。这些信息不是指南针,而是指导领导者行动计划的 GPS。那里。所以我才在乎。

有没有定性工具可以帮我们做到这一点?简答:有。自动化分析这些信息是可能的,但是它有效吗?我们拿着一个“单词包”,用一个马里奥式的木槌把圆形定性数据打碎成方形定量数据。手动完成这项工作需要花费大量精力,但是当我们利用数据科学工具来加速这一过程时,会发生什么呢?会不会更快达到同样的效果?好点了吗?

Mario BI Analyst vs Qualitative koopa troopa

让我们把计算机比作人类

情感的幽灵出现了

让我们想想我们需要什么。就我而言,我指的是对医院调查的情感分析,我们希望了解医院周围的人对安全因素的积极和消极看法。

让我们用 VaderSentimentAnalysis。 这个库是一个很有前途的快速肮脏的‘意见挖掘’库。此外,作者是佐治亚理工学院的毕业生,所以有(去,夹克。蛰他们。bzzz🐝)无论如何,在开始之前,有一些基本的注意事项:

  1. 它的预期目的是挖掘和分析社交媒体。

2.它建立在单词、字符和表情符号(是的,表情符号)的静态库上,随着库的更新而更新。所以之前我写的时候,"😯☃️😤🎄😒🎅🙊☃️,“不仅你确切地知道我的意思,而且显然维达也知道我的意思。好吧,或者反正是编出来的😏←这家伙。

3.该方法的输出包含四个分数:正面、中性、负面和复合。以下是更多相关信息。

出于这种分析的目的,我们为什么不假设调查评论的结构类似于“推文”。我知道他们不一样。这不是一篇研究论文。冷静点。重点是,人们通常会写下他们的感受,所以调查评论包含许多俚语、拼写错误和情绪化的词语……就像……一条推特。

我们来了解一下维达。有了这个假设,让我们来看几个例子和它们相应的分数。这些是直接来自维德 GitHub 页面。注意以下几点:标点符号很重要,大写字母很重要,俚语也很重要。事情很重要。

**[IN]** VADER is smart, handsome, and funny.
**[OUT]** {'pos': 0.746, 'compound': 0.8316, 'neu': 0.254, 'neg': 0.0}**[IN]** VADER is smart, handsome, and funny!
**[OUT]** {'pos': 0.752, 'compound': 0.8439, 'neu': 0.248, 'neg': 0.0}**[IN]** VADER is VERY SMART, handsome, and FUNNY.
**[OUT]** {'pos': 0.754, 'compound': 0.9227, 'neu': 0.246, 'neg': 0.0}**[IN]** VADER is not smart, handsome, nor funny.
**[OUT]** {'pos': 0.0, 'compound': -0.7424, 'neu': 0.354, 'neg': 0.646}**[IN]** Today SUX!
**[OUT]** {'pos': 0.0, 'compound': -0.5461, 'neu': 0.221, 'neg': 0.779}**[IN]** Not bad at all
**[OUT]** {'pos': 0.487, 'compound': 0.431, 'neu': 0.513, 'neg': 0.0}

也许‘pos’,‘neu’和‘neg’是不言自明的(也许不像我们将看到的那样),但是‘compound’需要一些背景:

“复合得分是通过对词典中每个词的化合价得分求和计算出来的,根据规则进行调整,然后归一化到-1(最极端负)和+1(最极端正)之间。如果你想对一个给定的句子进行单一的一维情感测量,这是最有用的度量。称之为‘标准化加权综合得分’是准确的。”—Vader perspection GitHub

所以,如果我理解正确的话,他们的复合分数有点数学魔力。这是对文本块进行分类时最重要的度量。例如,这里有一个例子,从各种新闻句柄抓取推文,并从 7 月份开始计算它们的综合得分。

让我们来做这件事。好了,够了。在本地环境中安装库,并根据提示进行升级。

> pip install vaderSentiment
> pip install -- upgrade vaderSentiment

假设您已经有了其他基本的 Python 分析库,这就是我们所需要的。现在,让我们对这个注释进行一些测试:

*“There is a culture where I work that does not appreciate the nurses and does not adequately address concerns brought up by staff regarding potentially dangerous patient situations and potentially dangerous staff situations. Valid concerns are dismissed and disregarded by local and senior management. Employees that raise concerns are made miserable until they quit. Dangerous and problematic employees are kept on and protected.  There is a pervasive culture of bullying among our staff that is not being adequately addressed by management"*

这是一个极好的样本。全国各地的医院都有很多类似的观点。也就是说,如果我看到这个评论,并把它分为积极、中立或消极,你认为这会是什么?是啊。咄。它是阴性的。它还对一些特定的类别持否定态度,但稍后会有更多的内容。现在,让我们看看维德要说什么:

**[IN]:***# Import libraries including the sentiment analyzer* import pandas as pd
import numpy as np
from vaderSentiment.vaderSentiment import SentimentIntensityAnalyzer
analyzer = SentimentIntensityAnalyzer()*# Read in the comment into a dataframe*
df = pd.read_csv(‘comments.csv’)*# Analyze the comment*
sample = df.iloc[0,0]
compound = analyzer.polarity_scores(sample)[“compound”]
pos = analyzer.polarity_scores(sample)[“pos”]
neu = analyzer.polarity_scores(sample)[“neu”]
neg = analyzer.polarity_scores(sample)[“neg”]*# Print the results*
print(‘ — — — — — — — — -’)
print(f’compound: {compound}’)
print(f’pos: {pos}’)
print(f’neu: {neu}’)
print(f’neg: {neg}’)**[OUT]:** -----------------
compound: -0.965
pos: 0.03
neu: 0.718
neg: 0.251

这很有意思。我不确定如何理解“积极”、“消极”和“消极”的分数,因为“消极”的分数在 0.71… 时占主导地位。??但是,注意,‘复合’得分是 -0.965。这意味着,“你的文本斑点非常非常消极。”这符合我们的精神分类,所以你说对了,维德。

接下来,有两个任务。

  1. 这在汇总我们所有的调查文本时会起作用吗?
  2. 有没有办法让这个分析更深入,因为那又怎样?

首先,聚集所有的文本(在本例中大约有 400 条评论),并在新的 blob 上再次运行代码。接下来,如果您想要查看每个单独字符串的分数,创建某种循环并将值推入列表中,以便进行切片和切块。这就是我在分析方面要说的全部。这里有一个方法:

compound = []
positive = []
neutral = []
negative = []for x in comments:
    x_comp = analyzer.polarity_scores(x)["compound"]
    x_pos = analyzer.polarity_scores(x)["pos"]
    x_neu = analyzer.polarity_scores(x)["neu"]
    x_neg = analyzer.polarity_scores(x)["neg"]
    compound.append(x_comp)
    positive.append(x_pos)
    neutral.append(x_neu)
    negative.append(x_neg)

print(f'compound: {compound}, length: {len(compound)}')
print(f'positive: {positive}, length: {len(positive)}')
print(f'neutral: {neutral}, length: {len(neutral)}')
print(f'negative: {negative}, length: {len(negative)}')

让我们看看我们的综合结果。当我手动分析大约 400 条评论时,这是情绪的分布。一个有医疗保健经验并了解全部数据集的资深分析师大约需要一个小时来执行我们的手动“评论分析”

= 4 hours of manpower

Python 和 Vader perspection 代码在这大约 26,000 个单词上运行的结果是什么?

< 4 seconds of computing power

嗯……这看起来很不一样。然而,还有一线希望。复合得分为 -0.6951 。如果我们粗略地将其与我们的手动分析进行比较,负比率为 0.85 ,我们可能会有所收获。然而,我还不确定在哪里。

感情未来的幽灵

那么,我们学到了什么?

  • PRO :在宏观层面上,Python 情绪分析复合评分认识到了整体数据集的负面性。就像我在维德的介绍中所说的,如果你需要快速和肮脏,这就是你的工具。
  • 反对:然而,即使将我们到目前为止所做的所有假设标准化,总得分中的 15.49% 的差异也是巨大的。这一点尤其正确,因为我们讨论的是一个数据集,它认为 1%的增量是平均值,5%的增量是显著的。如果我告诉一位首席执行官,69.51%的评论是负面的,他或她会不高兴。如果我后来回来告诉那位首席执行官,我仔细检查了,手动梳理了数据,结果,实际上 85%的评论都是负面的,我可能会被扫地出门。理解上的差距还不够小。
  • PROPRO:情感分析工具可以提供快速简单的结果,将文本块分类为正面、中性、负面等等。
  • 反对:无论如何,有了 Vader perspection,就很难理解正、中和负突破值的确切含义。复合分数是有用的,但还需要更多的研究。
  • 我们为自己节省了大量时间。四小时和四秒钟的差别对于大规模雇佣顾问来说是一大笔钱
  • 反对意见:即使客户在省钱,他们也可能忽略了评论中的价值。我关于定量分析的整个策略是,它补充了定量分析,并允许我们超越切片。否则,一个复合分数告诉我们什么?69%的回复是抱怨和抱怨?哦。好的。(再次显示门)。
  • PRO: 将复合分数打成列表对于查看基于单元的、基于角色的或者除了聚合之外的任何其他微观分析可能非常有用。
  • :小心。现在我们进入了基于实践的伦理学。允许的微观分析程度将根据一个组织对其反馈的“老大哥”程度而有所不同。如果员工认为他们会因为说了对组织不利的话而受到惩罚,他们会抑制或缩减他们的语言。如果你打算走这条路,想出一个与领导沟通的计划。

我们还有很长的路要走。展望未来,在处理定性数据时,有一个行动呼吁和一些关键要点。

  • 不要仅仅依赖 NLP 数据科学工具。自己花时间去理解组织和文本数据。这可能很耗时,但它将提供自动化分析之外的价值
  • 理解你的词典。如果员工使用大量医学术语,那么预先构建的自然语言处理库可能就没有用了。如果不剖析代码库,Vader perspective 的字典可以被视为一个黑盒。作为数据科学家,我们可能必须建立解释这种类型分析的字典
  • 不要忘记上下文和微观分析。文本工具正在变得越来越好,但我们仍然错过了上下文、微妙之处、细微差别、习语、讽刺,以及……嗯,说出任何其他与交流相关的特征。
  • 了解 NLP 的其他应用(但是这里有一篇很棒的文章包含了关于其他 Python NLP 库和应用的信息。我们需要找到合适的工具。)

我留给你两样东西。首先,

**[IN]**
sample = '😯☃️😤🎄😒🎅🙊☃️'
compound = analyzer.polarity_scores(sample)["compound"]
pos = analyzer.polarity_scores(sample)["pos"]
neu = analyzer.polarity_scores(sample)["neu"]
neg = analyzer.polarity_scores(sample)["neg"]
print('-----------------')
print(f'compound: {compound}')
print(f'pos: {pos}')
print(f'neu: {neu}')
print(f'neg: {neg}')**[OUT]**
-----------------
compound: 0.0
pos: 0.0
neu: 1.0
neg: 0.0*# Neutral?!? Vader, please...*

最后,

亲爱的圣诞老人,

请给我一个有用的自然语言处理工具。

SRSLY。分析 TINY TIM 的患者体验反馈表的 BI 团队就指望它了。

真诚地,

杰夫

我分析了 122 小时的假日广播

原文:https://towardsdatascience.com/i-analyzed-122-hours-of-holiday-radio-874b5c2cd3ae?source=collection_archive---------15-----------------------

你会被迫听到多少次“美妙的圣诞节”?

122 hours, 1,510 tracks. Only 80 original songs. Source: 106.7 LiteFM; 11/30/2018–12/5/2018; Download the data.

早在感恩节前就开始了。准确地说,今年是 11 月 16 日下午 5 点。这时,纽约州的 WLTW 106.7 LiteFM 硬切换到全圣诞音乐节目。它持续到圣诞节。这是一种家庭规则,让汽车收音机在这段时间里一直调到这个电台。

我和我的家人最近开着车听 106.7 的圣诞音乐,似乎每次我打开汽车,我都会被迫听到那些可怕的八个混响合成器音符,这些音符出现在最糟糕的圣诞歌曲保罗·麦卡特尼的“美妙的圣诞节”之前。其他人已经说了很多关于为什么这首歌这么差,所以我继续。

The 8 synthesizer hits at the beginning of the worst Christmas song of all time.

但它确实让我对这个长达 943 小时的圣诞音乐节目感到好奇。我有一些问题。我很好奇新的圣诞歌曲似乎很少。许多艺术家每年都会推出圣诞专辑,但这些通常只是圣诞经典的封面。圣诞音乐有过黄金时代吗?音乐家们已经不再尝试创作原创的圣诞新歌了吗?我决定收集一些数据,并尝试回答其中的一些问题。

我首先从 LiteFM 的网站上下载了“最近播放的”播放列表,这是从 11 月 30 日到 12 月 5 日五天多一点的圣诞音乐。在这段时间里,我播放了 1510 首歌曲。此提要列出了歌曲标题、艺术家、专辑封面和歌曲播放时间。对于每首歌,我都尽可能地搜索最接近最初“出版”日期的日期——歌曲创作或作曲的时间——以及作家和作曲家的名字(如果有的话)。这相当于大约 122 小时的广播时间(其中包括他们在歌曲之间播放的任何广告,我没有跟踪这些广告)。

圣诞音乐有过黄金时代吗?音乐家们已经不再尝试创作原创的圣诞新歌了吗?

考虑到每首歌创作的年份,我的数据集跨越了 484 年的出版音乐。当然,许多老歌被认为是“传统”歌曲,没有明确的作者或作曲家。这种类型的一个明显的特点是它有丰富的翻唱(表演别人歌曲的新版本)。在我检查的这段时间播放的 1,510 首歌曲中,事实证明数据集中只有大约 80 首独特的歌曲。但是从这 80 首歌中,出现了许多翻唱、混音和现场录音。

所以让我们从基础开始。“圣诞老人进城了”是我的数据集中播放次数最多的歌曲。这包括了这首歌所有 10 个版本的所有播放次数。《雪橇之旅》紧随其后,共有 89 部戏剧,11 个不同版本。

Source: 106.7 LiteFM; 11/30/2018–12/5/2018; Download the data.

Michael Bublé, the holiday music juggernaut. Photo: Jeanie Mackinder [CC BY 2.0]

现在,如果我们看看特定版本的歌曲(包括所有这些封面),总的来说播放最多的歌曲是宾·克罗斯比的“白色圣诞节”——绝对是一首经典老歌。但是紧随其后排在第二(和第三)位的是麦可·布雷。我不得不承认我以前从未听说过他的名字,但是这位 43 岁的加拿大歌手(4 次格莱美奖得主)是假日音乐排行榜上不可忽视的力量。在撰写本文时,Bublé目前有 9 首歌曲登上了 Billboard Holiday 100 排行榜

Source: 106.7 LiteFM; 11/30/2018–12/5/2018; Download the data.

果不其然,当我们按照表演者最多的戏剧来看数据时,布莱在这个包含一些大师的列表中占据主导地位。LiteFM 的听众一定非常喜欢他天鹅绒般光滑的声音,因为在我监测的这段时间里,麦可·布雷的播放量是弗兰克·辛纳特拉的六倍多。

Source: 106.7 LiteFM; 11/30/2018–12/5/2018; Download the data.

Yukon Cornelius sang the words of Johnny Marks.

所以那只是唱和表演这些心爱歌曲的人。幕后真正的词曲作者呢?你可能不认识约翰尼·马克斯这个名字,但你肯定听过他的音乐。约翰尼·马克斯写了《红鼻子驯鹿鲁道夫》《过一个快乐的冬青树圣诞节】《围着圣诞树摇滚》以及许多其他假日热门歌曲。尽管约翰尼·马克斯创作了一些最经典的圣诞歌曲,但他是犹太人(与此同时还有欧文·柏林和其他许多歌曲作者)。虽然没有出现在这个数据中,但 Marks 还创作了“银和金”育空·科尼利厄斯在定格鲁道夫漫画中演唱的朗朗上口的曲子。

Source: 106.7 LiteFM; 11/30/2018–12/5/2018; Download the data.

因此,如果我们查看这个收藏中的所有原创歌曲,并回顾它们创作或首次出版的年份,我们可以了解最常播放的音乐是何时产生的。果不其然,有一个十年跳出来,成为该数据集播放的近 30%的歌曲的来源——20 世纪 40 年代。

Source: 106.7 LiteFM; 11/30/2018–12/5/2018; Download the data.

在我监测的五天中,近 30%的歌曲创作于 20 世纪 40 年代。

Martin Luther. Cranking out the hits since 1529. Lucas Cranach the Elder [Public domain]

在我收集数据期间,艾米·格兰特(Amy Grant)的混合曲目“一个强大的堡垒/我们在高处听到的天使”只播放过一次,但这首曲目拥有收藏中一些最古老音乐的殊荣,因为马丁·路德在 1529 年首次为赞美诗一个强大的堡垒创作了音乐。

看着这张图表,虽然事情似乎在 20 世纪 70 年代后减少了,但这真的很值得注意。90 年代确实给了我们一个真正的现代圣诞大片的最出色的例子,玛丽亚·凯莉沃尔特·阿法纳西夫的 “我想要的圣诞礼物是你”凯里在 1994 年录制。事实上,我很惊讶的是 AIWFCIY 不在这张专辑中播放次数最多的前 20 首歌曲中,因为它目前在 Billboard 的假日 100 首歌曲中排名第一。有趣的事实:这张唱片里没有真正的乐器,因为它都是在电脑上完成的

玛丽亚·凯莉还声称为另一首非常受欢迎的圣诞歌曲《你的圣诞在哪里》创作了歌曲(连同詹姆斯·霍纳威尔·詹宁斯)来自 2000 年的电影《鬼灵精》。她最初为电影配乐录制了这首歌,但由于她与汤米·莫托拉的离婚,她被法律禁止演唱这首歌。

那么这些圣诞歌曲中哪首版本最多呢?如果你在我分析的这段时间里不停地听 LiteFM,你会听到 11 个不同版本的【雪橇之旅】(播放了 89 次)和不少于 10 个版本的【圣诞老人进城】(播放了 90 次),尽管我不明白为什么你需要除了布鲁斯·斯普林斯汀之外的任何版本

Source: 106.7 LiteFM; 11/30/2018–12/5/2018; Download the data.

最后,我想看看播放所有这些歌曲的模式是什么样的。下面是所有独特歌曲的集合(包括所有版本),按播放次数从多到少排序。每个红框表示每小时播放一次。我从 11 月 30 日星期五下午开始收集数据,到 12 月 5 日星期三晚上结束,是的,收集整整一周的歌曲会好得多。

我确实注意到某些歌曲在不同时间播放的一些有趣的模式。我联系了 LiteFM 的项目主管,但没有得到回复。看着电视台的播出时间表,我确实看到一些模式与不同主持人的轮班相匹配。我很想知道主持人(他们现在还被称为 DJ 吗?)还是对播放列表有一定的创意控制。看起来午夜到凌晨 5 点是玩“祝你小圣诞快乐”的热门时间。如果我收到电视台的回复,我会更新这个帖子。

Source: 106.7 LiteFM; 11/30/2018–12/5/2018; Download the data.

你可以在这里下载我收集的数据。你可以在jonkeegan@gmail.com向我发送任何问题。感谢阅读!

Jon Keegan 是大纽约地区的视觉记者。他在华尔街日报工作了 18 年,处理数据并开发新闻应用。创作了《华尔街日报》的“ 【蓝馈】、红馈“ *,图文并茂地过滤脸书上的气泡。其他感兴趣的领域包括 3D 打印和扫描、太空、无线电和可视化。你可以在 jonkeegan.com看到更多他的作品。*

* [## 乔恩·基根:视觉记者

18 年来,我为华尔街日报开发新闻应用程序。我设计、写文字、编码和可视化数据。我…

jonkeegan.com](http://jonkeegan.com/)*

我分析了法戈的犯罪数据,这是我的发现

原文:https://towardsdatascience.com/i-analyzed-fargo-crime-data-and-this-is-what-i-found-25138e2d6bb1?source=collection_archive---------5-----------------------

TL;博士: 如果你没有耐心,想直接进入有趣的东西,这里有一个链接到我建立的 互动网络仪表板 来补充这个分析。在台式电脑上观看效果最佳。

最近的一个周一下午,我通常会趴在桌子上小心翼翼地敲代码,但我偶然发现了一篇关于我家乡的文章,这让我恍然大悟。法戈暴力犯罪首次超过美国全国平均水平。这篇文章详细描述了坐落在肥沃平坦的古老湖床上的曾经沉睡的农业社区是如何超越全国暴力犯罪率的。

我是一个新爸爸,所以我对这些说法一点也不担心,所以我做了任何数据科学家在这种情况下都会做的事情,我搜寻了一些数据以了解更多信息。幸运的是,法戈警察局公布了他们的调度日志,其中详细记录了所有打给警方的电话。还有一个方便的地图应用程序,可以帮助你在二维空间中可视化“危险区域”的位置。但是,我想知道更多。因此,我制定了一组问题,我将使用 2017 年的派遣数据来回答这些问题。

问题陈述

  • 问题 1:哪个月犯罪最多?
  • 问题 2:哪个工作日犯罪最多?
  • 问题 3:一天中什么时候犯罪最多?
  • 问题 4:犯罪发生在哪里?

但是首先,让我们把假设和方法放在一边。

假设

(1)在调度日志中的犯罪类别中,我们将查看实际上是犯罪的呼叫,例如,我们将忽略停车投诉、胸痛等。

(2)每个电话事件都在街区级别报告,这意味着我们的地图将精确到街区,而不是房子或地址。

(3)为了简洁起见,我将使用“犯罪”一词代替“调度呼叫”,假设调度呼叫通常表示犯罪。

方法

计算语言被用来执行这些分析。完整的源代码可以在这个 Github 库找到。

哪个月犯罪最多?

法戈既有热天气也有冷天气,但在流行文化中,哈姆雷特更因后者而闻名,(谢谢,科恩兄弟/FX!).天哪,当你搜索法戈的图片时,你得到的只是 1996 年电影的海报和一个血迹斑斑的史蒂夫·巴斯米:

北方气候的人们都知道“幽居病”是真实存在的,尽管没有杰克·尼克尔森在《T4》的《闪灵人》中的解释那么极端。我的观点是,当你不得不刮擦挡风玻璃并在助推汽车前预热发动机时,犯罪就会变得更加困难。

在我查看数据之前,我认为在寒冷的几个月里,犯罪率会很低,这可能从 10 月份开始,一直持续到 5 月份。

上面的图表被称为日历热图。它按月份和星期几显示犯罪频率。冷色(紫色)表示低犯罪率,暖色(黄色)表示高犯罪率。正如我所怀疑的,与六月和九月的狂欢相比,十一月到二月相对平淡。

啊,现在这个条形图更清楚了。似乎从一月开始到五月的寒冷月份是堕落的夏季月份的隐喻斜坡,六月是这种放荡的顶峰。

哪个工作日犯罪最多?

我认为条形图也可以解决这个问题。

这很有道理。随着人们在工作周的忙碌,他们比周末有更少的时间变得野蛮。我很好奇,某些犯罪在一周的不同日子里会更常见吗?为此,我将从交互式仪表盘中截取一些截图:

受损司机

人们在周末聚会更多;很明显。

骚扰

看一下调度记录,似乎很多电话都是对电话骚扰的回应,就像骗子一样。显然周一是他们在骗子公司的大日子。

一天中什么时候犯罪最多?

没想到会看到这些结果。显然,犯罪率在午夜左右下降,然后在凌晨两点酒吧打烊时又回升。为简单起见,我将不同的犯罪类型分为三个子类。

犯罪在哪里发生?

总的来说,这个城市到处都是犯罪。然而,市区在 2017 年的犯罪率最高。

互动仪表盘上的热图很有趣,可以用来查看特定犯罪的热点。

有趣的发现

当我摆弄仪表板时,我发现了一些有趣的事情。首先,我注意到窥视者数据相当集中在一个区域:

西英亩西部的法戈地区是主要的偷窥场所吗?我不知道。但是这可能表明只有一两个偷窥者呆在他们自己的社区里。周日的电话数量几乎是一周其他时间的两倍,这是一个明确的模式。

对“过量中毒”犯罪图表的研究显示了一种不同的模式:

这里我们看到两个不同的集群;一个在 Yunker 农场东部,另一个在市中心。如果我放大市中心的集群,我们可以精确定位震中(记住这是块级别的数据):

似乎是一个需要小心的地方。

结论

那么我们学到了什么?当你检查交互式仪表盘时,你总是会得出与我不同的结论,但我的观点是:( 1)市中心=危险区,( 2)寒冷肯定对当地犯罪有“冷却效应”(抱歉),( 3)酒吧关门不是遛狗的好时候。

进一步研究

我曾想过建立一个实时网页来展示法戈犯罪的发生。有一个网页已经做了类似的事情,但它笨拙而缓慢。如果对这个分析有足够的兴趣,我肯定会把这个应用扔在一起(如果你喜欢这个,给我发电子邮件或评论)。

我可以根据合同提供数据咨询。给 bradley.lindblad@gmail.com 发邮件

我分析了漫威的电影剧本,以了解每个复仇者说得最多的是什么。

原文:https://towardsdatascience.com/i-analyzed-marvel-movie-scripts-to-learn-what-each-avenger-says-most-2e5e7b6105bf?source=collection_archive---------8-----------------------

处理等待无限战争的一个方法是玩一些复仇者联盟的数据。我拿了最近三部漫威电影宇宙跨界电影(《复仇者联盟》、《复仇者联盟:奥创时代》和《美国队长:内战》)的剧本,找出了每个英雄最具特色的词语。我离开洛基和奥创是因为他们有如此独特的声音。

Matt Winn,数据可视化超级英雄,使用 R 的 ggplot 库制作了这个图(在这里查看他的教程)。这并不容易,我们得到了西雅图数据即 Jam meetup 的大力支持。

我们希望你喜欢!

一些值得注意的数据观察:

  1. 鹰眼和浩克都在说纳特。当然是因为不同的原因。
  2. 洛基有着崇高的想法,比如权力改变。虽然索尔比其他复仇者更多地提到洛基,但洛基并没有回报兄弟般的关怀。他的眼睛盯着他的目标。
  3. 雷神的关键词表明,在复仇者联盟的电影中(不包括雷神标题的电影,如 Ragnarok 和黑暗世界),他比大多数其他角色更注重行动。除了他和洛基的关系,他倾向于关注推动剧情发展的有形艺术品。比如洛基的权杖宇宙魔方和心灵之石。
  4. 蜘蛛侠是如此笨拙和追星族。他的关键词包括“嘿”、“嗯”、“嗯”。
  5. 看看《幻视》和《猩红女巫》有什么相似的词汇——它们都在谈论恐惧。我希望他们在无限战争中保持同步。有趣的是,我也做了一个情绪分析,Vision 有最多的负面情绪。这并不是因为他是一个经常令人沮丧的人,而是因为他认为情况就像他看到的那样,并且有时反思他所爱的人类英雄的徒劳。他看到了额外的,额外的大局,我觉得这让他很不安。
  6. 美国队长经常谈论其他人。事实上,他的五个最有特点的词中有四个是名字(托尼、萨姆、斯塔克、斯特鲁克;另一个词是“西装”,几乎都是指托尼的西装)。
  7. 看到黑豹的话随着他的角色继续发展而变化将会很酷——我们刚刚在内战中见到他,他在他的个人电影中经历了一个惊人的过程。在内战中,他仍然被他在瓦坎丹皇室的地位和他对传统的依赖所定义,这表现在他的用词上。当他被他的个人电影中的事件改变时(这里没有剧透),他必须改变他的世界观并重新定义他与他的遗产的关系。

很想听听大家的评论和见解!

再见了,

我分析了我在脸书的数据,这是一个关于害羞、孤独和变化的故事

原文:https://towardsdatascience.com/i-analyzed-my-facebook-data-and-its-story-of-shyness-loneliness-and-change-7f4e0ec3a952?source=collection_archive---------1-----------------------

我跟随最新的趋势也下载了我的脸书数据的 zip 存档,但是在分析数据之后我发现的并不是我所期望的。

我想知道脸书对我有什么了解,就像现在其他人一样,但我开始深入挖掘联系数据、广告点击量和我的活动历史之外的信息。第一次,我脑子里所有关于解析我的 facebook 数据的想法看起来都是可行的。页面是干净的,他们只是对我尖叫,“利用我,你知道如何编码我周围的东西”。我开始写一个刮刀来分析所有这些数据,数万条消息,好友添加历史,我的词汇,我对一切都很好奇。整个脸书剑桥分析丑闻应该提醒我们,Facebook 在我们的生活中有多重要,我们每天使用它有多频繁,我们表现出的行为远远超出了简单的喜欢和照片。

我想知道我的模式,并在这些年里做了一些改变。我使用脸书这么多年了,在很长一段时间里,信使也一直是我主要的交流方式。那里必须有有趣的数据,如果我所有的工作变得枯燥乏味,我会非常失望。我在 ruby 中创建了一个脚本来解析我的 zip 存档数据,我与你们所有人分享它,所有你需要的是脸书的 zip 副本存档(它必须是英语)。

这是给你阅读后尝试的,对代码质量抱歉,但这是一个快速的黑客,所以请原谅我:

https://github.com/Lackoftactics/facebook_data_analyzer

这个脚本将生成 excel 文件,其中包含所有分布在工作表中的统计数据:“朋友排名”、“我的消息统计”、“词汇统计”、“联系人列表”、“交朋友”。

我首先感兴趣的是我和谁写得最多,以及我们的转化率看起来如何。

People, groups I wrote the most

到目前为止,一切都很好,我最好的朋友排在第一位,其次是我现在的女朋友,我看到他们在交谈中投入了更多,因为他们写了更多的信息和文字。这是一个非常有趣的统计数据,可能说明我真的更喜欢和同样乐于交谈的人交谈。

到目前为止,这很有趣,我有一个我的朋友的排名,通过一些信息,单词,字符。接下来的部分带来了回忆。是时候坦白了,我是一个非常害羞的人,我独自坐在学校直到高中结束。我不会去参加聚会,喝酒,甚至不会和朋友出去玩。如果提到的任何事情曾经发生过,那也是非常罕见的,几乎是不存在的。我从父母身边搬走后,我知道这是我一生中最好的决定,我独自一人,渴望朋友,但他们无处可寻。我从不约会,很少和任何人去看电影或喝啤酒,我把时间都花在看电视节目上。但是有一年,当我开始出去,经常出去,我是说真的经常出去的时候,我突然明白了一些事情。参加那么多派对并不好,但我需要,接触女孩,去上嘻哈课程,更关心更多的外表。有趣的是,你可以从数据中看到。

这是我每年发送的信息数量,猜猜看,我是从哪里开始变得更加社会化的。

Number of messages sent by year

在 2016 年,当我开始在社交和约会领域迈出第一步时,这一数字增加了近 10 倍,然后与 2015 年相比增加了近 40 倍。我知道这只是一种通信类型的数据,但我以前总是使用 messenger 作为我的主要通信方式。不可否认,我与人们的社会交往和我发送的信息数量之间有很强的相关性。在 2015 年和 2014 年,我每天平均收到 3.6 条消息,这表明我当时有多孤独,电话那头没有任何人让我说话,安排会议,关心我的一天或说晚安。在 2017 年,平均每天有 108 条消息,我有可以交谈的人,有趣的人,我每天都可以和他们交谈和交换这么多消息。我的社交能力处于巅峰状态,在接近女孩时,我觉得自己真的不可战胜。

最繁忙的消息传递日

好吧,即使是这个数据也显示了社交模式的美妙之处。大多数繁忙的消息传递日恰好是从 2017 年 6 月开始的,就在我遇见我的女朋友并给我留下了非常好的印象之前,好到我们在一起了。

Most messages sent by date

我们在这里,我们在一起不是很可爱吗?😃

@p_mroczek picture from instagram

我还分析了我添加新朋友的历史,进展仍然存在,但这个统计数据并不那么可信,因为每次工作变动,旧同事的快速增加很容易造成脸书,使数据混乱。但是你也可以在这里看到进步。

按年交友

我社交最多的一年也是我交朋友最多的一年。但就像我之前说的,这不是我百分百信任的数据,因为任何社会环境的变化都让这个数据不可靠。

我也对我交新朋友感兴趣,是在周末还是在工作日。正如我所预测的,大多数新的友谊来自于周末外出。

你知道,你还能从脸书的数据中得到什么?类型的人,夜猫子对早起的鸟。这并不难,只要分析你的信息模式,按一小时分解。

快速看一看,你就知道,我不是那种早起的人。我一直怀疑我是夜猫子,但现在我有数据支持它。我在晚上更有效率,我最密集的编码会议发生在晚上。即使是这篇文章,我也是在深夜创作的。对我来说更容易进入心流状态,但也很安静。

我们来看看词汇统计。我对我的词汇感兴趣。我总共使用了 43k 个单词和 366k 个单词。那只是冰山一角。我用的最常用的词呢,在我们过了常用词之后,我们得到了有趣的东西。我怀疑,可能作为一个相当敏感的人,这也应该反映在我的写作中。为了更好的理解,我将把这些波兰话翻译成英语。我不想过度分析这一点,但与我的其他朋友相比,我会说这看起来不同,显然我喜欢表达我的情绪和我的感受,人们倾向于隐藏它们,特别是在发短信的时候。也许这也是害羞的一部分,写东西比在别人面前说容易。

Word rank

此外,我真的很喜欢谈论 Taco Hemingway,波兰嘻哈艺术家:)我非常公开地交流我的感受,根据我的经验,这样做的人可能很容易成为欺凌的目标,这导致封闭自己,少说话,更少机会,因为第一次尝试以可怕的方式结束。

所以现在你知道了我的故事(至少有一小部分没有进入沮丧的情绪),用数据表达,一个我几乎忘记的故事,因为现在事情对我来说太不同了。我不记得那个害怕接近女孩、和她们跳舞、和朋友出去的家伙。这就是我们这个时代真正有趣的地方,我们不仅可以通过写日记,拍照片来创造记忆,我们还可以通过创造数据来创造记忆。这些数据我们可以在未来进行分析,可以激发记忆,尽管有时有点悲伤。

想要运行此脚本并了解自己。也许只是为了好玩,也许你也会发现自己的一些有趣之处。

查看我的 github 存储库,了解如何运行:

[## lacoftactics/Facebook _ data _ analyzer

facebook_data_analyzer -分析你的数据的 facebook 副本。从 facebook 下载 zip 文件并获取朋友的信息…

github.com](https://github.com/Lackoftactics/facebook_data_analyzer)

请在产品搜索上投票支持我的存储库,以便更好地展示该库。那会对我有很大的帮助。

https://www.producthunt.com/posts/facebook-data-analyzer

我为我的工作申请建立了一个拒绝-不拒绝电子邮件分类器

原文:https://towardsdatascience.com/i-built-a-reject-not-reject-email-classifier-for-my-job-applications-844a3b6cd67e?source=collection_archive---------3-----------------------

可怕的拒绝邮件。到现在,我已经很习惯了。就好像我申请工作会被拒绝一样。在我的职业生涯中,我收到过很多拒绝邮件。起初,每当我收到拒绝邮件时,我都会感到非常失望。但是随着时间的推移,我有点习惯了。事实上,现在,我一边阅读拒绝邮件,一边享受人力资源团队的创造力。大多数人力资源试图让它听起来尽可能的甜蜜。他们中的一些人会说工作的要求和候选人的技能不匹配。有些人会安慰说,他们确信在其他地方会有更好的机会。有些人会直截了当地说你不够好。

那么一个数据科学家在收到大量拒绝邮件的时候会怎么做呢?构建一个分类器,自动将指示拒绝的电子邮件分类到拒绝类别,并将其他电子邮件分类到非拒绝类别。让我详细说明一下这个过程,这样你也可以这样做。

我开始从我自己的收件箱收集数据。我曾想过从收件箱中使用相关关键词(如“谢谢你的申请”、“我们祝你有个美好的未来”)有计划地收集电子邮件,但后来我决定不这么做,因为我不知道这些关键词是否正确。我手动浏览我的收件箱,并从拒绝邮件中提取文本。我还随机收集了等量的没有任何拒绝的邮件。我将这两类电子邮件文本收集在一起,保存在一个 csv 文件中。

Screenshot of reject emails with their labels

这项任务数据收集的一个问题是,我没有收到很多拒绝邮件。许多公司根本不发送任何拒绝电子邮件。他们中的一些人在他们的门户上发送拒绝消息。结果,我们收到的拒绝邮件数量非常有限。事实上,尽管我们被拒绝了很多次,我们还是收到了大约 10 封拒绝邮件。这对于一个健壮的分类器来说是远远不够的。但是让我们试着用我们可以支配的资源来建造一个。

在数据收集之后,我们进入数据预处理阶段。在这一阶段,我们首先将所有大写字符转换成小写字符,因为计算机对每种情况都有不同的处理方式。之后,我们删除标点符号,因为它们对分类器没有贡献。然后,我们删除数字,因为它们对分类器没有贡献。

一旦数据经过预处理,就必须将其转换成可用于机器学习的形式。有多种技术可以将文本转换成数字矩阵。其中包括计数矢量器、Tf-Idf 矢量器和单词包。在我们的例子中,我们使用计数矢量器,因为它几乎可以与 Tf-Idf 矢量器相媲美。

我们还使用 sklearn 的 LabelEncoder 对我们的目标变量,即标签(拒绝或不拒绝)进行编码。这将拒绝和不拒绝分别编码为 0 和 1。

然后,我们使用 sklearn 的 train_test_split 将数据分成训练集和测试集。我们将训练数据标记为 x_train 和 y_train,将测试数据标记为 x_test 和 y_test。

我们使用多项式朴素贝叶斯分类器模型来拟合训练数据。之后,我们编写一个函数,将编码的类别转换回它们的名称,并对测试数据使用预测函数。我们在测试数据上获得了大约 80 %的准确度。

我们还通过给出定制的输入语句来测试我们的分类器,看看它的性能如何。以下是一些预测。

Reject and Not Reject predictions from the Multinomial Bayes model

厉害!当然,它并不完美,但它显然能够识别拒绝邮件的模式。有了更多的数据,我相信它可以变得更加稳健。此外,我想探索一下我是否可以将它与我的 gmail 帐户整合在一起。

另外,如果你想浏览一下代码,我已经把它作为 Ipython 笔记本上传到 Github 上了。

https://github.com/imaadmkhan1/reject_not_reject

我用 Python 构建了 T(并修改了它)

原文:https://towardsdatascience.com/i-built-the-t-with-python-and-revamped-it-632127364f4e?source=collection_archive---------9-----------------------

Python 是一个很好的网络建模工具——那么它能告诉我们如何改进 T?

今年秋天,我在麻省理工学院上了一堂网络模型课( 1.022 )。这门课涵盖了许多网络/图形的酷概念,如节点中心性和最短路径,以及重要的应用,如流行病和社交网络的行为。这个理论的另一个应用——我选择做我的毕业设计——是交通网络。在我这堂课的最后一个项目中,我模拟了 T,并实验性地对网络做了一些改变。

如果你不熟悉 T…

T 是波士顿地铁系统。马萨诸塞湾运输管理局(MBTA)经营 T,以及公共汽车和通勤铁路。T 上有五条线:红色、蓝色、绿色、橙色和银色的线。银线实际上是一辆公共汽车,我没有把它包括在我的模型中。

T 的官方地图,参考这一页

Have fun exploring the T via this map I made on Carto! 😃

首先,我将解释一下我是如何对网络建模的。

你应该知道的第一件事是, MBTA 的 GTFS 数据在网上公开。 GTFS 数据是一种纯文本格式(。txt)数据,Google 创建这些数据是为了标准化公共交通机构与开发者共享/报告路线的方式。特别是,我使用了“stops.txt”文件,该文件报告了关于 MBTA 站的所有信息。这些数据给了我创建网络节点所需的信息,也就是 T 型站点。

Here is the class Station that I defined to represent the MBTA stations, and the function create_stations that creates Station objects from the MBTA’s GTFS data.

在图论中,图由节点和边组成。边连接节点;它们还可以具有表示其相对重要性的权重。对于 T 形网络,边代表车站之间的连接,即火车轨道所在的位置。这些边的权重表示站点之间的旅行时间。

This map by Stonebrown Design was incredibly helpful in reporting travel times.

在时间比例的 T 地图的帮助下,我写了一个文本文件,指定了车站之间的每条边和旅行时间。文件中 116 行的每一行都采用以下形式:

stop1,stop2,time,color

你可以在这里看到整个文件。

使用 Python 上的 Networkx 包,我制作了一个表示地铁网络的 Graph 对象。我还编写了一个函数,使用站点的地理坐标绘制网络,并保持边的颜色与线的颜色一致。

This module makes a Networkx Graph object to represent the T, and it also plots the resulting network.

Here’s what the network looks like! Travel times are not visually represented, but you can see how physically far apart the stations are, which is correlated to travel time.

但是我不只是对电视台的网络感兴趣;我想知道实际上有多少人乘坐 T 型车,哪些路线最受欢迎。我联系了 MBTA,得到了一些 2017 年秋季的需求数据!利用他们给我的数据,我实现了一个类似的程序来建立另一个网络。在“需求”网络中,边权重代表工作日一对车站之间的平均乘客数量。你可以在这里看到我为那个写的代码

This is a visualization of the demand network, with green edges being the most traveled routes.

在对网络进行更改之前,让我们看看我们已经能够辨别出什么。

我从对节点中心性的一些初步分析开始。在地图上,科普利阿灵顿具有最高的接近中心度。实际上,这意味着这两个站是网络上所有其他站“最接近的”(在行驶时间上)。同样, Copley 具有最高的中间中心性,这意味着网络上最多的最短路径经过 Copley(注意,这没有用行程时间加权)。 State Street 具有最高的特征向量和 Katz 中心性,这意味着它是最有影响力的(同样,不根据出行时间或需求进行加权)。度中心性在地图上的唯一意义是指出发生换乘的车站。因此,使用需求图来计算度中心性更相关。公园街具有最高的中心度,意味着它具有最多的交通/需求。下面是地图图形的放大视图,中心节点已标记。

Not surprisingly, the most central nodes are all located in the center of Boston, a.k.a. downtown.

This is an interactive map of the same stations, to give you a little more context if you’re unfamiliar with downtown Boston.

我还计算了乘客在地铁上的平均出行时间。为此,我做了一些假设。首先,我假设乘客会通过最短的路径(以分钟为单位)从出发地到达目的地。我还假设线路之间的每一次转换都需要五分钟。这是一个重要的规范,因为否则,我的算法会认为换乘是“免费的”——而实际上乘客喜欢尽可能避免换乘。考虑到传输,我制作了另一个版本的 edges 文件;我拆分了每个有换乘的车站(例如,公园街→公园街红和公园街绿),而是通过 5 分钟的边连接两个车站。下面,看看那些转移边在文本文件中是什么样子的。

place-pktrm_red,place-pktrm_green,5,black
place-gover_blue,place-gover_green,5,black
place-state_orange,place-state_blue,5,black
place-haecl_green,place-haecl_orange,5,black
place-north_green,place-north_orange,5,black
place-dwnxg_red,place-dwnxg_orange,5,black
place-kencl_B,place-kencl_C,5,black
place-kencl_C,place-kencl_D,5,black
place-kencl_D,place-kencl_B,5,black
place-coecl_BCD,place-coecl_E,1,black
place-jfk_A,place-jfk_B,5,black

我的算法是这样计算平均乘客行程时间的:

  • 迭代需求网络上的每条边(例如,站 A 到站 B,150 名乘客/天)
  • 计算这些站点之间的最短路径/行驶时间(例如,站点 A 到站点 B 的最短路径需要 13 分钟)
  • 乘客数量乘以行程长度(例如,从 a 站到 b 站每天贡献 1950“乘客分钟”)
  • 合计每个连接的乘客分钟数,然后除以乘客总数

Here’s how I did it!

使用这个算法,我发现 T 上的平均行程时间(工作日)是 14.7 分钟。

那么,如果 MBTA 最终建造了红线-蓝线连接器会怎么样呢?

Here’s what the network would look like with the Red and Blue Lines connected at Charles/MGH! (Currently, the Blue Line ends at Bowdoin.)

关于从鲍登延伸蓝线——它的终点——到查理斯/MGH 已经有谈了T5 年了。红色和蓝色线路是该网络中仅有的两条没有直接连接的主线(抱歉,是银色线路)——目前,你必须乘坐橙色或绿色线路才能在两条线路之间穿行,而无需离开地铁。由于两条线路在地理位置上非常接近(例如,步行 5 分钟),为了避免再次点击你的查理卡并支付另一笔 2.25 美元,乘坐橙色或绿色线路的一站可能会感觉非常愚蠢。

红线-蓝线连接的好处是什么?我的模型预测红线-蓝线连接可能不是很有用。在没有连接的情况下,平均乘客行程时间为 14.70 分钟;有了这条线路,平均乘客出行时间变成了 14.66 分钟。平均而言,这种连接对乘客的影响可以忽略不计(特别是与施工期间的不便相比)。然而,这种连接不会对乘客产生任何影响,除非他们真的在红线和蓝线之间旅行。所以,我也研究了这种差异。我制作了另一个版本的 average_shortest_path ,它只查看两组不同车站之间的乘客——在这里是红线车站和蓝线车站。

如果没有连接,乘客在两条线路之间的平均旅行时间为 16.61 分钟。通过连接,这一时间缩短至 15.77 分钟,因此这些乘客每天可以节省近一分钟。这是一个更显著的区别。此外,该模型假设当添加新连接时,需求不会改变;然而,如果更多的乘客开始乘坐红蓝线之间的 T 线,因为它变得更加方便,这将进一步减少网络上的平均旅行时间。

一条新的快线能给 T 的乘客带来多少好处?

目前,T 没有任何快线。我想知道添加什么样的快速连接是最好的,以及它会带来多大的不同。我应该注意到,我用来确定这一点的指标是相当任意的,但是随着更多的信息和更多的时间,我的模型可以产生更准确的结果。

我看了两个快线场景。在第一种情况下,一列快速列车将在已经存在的轨道上运行,但比正常情况下快 40%(因为它不会在中间停车)。在第二种情况下,一辆特快列车将在两个车站之间的全新轨道上直线行驶,但与其他列车的平均速度相同。

为了确定两种情况下的最佳快速线路,我编写了一个函数(build_best_xline ),测试了给定规范下的每一个可能的连接,并返回平均乘客行程时间减少最多的边。

在这两种情况下,我的算法确定从昆西到波士顿市中心的快速线将是对乘客最有用的快速连接。

在没有铺设新轨道的情况#1 中,公园街到昆西亚当斯将是最好的新连接。在情况#2 中,新线在两个车站之间的直线轨道上运行,最佳新线将是从市中心交叉口到昆西中心

Shown on the maps are the two express lines that my algorithm recommends.

当然,我目前展示的所有发现都是基于一些假设,有很大的误差空间。车站之间的行程时间仅仅是粗略的预测。此外,新快线的规格相当随意。此外,换乘线路时假定的 5 分钟行程时间是任意的,尽管它在为换乘线路分配非零成本方面部分地达到了其目的。但是,由于寻找车站之间的最短路径是我计算的一个重要部分,用更准确和具体的传输时间重做这个项目会很好。我也只使用了在两个 T 站之间旅行的乘客的需求数据;这并没有考虑到 T 上的所有乘客,因为许多乘客从公共汽车站或通勤铁路开始和/或结束他们的旅行。

我认为 T 的这个模型传达了网络的一般行为,但是缺少了许多精确的层次。没有更精确的计算细节,很难说我的结果实际上有多准确。尽管如此,这里还是有一些很酷的外卖。

T 是一个网络,网络的一般性质可以用来理解在 T 上旅行或改进 T 的最有效方式。

我们可以使用介数中心性、度中心性和最短路径的概念来分析网络的潜在改进。理论上,这种分析可以预测对网络的某些修改会有多大帮助。但是要真正理解这些变化的影响,我们还需要预测需求会如何变化——这要困难得多。

在未来的工作中,我希望使用这种类型的分析来推荐增加 T 型车乘客数量的方法。例如,我可以查看优步的需求数据,而不是只查看 T 型车的当前需求。我怀疑,当公共交通不能充分连接两个点时,人们会更频繁地在这两个点之间乘坐优步。因此,研究如何更好地连接通常由汽车服务的成对 T 型站点可能是值得的。我还想扩展网络模型,使其更加全面;显然,公共汽车(和银线……)是一个重要的考虑因素。该模型的未来迭代也可以包括所有这些连接。

我的希望是,通过向您介绍我是如何做到这一点的,您可以自己尝试一下——或者甚至尝试模拟一个不同的交通网络!

如果您对我的流程有任何疑问,或者对您希望我测试的网络的不同修改有任何想法,请在下面留下评论或直接联系我!

感谢所有帮助我实现这个项目的人!感谢 MBTA 为我提供乘客数据来构建需求网络。感谢我的教授 Amir Ajorlou 和我的助教 Paolo Bertolotti 为我的项目提供指导和反馈。

我可以成为你的英雄,宝贝

原文:https://towardsdatascience.com/i-can-be-your-heroku-baby-a5c1fa2edfd9?source=collection_archive---------11-----------------------

在 Heroku 部署 Python 应用程序!

你喜欢数据科学吗?

<上下摇头>

你喜欢数据科学 DIY 部署吗?

<左右摇头>

我也没有。

早期数据科学学习或个人工作中最令人沮丧的部分之一是通过免费的云应用程序部署应用程序。你的代码是最棒的,在本地很管用。我相信你。那么,为什么每次你试图把它推到云端时,它都会爆炸呢?

当然,我具体说的是 Heroku。世界上有十亿本指南,然而我认识的每个人在我们每次尝试部署 Python 应用时都会遇到问题。我们的 Flask 应用程序在本地 Python 服务器上运行良好,但是看似简单的 Heroku 设置会在“创建”或“打开”期间崩溃,让我们对着墙壁大喊大叫……无生命的物体。

不管怎样,重点是赫罗库的性情非常多变。如果一个步骤做得不正确,部署很可能会失败,因此应用程序会崩溃。事实上,在早期,我的努力会变得如此之快,我会删除 Heroku 上的应用程序,然后从头开始。

男孩女孩们,让我的猴子成为你们的马戏团。或者别的什么。下面是 Python apps 的指南来指导你我失败的地方。

  1. 准备您的申请
  2. 创建 Heroku app
  3. 通过 Git 推送到 Heroku

0。但是首先…示例代码&示例应用程序!

目标:懒惰

注意:可以随意叉这个回购,自己试试。这是一个关于肚脐眼的荒谬数据集,但是它的简单性和复杂性使它成为本教程的主要候选对象:链接到回购

1。准备您的申请

目标:无聊的 Python 基础

像大多数项目一样,最好从一个全新的环境开始,所以继续创建、复制或安装一个环境。我这里用的是康达。

$ conda create — name env_name

或者克隆您现有的工作环境

$ source activate env_name

您可以随时通过以下方式查看您的环境列表:

$ conda env list

更多关于管理 Conda 环境的信息请点击:

注意:如果您使用 PyHeroku 中的示例代码,跳过下一步,在 requirements.txt 文件上构建环境。

$ conda install —- yes —- file requirements.txt

安装所有必要的库

有时创建一个全新的 python 环境并不包含根环境的基本库标准。为什么?不知道。没关系。我只是注意到这一点。因此,请确保您已经在环境中安装了运行应用程序所需的一切。

通过在活动环境中调用以下脚本来检查包

$ conda list

如果您缺少必需品(例如熊猫)或任何其他东西(例如 Flask、Flask-SQLAlchemy),请立即安装 pip 或 conda。在这一切都很舒适之后,我们还需要两个软件包,如果你是一个 Heroku noob,它们可能不会被安装。Herokoob。

安装 Gunicorn

这个库是一个高性能的 web 服务器,可以在生产环境中运行他们的 Flask 应用程序。我不会对“如何”进行更多的细节描述,但这就是应用程序工作的原因。在您的环境中:

$ pip install gunicorn

安装 psycopg2
如果你的应用程序使用本地数据库,它很可能使用本地数据库

$ pip install psycopg2

调试 app

不要忘记显而易见的事实。确保你的项目在本地运行。由于我使用 Flask 作为示例,只需“Flask run”您的 app.py。如果有问题,请确保 Flask 应用程序已正确初始化、路由和部署。例子包括

# the top of your flask appapp = Flask(__name__)# a route example[@app](http://twitter.com/app).route(‘/’)
 def home():
 return “Hello, Jeffrey Box. U R Kool with a K.”# the bottom of your flask appif __name__ == ‘__main__’:
 app.run(debug=True)

创建必要的项目文件

现在,我们需要在与 app.py 相同的目录下生成两个文件,它们是 Procfile 和 requirements.txt 文件。Heroku 需要这两者来安装所有的应用程序依赖项,然后利用 Gunicorn 在云中启动我们的应用程序。首先创建 Procfile。

$ touch Procfile

使用终端、代码编辑器、文本编辑器打开 Procfile,只需添加以下文本

web gunicorn app:app

如果您的应用程序碰巧在不同的子目录中,部署将会失败。您可以通过将脚本修改为“gunicorn 子目录. app:app”或类似的内容来回避这个问题,但我不建议这样做。只要把它们都放在根目录下就行了。

最后,我们通过以下方式创建 requirements.txt 文件

$ pip freeze > requirements.txt

注意:这些文件已经存在于 PyHeroku repo 中

2。创建 Heroku 应用程序

目标:唤醒 Heroku Heroku

嗯……如果你还没有 Heroku 账号的话,创建一个。之后,让我们创建第一个应用程序

创建新应用

拥有帐户后,点击“新建”>“创建新应用”。您将始终为您部署的每个应用程序创建一个新的“应用程序”。在下一个屏幕中,创建您的“应用程序名称”。

重要!!!

这是很多人犯错的地方。该名称对于 Heroku 必须是唯一的,但是该名称还必须与您的本地项目目录(包含 app.py、procfile、需求文件的目录)的名称相匹配。在下面的截图中,heroku app 名称为‘pyheroku-tutorial’;目录名为“pyheroku-tutorial”。明白了吗?

但是你真的明白吗?因为如果由于 Heroku 应用程序名称不可用而导致您最终需要修改您的目录名称,这可能会造成 Github 或任何其他代码依赖的问题。现在你明白了,一些非常简单的事情会浪费你几个小时的时间。

一旦完成,点击“创建应用程序”。

为您的数据库配置 Heroku 应用

我们将配置 Heroku 在其末端使用 Postgres。导航到“资源”选项卡。在“加载项”搜索栏中,键入“Heroku Postgres”。它会弹出来。补充一下,但是一定要用免费版!随意 lol 超硬的定价结构。

接下来,单击“设置”选项卡,然后导航到“显示配置变量”按钮。

到数据库的连接字符串现在应该是可用的:
Heroku 会自动将这个 URI 字符串分配给在您的“app.py”文件中使用的“DATABASE_URL”环境变量。已经在 app.py 中的代码将能够使用该环境变量来连接到 heritary 数据库。如果您在 Python 代码中使用 SQLAlchemy,它在 app.py 中可能看起来像这样

app.config[“SQLALCHEMY_DATABASE_URI”] = “sqlite:///db/bellybutton.sqlite”
 db = SQLAlchemy(app)
 …

如果这看起来不熟悉,或者您没有专门初始化数据库,那么您可能不需要修改配置变量或这段代码。我们继续吧。

3。通过 Git 推进到 Heroku

目标:万岁!我们快到了。

有几种方法可以完成下一部分,但是让我们选择最简单的方法,使用 Heroku Git。导航到“Deploy”选项卡,您将看到有关管道的信息以及以下内容:

选择 Heroku Git 为您提供 CLI 说明;然而,我在下面概述了它们。

在您的 CLI 中,确保一切仍在顺利运行,并且您仍处于适当的环境中。然后逐行执行以下命令

$ git init
$ git add .
$ git commit -m “init repo”
$ heroku create
$ git push heroku master
$ heroku open

您的浏览器应该会打开正常运行的应用程序!!!

你做到了!犒劳一下自己,在法国南部进行一次长途散步。一边洗泡泡浴,一边听约翰·泰什的音乐。创建一个全新的 Heroku 应用程序,因为你可以。

但只是为了团结,这里是如何使用 Github,而不是每一个微小的变化和更新都更新和推送到 Heroku git。

加成:Github
我这条“@路线”运气一直不太好……懂了吧……?烧瓶…?😑总之,要这样做,在部署选项卡中,我们选择 Heroku Git

  1. 选择“连接到 Github ”,然后单击底部的按钮。
  2. 在“repo-name”字段中,输入您的 Github repo 的名称,然后单击“Search”。
  3. 点击“连接”,将 Heroku 应用程序与 Github repo 链接起来。
  4. 点击“启用自动部署”,这将允许 Heroku 服务器在您对 Github repo 进行更改时重启您的应用程序。
  5. 最后,点击“资源”标签,然后点击带有铅笔图标的“编辑”按钮。
  6. 向右滑动工人开关,然后点击“确认”。
  7. 交叉手指,向上帝祈祷

希望这有所帮助。这是我的第一篇 Medium 帖子,当我在广阔的数据科学世界中蹒跚前行时,我期待着分享更多的“智慧”。同时,我们都指望你了,Heroku

杰弗里盒子

“我讨厌数学!”—教育和人工智能在我们所做的事情中寻找意义

原文:https://towardsdatascience.com/i-hate-math-part-1-4e793f5a8f72?source=collection_archive---------9-----------------------

你讨厌的是数学的教授方式。

那一大堆方程式、抽象概念和我们不知道的问题的解决方案,我们很难享受那些我们感觉不属于其中的东西。

但是把我们周围世界的一些数学技巧联系起来怎么样?有可能重新发现数学吗?你愿意试一试吗?

这么多问题!让我们和一只可爱的小猫一起放松一下:

可爱的😍!

解数百个方程,解什么“ X 等于”……或者,嗯,学习其他数学概念,比如“导数”(【https://en.wikipedia.org/wiki/Derivative】)是有区别的。

同样,我们解决了几十个不同的问题,包括衍生品。我们练习,解答,再解答,过了一会儿,我们忘记了第一次练习的答案。

当然,有些人乐于解决这类问题,开发新的数学定理,或解决费马大定理(http://www . telegraph . co . uk/science/2016/03/20/why-its-so-impressive-that-fermats-last-theorum-has-solved/),这是一个致力于抽象数学的数学分支。姑且称之为纯数学

放大图像。
来源:http://dominicwalliman.com/

如果你在这一点上喜欢数学,找到了!如果你没有,那我邀请你继续读下去……我们就去应用数学领域

我的个人经历

当我在高中和大学以标准的方式学习数学时,我有点不情愿。练习指南以千克为单位称重,学生们成为解决数学问题的熟练忍者,却忘记了所有这些的目的(除了通过考试),也不知道所有这些的真正用途。

“我为什么要学这个?”这就是问题所在

在大学里,当我协助一个名为“人工智能和机器人”的研讨会时,一切都开始改变。(好酷的名字!)

一到那里,我就体验到了我以前写过的东西:当演讲者在解释人工神经网络时说:

“人工神经网络可以学习…”🙀哇!

他们的学习得益于一种叫做反向传播的算法。通过使用衍生品!!!

所以导数除了通过考试还有别的用处!让我们来说明这一点:

“我们害怕我们不了解的东西。”—很多人。

数学在实践中!

这种算法(反向传播)与现在深度学习(人工智能)中使用的 TensorFlow 框架下的“梯度下降”高度相关。

deep learning——谷歌推出的神经网络的花哨名字,(https://static . Google user content . com/media/research . Google . com/en//pubs/archive/45530 . pdf)。

你不需要知道如何求导。但是,了解其背后的原因可以帮助您:

a)训练你的逻辑技能(比如在困难水平下解数独)
b)开发新的算法。
c) 其他

如果你没有,放松下来,只是保持高水平,同时将过程作为黑盒使用——但是对什么是输入和输出有深刻的理解

免责声明:我不是衍生品的狂热爱好者;其实我今天连怎么推导都不记得了,只记得“指数函数”因为笑话:

来源: Reddit 笑话

反正我的个人经历和这里的不相关。此时最重要的是:

📌当我们学习任何新东西时(抽象的东西更是如此),通过使用诸如“它对什么有用”、“谁在使用它”、“它与我已经知道的任何东西相似吗”、“背后的直觉是什么”等问题进行研究来找到意义是很方便的

📌我发现学习数学时有用的另一个要点是通过编码学习

📌寻找例子——当然我们周围有很多。通过改变代码的参数来播放和销毁代码。使用试错的强大技术。

我们公正的朋友:试错法

我们试了一次,结果却犯了一个大错误。我们再次尝试,得到一个较小的误差,最后,我们最后一次尝试产生最小的误差!

这个误差这么小,也算我们学会了!

(这过于简单化了,但这就是深度学习的学习方式😉)

你不知道吗?现在你知道了。这是一个通过直觉学习的例子,通过使用已知的东西。

下面看一个真实的例子。深度学习就是这样学习的(用 R):

来源:https://keras . r studio . com/articles/training _ visualization . html

在深度学习术语中:

  • 这种损失可以看作是错误。
  • 准确度是…准确度。
  • 每个纪元就是时间。

在: 了解深度学习的介绍 https://medium . freecodecamp . org/want-to-know-how-deep-learning-works-heres-a-quick-guide-for-every one-1 adeca 88076

逆向工程:从人工智能到“现实生活”

当我们为考试而学习时,我们用一个我们知道有结果(蓝线)的练习指南练习几次(epochs),所以我们学习如何解决那些问题(使准确率更高)。

现在老师设置一个考试,我们不知道结果,她/他用已知答案(橙色线)进行评估。

最后的话

当我们学习时,通过联想来做是很方便的(就像我们在最后几段中做的那样)。

与其说我们是一个“方程的数据仓库”,不如说我们作为人类更适合将事物互联,在我们想要探索的知识中寻找目的,对呈现在我们面前的提出质疑

联系概念,使用你真实的“现实生活”知识,实践,并找到你所做的事情的意义。

这就是这篇文章的主旨。

哦..还在吗?看看这个👇

我不能保证它会很容易理解,但我邀请大家阅读我刚刚出版的开源书籍“数据科学活书”📗。

这是我目前从实用和直观的角度教授数据科学的最佳尝试。

这本书可以在http://livebook.datascienceheroes.com获得🚀

谢谢🙂

推特: @pabloc_ds 🐦|| 博客 ✍️.

我有数据。我需要洞察力。我从哪里开始?

原文:https://towardsdatascience.com/i-have-data-i-need-insights-where-do-i-start-7ddc935ab365?source=collection_archive---------1-----------------------

这个问题经常出现。

这通常是刚接触数据科学的数据科学家、分析师和管理人员会问的问题。

他们的老板面临着压力,要求他们展示花在收集、存储和组织数据的系统上的所有资金的投资回报率(更不用说花在数据科学家身上的钱了)。

有时他们是幸运的——他们可能被要求解决一个非常具体且经过充分研究的问题(例如,预测哪个客户可能会取消他们的移动合同)。在这种情况下,有许多方法来剥猫的皮,这是数据科学的天堂。

但通常他们只是被要求“挖掘数据,告诉我一些有趣的事情”。

从哪里开始?

这是一个困难的问题,它没有一个单一的、完美的答案。我确信有经验的从业者已经进化出许多方法来做到这一点。这里有一个我发现很有用的方法。

它基于两个概念:

  1. 每个企业都可以被认为是一个复杂的系统,有许多活动的部分。没有人真正 100%理解它。即使对于有经验的员工来说,他们对业务的理解和实际运作之间也有差距。由于业务不断变化,这种差距总是越来越大。
  2. 你所拥有的任何业务数据都描述了这个复杂系统的行为的某个方面。

鉴于此,你可以把“洞察力”想成是增加你对系统 实际上 如何工作的理解的任何东西。它弥合了你对系统工作方式的看法和它实际工作方式之间的差距。

或者,借用安迪·格罗夫的高产出管理的类比,复杂系统是黑盒,洞察力就像是黑盒侧面的一扇窗户,可以“照亮”里面发生的事情。

所以对洞察力的探索可以被认为是通过分析数据来理解复杂事物是如何运作的努力。

但这是科学家做的事情!这个世界复杂得令人难以置信,他们有一个屡试不爽的剧本来逐渐增加我们对它的了解——科学方法。

非正式地:

利用他们目前对系统如何工作的理解(“理论”),他们做出某些预测。

然后他们检查数据(有时建立精心设计的实验来产生数据),看看它是否与他们的预测相符。

如果没有,他们会深入了解发生了什么,并更新他们的理解(“修改理论”)。

他们做出新的预测。重复循环。

数据科学家和分析师也可以做同样的事情。

在探索数据之前,写下一个简短的列表,列出您期望在数据中看到的内容:关键变量的分布、重要变量对之间的关系等等。这样的列表本质上是基于你当前对业务的理解的预测。

现在分析数据。制作情节,做总结,无论需要什么,看看是否符合你的预期。

有什么不符合的吗?任何让你觉得“很奇怪”或“没有任何意义”的事情。?

放大并尝试理解在您的业务中是什么使这种奇怪的事情出现在这样的数据中。这是关键的一步。

您可能刚刚发现了对业务的洞察力,并增加了您的理解*。

这里有一个真实的例子。几年前,我们在查看一家大型 B2C 零售商的交易数据。数据集中的一个字段是“交易金额”。

我们期待看到什么?嗯,我们预计大部分金额会在平均值左右,但可能会有一些较小的金额和一些较大的金额。所以磁场的直方图可能看起来像这样:

但是当我们检查数据时,我们看到的是:

我们调查了“嗯”。

原来这些交易不是由典型的购物者——为孩子购物的年轻妈妈们进行的。它们是由每年从国外到美国旅行一次的人制作的,他们走进一家商店,买很多东西,带回到他们的国家,在他们自己的商店里出售。他们是经销商,与我们的零售商没有特殊关系。

这家零售商当时在北美以外没有实体业务,也没有从他们的电子商务网站向这些地方发货。但是国外有足够的需求,当地企业家涌现来填补这个空白。

这一小小的“发现”引发了一系列有趣的问题:这些经销商购买的是什么类型的产品,什么样的促销活动最适合他们,甚至这些数据如何用于制定全球扩张计划。

全部来自一个简单的直方图。

精彩的艾萨克·阿西莫夫完美地抓住了这种精神。

在科学界听到的最激动人心的短语,也就是预示着新发现的短语,不是“尤里卡!”但是“这很有趣……”

艾萨克·阿西莫夫

请注意,从数据追溯到业务中的“根本原因”需要时间、精力和耐心。如果你在商界有一个很好的关系网,可以回答你的问题,你的工作效率就会更高。此外,对你来说奇怪的事情对他们来说可能是显而易见的(因为他们对业务的理解可能比你更好),你可以节省时间。

总的来说,你越了解业务的细微差别,你的预测就越有针对性,最终你会发现更好的洞察力。所以,尽你所能去了解业务的细节。寻找了解业务的同事,向他们学习,如果可能的话,让他们成为你的合作伙伴。

数据科学知识显然是一件好事,但是您的业务知识将对您的工作质量产生更大的影响。

除了数据科学工作之外,我发现这种“预测并检查”的心态在查看任何分析时也很有用。

在“翻页”之前,暂停几秒钟,猜猜你会看到什么样的东西。你可能会发现这增加了对比度,并且你能够更好地在数字的海洋中发现有趣的事情。

  • 或者你可能会发现你的数据收集或计算方式有问题

如果你对这篇文章感兴趣,你可能会喜欢阅读:

[## 首先创建一个常识基线

当你着手解决一个数据科学问题时,很容易一头扎进去,开始构建模型。

towardsdatascience.com](/first-create-a-common-sense-baseline-e66dbf8a8a47) [## 如何在日常分析工作中使用因果推理(第 1 部分,共 2 部分)

在商业领域工作的分析师和数据科学家充斥着大量的观察数据。这些数据是…

towardsdatascience.com](/how-to-use-causal-inference-in-day-to-day-analytical-work-part-1-of-2-b5efbdbf8ab0) [## 如何在日常分析工作中使用因果推理——第 2 部分,共 2 部分

在第 1 部分中,我们研究了如何使用因果推理得出正确的结论——或者至少不会跳到错误的结论…

towardsdatascience.com](/how-to-use-causal-inference-in-day-to-day-analytical-work-part-2-of-2-1824e7024cd2)

我只是没有时间做出更好的决定…

原文:https://towardsdatascience.com/i-just-dont-have-time-to-take-better-decisions-2dc82cb26f16?source=collection_archive---------6-----------------------

The Right Scoop

前水门事件记录者鲍勃·伍德沃德上周末充满激情地讲述了在为自己做决定和影响周围人时,花时间弄清事实的重要性。[1]听众中那些潜力巨大的经理们苦笑了一下,因为他们非常清楚现代管理的压力已经使时间成为最稀缺的商品。他们每天有太多的决定要做——根本没有时间去思考最好的真相。

在这种情况下,我们为什么要花时间去改善我们的决策呢?毕竟,管理决策是一个耗时的过程。我们工作中固有的模糊性、复杂性和风险可能会促使许多经理尽可能少地做出决策。许多人认为,近五十年的业务流程改进已经在很大程度上消除了解决简单问题的需要——我们可以遵循程序,阅读脚本,如果情况变得更糟,只需在我们前进的过程中编造事实。剩下的问题:在不断变化的经济环境中优化职业选择,促进工作场所的参与度和幸福感,实际上帮助客户解决他们的问题,这些问题可能太复杂,无法花任何时间来解决。他们认为,除了唾手可得的水果,你不应该浪费时间去追求任何东西。

尽管这种推理看起来很实际,但在得到进一步通知之前,经理们是靠解决问题赚钱的。问题越难,潜在的回报就越大。有些依靠直觉,有些运用分析。在概率论中,解决企业实际问题的机会成本通常在开发或探索场景中建模。是相信我们自己的经验更有利可图,即使不能解决问题,还是花时间去探索提供更令人满意结果的新替代方案?在决策科学中,Gitten 指数、置信上限,甚至杰夫·贝索斯的内疚最小化框架都为探索新的推理路线的价值提供了压倒性的证据。[2]

管理就是在时间投资和成功投资之间找到恰当的平衡。改善管理决策包括学会识别我们试图解决的问题的本质以及我们所掌握的数据的质量。机器学习意味着对人类经验进行编码,以检测给定手边问题的最佳、更好或难忘的决策。管理团队和社区需要将数据转化为有影响力的决策——包括我们自己的以及我们的客户、团队和利益相关者的决策。所有这三个学科都有一个共同的目标,那就是帮助管理层明智地使用他们的时间。

商业分析是关于校准思维以做出更好的决策。就像一个网球运动员试图优化他的反手击球一样,时间是一项投资,可以用得其所,也可以用得其所。利用我们对自己的了解和任何一个游戏的背景只会让我们到此为止。球场外的时间也需要用来分析手头挑战的性质,以及探索比赛的新选择和新心态。如果天才的直觉有时能够赢得胜利,那么分析为我们所有人提供了游戏发展的空间。谚语“熟能生巧”依赖于花时间开发最容易获得的真理版本。

商业分析实践是商业分析研究所的核心和灵魂。在巴约纳的暑期学校,以及在欧洲的大师班,我们让分析为您和您的组织服务。该研究所专注于管理人员数据科学的五个应用:在数字时代工作、数据驱动的决策、机器学习、社区管理和视觉通信。数据驱动的决策会对你未来的工作和职业生涯产生影响。


[1]P .卡尔法斯,j .(2017 年)。阅读鲍勃·伍德沃德和卡尔·伯恩斯坦在白宫记者晚宴上的建议,时代杂志,2017 年 4 月 30 日,http://Time . com/4760743/White-House-conductors-Dinner-Woodward-Bernstein-speech-2017/

[2]克里斯蒂安和格里菲思(2016 年)。《赖以生存的算法:人类决策的计算机科学》,亨利·霍尔特公司,纽约

我,机器人和人力资源总监

原文:https://towardsdatascience.com/i-robot-and-hr-director-6b1604921870?source=collection_archive---------18-----------------------

人工智能被专注于软技能的部门采用和使用只是时间问题。传统上,人力资源管理是心理学家和其他更具人文精神的专家的领域。计算机能代替多年的经验和人类互动来评估最佳候选人吗?

事实上,人工智能的作用是与人力资源经理和招聘人员并肩工作,向他们伸出援助之手,并承担一些底层工作。采用这一系统有望提高准确性、降低成本并最终加快流程,而现在从开始到结束可能需要几个月的时间和数千美元的成本。

工作流程管理

像在其他领域一样,引入自动化工具对各种过程都有积极的影响。第一个变化是速度和节奏的变化。其他改进包括流程标准化和消除偏见。

候选人筛选

目前,候选人筛选占据了大部分时间。主要的问题是许多申请人不符合他们申请的职位的条件。Glassdoor 声称大多数候选人在简历中撒谎,或者至少美化他们的简历。另一项研究详细说明了这种详述包括夸大他们的技能、以前的职责、职称、学位、公司和奖励。当然,更严重的隐瞒与他们被解雇的原因和犯罪记录有关。

人工智能通过其检测模式的能力,将成为根据一些预先定义的标准筛选简历的完美工具。在初步筛选排除了第一批不合适的候选人后,进一步的调查可能会发现一些危险信号,比如与以前的经验不匹配的技能、虚假的推荐信等等。

改善和规范职位匹配

LinkedIn 等平台以及专有的人力资源管理系统包含大量信息,可用于训练算法,以识别候选人的技能组合、职位甚至成长路径之间的最佳匹配。

更好的工作匹配有大量的长期优势,包括更快乐、更有效率的员工,他们不太可能换工作。来自 InData Labs 的人工智能开发人员声称,随着系统的学习和发展,它将能够通过快速浏览上传的简历来找到合适的候选人,甚至通过搜索公开信息和识别最佳人选来取代猎头。

情感分析

如今有很多关于政治正确、行为公正和不偏不倚以及消除任何形式的工作场所歧视的言论。然而,旧习难改,有时一个良好的意图可能会适得其反。人工智能可以帮助识别潜在的性别、种族或职业偏见,并建议更好的词语,以非对抗性的方式表达相同的想法,适合全球化的世界。

这一切都从招聘启事开始,招聘启事需要清晰、简洁,用公司自己的声音写出来。阅读它应该让潜在的候选人感觉到他们的个性和公司的个性是否匹配。情感分析可以指示公告的文本是更有趣、公司还是学术。

商业模式

尽管人工智能可以帮助削减一些关键的招聘成本,但它仍然需要定义其工作的商业模式。招聘是一种行为,只有当一个完美的候选人或一份优秀的工作被匹配时,才能为客户创造价值。因此,按成功付费是合理的。

这使得提供此类服务的公司现金流波动,可能很快导致破产,或者至少让它们陷入生存模式,而不是提供增长机会。

为了成功地提供基于人工智能的招聘服务,有必要要么确定对员工需求高且相对容易找到技能的活动部门,要么确定除准时雇佣之外提供价值的方法,以证明经常性费用的合理性。

例如,这样的公司可以创建一个人力资源聊天机器人,取代该部门执行的一些乏味的工作,如回答员工的日常询问,就像银行机器人为客户做的一样。

伦理问题

我们之前提到过人工智能是一种消除任何偏见的工具,但这只是在用于训练系统的数据已经针对这些错误进行了检查的情况下。毕竟,人工智能的行为很像一个孩子,无论教它什么,它都会繁殖和延续。

这方面的一个主要例子是微软的 Tay bot,由于用户的输入,它在几个小时内就喷出了恐同和纳粹言论。同样,犯罪预防机制正在根据种族和教育做出假设。这些模式虽然有统计学上的原因支持,但对那些有前途的候选人来说可能是有害的,因为他们是各自阵营中的局外人。

当人工智能成为一种工具时,个人数据安全和隐私也是一个重要的问题。由于它只能通过大量数据来发挥作用,因此可以将 AI 视为对个人隐私的威胁。尽管 GDPR 的法规努力给这种混乱带来一些秩序,并防止未来剑桥分析公司的丑闻,但仍不清楚现有的立法框架是否足够。

今后

即使人工智能不会很快让人力资源专家失业,它也会带来一些新的工作和招聘方式。从好的方面来看,人工筛选不合适的候选人可能会节省大量的时间和精力。当然,使用这样的系统需要一定的学习过程,这甚至会降低常规操作的速度。

另一方面,人力资源人员可能会发现他们被从一个乏味的任务重新分配到另一个任务。由于人工智能需要良好的数据来学习,他们可能会陷入标记数据是否合适或排列候选人的枯燥工作中,只是为了给系统提供一组良好的信息。这被称为监督学习,对于人力资源来说,这可能是最好的方法,因为无监督系统会自己做出决定,这可能不一定是成为好同事和好员工的最佳方式。

我从 BuzzFeed 上搜集了 NYPD 警察纪律案件的数据库

原文:https://towardsdatascience.com/i-scraped-buzzfeeds-database-of-nypd-police-disciplinary-cases-74a30bb5fde8?source=collection_archive---------9-----------------------

BuzzFeed 的数据很棒,但我们能以一种更有用的格式收集它吗?

Photo by Dane Tewari on Unsplash

TL;博士: BuzzFeed 今天发布了一组有趣的数据——大约 1800 名被“指控行为不当”的纽约警察局(NYPD)雇员的纪律案件档案我写了一个 scraper 来下载 PDF 和纯文本格式的数据进行大规模分析。

不幸的是,案例文件的存储方式不便于大规模分析。每个案例文件都以单独的 PDF 格式存储,但是没有明确的方法下载所有的文件。原始文本存储在 JavaScript 界面中的选项卡后面。

我想对这些数据进行一些基于文本的分析,但是为了做到这一点,我需要每个案例文件的原始文本(最好是 pdf)。手动下载每一个都很耗时,所以我决定构建一个刮刀来收集数据。

下载 PDF 数据

首先,BuzzFeed 提供了一个有用的 CSV 文件,其中包含每个案例文件的 URL。

A few rows from the BuzzFeed CSV.

CSV 中的链接会将您带到存储在 DocumentCloud 上的案例文件。该接口主要是 JavaScript,这使得抓取更具挑战性,因为没有太多的 HTML。

Each case file has been converted to plain text via optical character recognition (OCR), though the conversion is fairly messy.

我的第一个目标是下载 PDF 格式的所有案例文件。PDF 文件存储在与 BuzzFeed CSV 中的 URL 结构非常相似的 URL 中。通过一点 regex,我能够将 DocumentCloud URLs 转换为 PDF 资产的 URL,并使用 Python 的 requests 库下载它们。

A few regular expressions format the URL correctly for downloading the PDF.

下载文本数据

下载转换后的纯文本更具挑战性。纯文本位于 DocumentCloud JavaScript 界面中,在一个名为 text 的选项卡后面。通过 HTML 抓取文本是不可行的,因为它不存在于页面的常规源代码中。对于 Selenium 这样的 web 驱动程序来说,这是一个自然的用例,它允许您像人类一样与 web 页面进行交互。

为了获取数据,我需要 Selenium 单击 Text 选项卡,以便下载纯文本。我需要一种可靠的方法来访问 Selenium 中的文本选项卡,所以我使用了 Chrome 的开发工具(在 Chrome 中,右键单击感兴趣的元素,然后单击 Inspect) 来获取文本选项卡的 XPath。 XPath 是一种查询语言,它使得在网页上查找特定元素变得更加容易。有时候自己编写 XPath 查询更好,因为这样会更灵活。在这种情况下,Chrome 的 XPath 足以让我每次都能看到文本标签。

Chrome Developer Tools makes XPath easy. Right click on the tag of interest and choose Copy >> Copy XPath.

使用 XPath 查询,我指示 Selenium 单击 Text 选项卡。通过检查 Chrome 开发工具中的文本,不难获得纯文本的 HTML 类的名称。我可以使用 Selenium 的 text 属性将原始文本下载到一个文件中。

最后,我编写了一个循环来为 CSV 中的每个 URL 下载 PDF 和原始文本文件。现在,我有了一个数据语料库,可以对其应用我自己的 OCR 算法或建立文本挖掘分析。

一般来说,没有一种“正确的”方法可以从网络上抓取数据。在这种情况下,我没有使用基于 HTML 的抓取(例如,使用像请求这样的库),但是逆向工程 URL 和 Selenium 抓取的结合给了我所需要的。

如果您想下载 BuzzFeed 数据集用于您自己的分析,请在这里克隆我的刮刀并让我知道它是如何为您工作的!

我支持向量机,你也应该支持。

原文:https://towardsdatascience.com/i-support-vector-machines-and-so-should-you-7af122b6748?source=collection_archive---------4-----------------------

大约一周前,我在大会上做了一个关于支持向量机的演讲。这是一个介绍性的演讲,旨在揭开支持向量机模型的神秘面纱,支持向量机模型非常强大,但其内部工作原理可能有点难以理解。如果你对这类事情感兴趣的话,一定要看看这个视频,但是我在这里也要讲同样的内容。你将会错过一些我本人的魅力和个人魅力,并因此变得不那么重要。

Man, I move my arms a lot.

好吧,支持向量机有什么用?它们是一种机器学习,允许计算机获取一组数据,并将其分为两组(或通过将任何一组与所有其他组进行比较而分为更多组)。我们可以使用它们来对基本上任何东西进行分类,从获取金融信息来决定某人是否可能拖欠贷款,到图像信息,以便计算机可以决定某物是狗还是猫。它们的一个好处是最大化两组之间的界限(或空间),以允许计算机以前没有看到的新观察被更好地分类。他们还可以利用一种叫做内核技巧的东西,我将很快解释这一点。

基本上,计算机使用大量的数学,youtube 上的聪明人可以向你解释,在已经标记的数据组之间画一条线,然后使用这条线来预测新的观察结果属于哪个类别或组。仔细想想,还是比较可观的。我们可以自然地看到下面的图表,并意识到在哪里最好地画一条线来区分蓝色和红色的 X,但实际上有很多不同的可能性,找到聪明的方法让计算机识别最好的是大企业。

One of these lines is better than the others

从数学上来说,计算机在数据之间画一条线,在两个方向上移动其他线,并旋转这些线,直到它在任何一边都碰到观测值。

The computer tries to increase the green area to its maximum

它的名字来源于这些最终支持模型的向量。这些向量也是计算机需要保留的唯一重要信息,因为所有其他点对模型或预测没有影响。

The aforementioned support vectors!

所有这些看起来很简单,对吗?确实是!虽然从技术上来说,我们只建立了一个最大间隔分类器。如果我们对有一些重叠或极端异常值的事物进行分类,这种方法将会失败。想象一下,你正试图区分猫和狗,而有人把一只吉娃娃扔了进来!或者,上帝保佑,一只西施犬。没有电脑能区分这些,对吗?不对。我们只是告诉我们忽略他们!要是人们这么容易编程就好了…

在下面的 GIF 图中,你可以首先看到一个混合群体,计算机无法用数学方法在他们之间画一条线。通过忽略两个点,它能够找到最佳支持向量,并绘制我们的线。在 GIF 的后半部分,一个极端的异常值(臭名昭著的西施犬)会将我们的线推得太靠近红色类,导致我们的模型对未来的预测分类错误。教导计算机一些观察结果根本不符合我们通常的预期,这在建模中非常重要,并防止过度拟合我们给它的任何训练数据。

Overlapping classes and extreme outliers can be overcome with support vector machines with careful tuning

好的。现在所有这些可视化显示了数据的 2D 表示。如果我们对狗和猫进行分类,就好像我们只看到了关于它们的两条信息。也许 x 轴代表他们的体重,y 轴代表,你知道,天生邪恶什么的。所有这一切都在 3 维及以上的空间中进行。我们在画平面(或 4D 及更远地方的超平面),而不是线,但一切还是一样的。看,这是同样魔术的 3D 照片:

I’d show you 4D, but I was swore to secrecy

到目前为止还不错,是吗?现在我们进入真正的魔术:内核技巧。所以,我相信你可以想象许多不同的数据集或图表,你不能简单地通过它们画一条线/一个平面/任何东西。被蓝色海洋包围的一簇红色是不可能被划一条线穿过的。数学又来拯救我们了。在下面的例子中,我们有 1D 的数据,无论我们在哪里画线,我们都不能把我们的组分开。这个例子中的核心技巧是用第一维的平方增加另一维。如果我们只是在谈论猫和狗的重量,就好像我们决定也告诉计算机它们重量的平方。对我们来说,这毫无意义,但是看。

天哪,我说的对吗?现在从 2D 到 3D 观看同样的东西!

That’s some mathematical magic!

这只是一个超级简单的内核技巧。人们已经为支持向量机想出了一些奇特的方法,这使得他们能够处理一些非常复杂的事情。如果你在增加一个维度后仍然有困难,没有人说你不能增加更多的维度!疯狂。

如果你想了解更多关于内核和一些更有效的内核,请查看 Eric Kim 写的这篇文章。就这些东西而言,它相当容易接近。

如果你对支持向量机其他方面背后的数学感兴趣,我推荐 youtube 上的这两个视频:
乌迪·阿哈尼:https://www.youtube.com/watch?v=3liCbRZPrZA
特梅尔·比利西姆:https://www.youtube.com/watch?v=5zRmhOUjjGY

我希望这有助于揭开支持向量机的神秘面纱,并教会你在开始用它们建模时,在引擎盖下发生了什么的基础知识。干杯。

我训练了一个严格按照福克斯新闻频道广播饮食的 Word2Vec 模型

原文:https://towardsdatascience.com/i-trained-a-word2vec-model-on-a-strict-diet-of-fox-news-broadcasts-14da0b174b11?source=collection_archive---------7-----------------------

这是它对世界的看法。

Screenshot of my attempt at a visually representing word embeddings. See the original here.

背景

几个月前,我第一次开始尝试 Word2Vec,当时我在 NYU 大学为一门文本分析课程做项目。该项目是一种概念验证,包括收集和分析数百万西班牙语 YouTube 评论,试图检测和测量政治导向的言论。

虽然 Word2Vec 实际上不是我们在本课程中学习的模型之一,但它捕捉单词之间微妙关系的能力给我留下了深刻的印象。

分析用户生成的西班牙语文本的一个主要问题是拼写——尽管有很大程度上的音位拼写,我发现到处都有拼写和语法错误。

不幸的是,目前可用的停用词词典只包括单词的正式拼写,这实际上比某些术语的错误拼写更不常见。更糟糕的是,拼写错误如此之多,以至于无法通过调整词频或缩减采样来消除。

Word2Vec 来救援!通过选取一个常见的拼写错误,并在模型中查询 50 个最相似的单词,我能够构建一个全面的停用词字典来过滤它们。

Fifty common but not super-common variations on the word “haha”? Not funny!

那么,为什么是福克斯新闻频道?

上面的实验真正说明了 Word2Vec 揭开语言“个性”的真正力量。我想:如果我训练一个 Word2Vec 语言模型,它以一种非常微妙的方式只代表现实的一种视觉,会怎么样?我唯一能想到的英语候选人是福克斯新闻频道。

挑战

获取文本

虽然福克斯新闻频道实际上在其网站上制作书面文本,但我想要一个考虑到整个福克斯体验的语料库:嘉宾评论、即兴评论、主持人之间的戏谑等。

我家里没有有线电视,所以我建立了一个网络抓取器,提取了当时福克斯新闻频道网站上所有视频的音频——大约 1150 个剪辑,长度从 1 分钟到 20 分钟不等。虽然一些视频可以追溯到 2015 年,但绝大多数是在过去六个月发布的。

为了转换音频,我使用了谷歌的语音识别 API,因为它产生的结果比任何其他服务都好得多(加上他们给你 300 美元的免费积分)。我在这里解释我是如何做到这一点的

哦,标点符号…

语音识别模型的一个不幸之处是,它们返回的文本实际上没有任何标点符号。这在使用 Word2Vec 时特别烦人,因为您需要向它输入标记化的句子(需要标点)。

幸运的是,奥托卡·提尔克已经掩护了我。他训练了一个双向递归神经网络模型,可以恢复英语文本中的标点符号。最棒的是,这个了不起的人还创造了一个 API ,你可以很容易地从 Python 中查询。

唐纳德卡车在房子里!

没错。谷歌并非完美无瑕。有时它会误解某些单词和短语,尤其是当人们互相谈论的时候。例如,与迈克尔·弗林相关的最常见术语之一是“律师”,但“锦标赛”一词也出现在前 20 名中。

我最初的策略是尝试使用变音编码和模糊字符串匹配来发现这些错误。然而,事实证明这比我原先预计的要花更多的时间,所以我搁置了这个想法。

最终,我能够调整 Word2Vec 模型的参数,以最小化不正确术语的影响。

结果

该模型接受了约 50 万个术语的训练——对于 Word2Vec 来说,这不是一个庞大的语料库,但结果仍然非常有趣。我列出了大约 24 个与当前事件或政治问题相关的术语,找到了与它们最相关的词,并将它们添加到(蹩脚的)D3js 图中。

不幸的是,Medium 不允许我嵌入 JavaScript vizualiations,所以你必须在这里查看。

一如既往,我希望听到您的反馈或建议。此外,如果你对我是如何做上述任何事情感到好奇,不要犹豫,伸出手来!

我训练假新闻检测 AI 准确率> 95%,差点疯了

原文:https://towardsdatascience.com/i-trained-fake-news-detection-ai-with-95-accuracy-and-almost-went-crazy-d10589aa57c?source=collection_archive---------0-----------------------

Fake news is still a real problem

TL;dr——我们用机器学习和自然语言处理制作了一个准确率超过 95%的假新闻检测器,你可以在这里下载。在现实世界中,准确率可能会更低,尤其是随着时间的推移和文章写作方式的改变。

随着自然语言处理和机器学习的如此多的进步,我想也许,仅仅是也许,我可以制作一个模型,可以标记新闻内容为假,也许可以减轻假新闻泛滥的毁灭性后果。

可以说,制作自己的机器学习模型最困难的部分是收集训练数据。我花了很多天收集 2017/2018 赛季每个 NBA 球员的照片,以训练一个面部识别模型。我一点也不知道我会陷入一个痛苦的、长达数月的过程中,暴露出一些真正黑暗和令人不安的事情,这些事情仍然被作为新闻和真实信息传播。

定义假新闻

我的第一个障碍出乎意料。在对假新闻做了一些研究后,我很快发现误传可以分为许多不同的类别。有些文章是明显虚假的,有些文章提供了真实的事件,但随后做出了一些错误的解释,有些文章是伪科学的,有些文章实际上只是伪装成新闻的观点,有些文章是讽刺性的,还有一些文章主要是由推特和其他人的引用组成的。我在谷歌上搜索了一下,发现有些人试图将网站分成“讽刺”、“虚假”、“误导”等类别。

我认为这是最好的起点,所以我继续前进,开始访问这些领域,试图寻找一些例子。几乎立刻我就发现了一个问题。一些被标记为“虚假”或“误导”的网站有时会有真实的文章。所以我知道,如果不进行健全性检查,就无法清除它们。

然后,我开始问自己,我的模型是否应该考虑讽刺和观点作品,如果应该,它们应该被视为假的,真实的,还是被归入自己的类别?

情感分析

在盯着假新闻网站看了大约一周后,我开始怀疑自己是否已经把问题过于复杂化了。也许我只是需要在情感分析上使用一些现有的机器学习模型,看看是否有一种模式?我决定构建一个快速的小工具,使用 web scraper 来抓取文章标题、描述、作者和内容,并将结果发布到情感分析模型。我使用了 Textbox ,这很方便,因为它在我的机器上本地运行,并快速返回结果。

文本框返回一个情感分数,你可以将其解释为正面负面。然后,我构建了一个蹩脚的小算法,为我提取的不同类型文本(标题、内容、作者等)的情感添加权重。)然后全部加在一起,看看能不能得出一个全局的分数。

起初它工作得很好,但是在我尝试了大约第 7 或第 8 篇文章之后,它开始下降。长话短说,它与我想要建立的假新闻检测系统相去甚远。

失败。

自然语言处理

这是我的朋友大卫·赫南德兹推荐的,实际上是在文本本身上训练一个模型。为了做到这一点,我们需要很多很多不同类别的例子,我们希望模型能够预测。

由于我很难理解假新闻的模式,我们决定试着去搜索那些已知的假的、真实的、讽刺的领域。看看我们能否快速建立一个数据集。

在运行原油刮刀几天后,我们有了一个我们认为足够大的数据集来训练一个模型。

结果糟透了。深入研究训练数据,我们意识到,这些领域从来没有像我们希望的那样被划分成整齐的小类别。其中一些是假新闻混合真实新闻,另一些只是来自其他网站的博客帖子,还有一些只是 90%的文本都是特朗普推文的文章。所以我们意识到我们必须从训练数据开始。

这是事情变糟的时候。

那是一个周六,我开始了漫长的过程,手动阅读每一篇文章,然后决定它属于哪一类,然后笨拙地将文本复制并粘贴到一个越来越笨重的电子表格中。有一些黑暗的,令人厌恶的,种族主义的,真正堕落的东西,我读了,起初我试图忽略。但是在阅读了数百篇这样的文章后,他们开始影响我。随着我的视力模糊,我对颜色的理解变得一塌糊涂,我开始变得非常沮丧。文明是怎么沦落到如此地步的?为什么人们不能进行批判性思考?我们真的还有希望吗?这种情况持续了几天,因为我在努力为这个模型找到足够多的例子。

我发现自己在自己对假新闻的解读中随波逐流,当我看到我不同意的文章时会感到愤怒,并努力克制只选择我认为正确的文章的冲动。到底什么是对的或错的?

但是最后,我找到了我一直在寻找的神奇数量的例子,并且如释重负地把它们通过电子邮件发给了大卫。

第二天,当我急切地等待结果时,他又开始了训练。

我们达到了大约 70%的准确率。起初我认为这很棒,但是在对野外的文章做了一些抽查后,我意识到这对任何人都没有用。

失败。

Fakebox

回到绘图板。我做错了什么?大卫提出,也许简化问题是提高准确度的关键。所以我认真思考了我想解决的问题是什么。然后它击中了我;也许答案不是检测假新闻,而是检测真新闻。真正的新闻更容易归类。它实事求是,切中要害,几乎没有解释。有很多可靠的来源可以得到它。

所以我回到网上,重新开始收集训练数据。我决定把所有的东西分成两类:真实和不真实。Notreal 包括讽刺文章、观点文章、假新闻,以及其他所有不以纯粹事实的方式撰写的文章,这些文章也符合美联社的标准。

我花了几周时间做这件事,每天花几个小时从你能想象到的各种网站获取最新内容,从 《洋葱》【路透社】 。我把成千上万真实和非真实内容的例子放入一个巨大的电子表格中,每天我都会添加数百个。最终,我决定我有足够的例子再试一次。所以我把电子表格发给大卫,不耐烦地等待结果。

当我看到准确率达到 95%以上时,我高兴得差点跳起来。这意味着我们在文章的写作方式中发现了一种模式,可以发现真实新闻和你应该半信半疑的东西之间的差异。

成功(算是)!

停止假新闻

这个练习的全部目的是阻止错误信息的传播,所以我很高兴与你们分享这个模型。我们称之为 Fakebox ,它非常容易使用。

粘贴您不确定的文章内容,然后单击分析。

用一个好的 RESTful API 将其集成到任何环境中。它是一个 Docker 容器,所以你可以在任何你喜欢的地方部署和扩展它。随心所欲地快速制作无限量的内容,并自动标记可能需要关注的内容。

记住,它告诉你的是,如果一篇文章的写作方式与一篇真实的新闻文章相似,那么如果分数真的很低,这可能意味着这篇文章是假的,是一篇观点文章,是讽刺文章,或者不是一篇直截了当、只讲事实的新闻文章。

总之,我们训练了一个机器学习模型,它分析一篇文章的写作方式,并告诉你它是否类似于一篇用很少或没有偏见的词、强烈的形容词、观点或丰富多彩的语言写的文章。如果一篇文章太短,或者主要是由他人的引用(或推文)组成,这可能会很困难。这不是解决假新闻的最终办法。但是希望它能帮助你发现那些需要半信半疑的文章。

请欣赏!

我想学人工智能和机器学习。我能从哪里开始?

原文:https://towardsdatascience.com/i-want-to-learn-artificial-intelligence-and-machine-learning-where-can-i-start-7a392a3086ec?source=collection_archive---------0-----------------------

我是如何从苹果天才到创业失败再到优步司机再到机器学习工程师

The trick is to café hop until you find one which has great coffee and plenty of natural light. Then studying becomes easy. Photo by Madison Kanna. Thank you, xoxo.

我在苹果商店工作,我想改变一下。开始制造我所服务的技术。

我开始研究机器学习(ML)和人工智能(AI)。

事情太多了。太多了。

似乎每周谷歌或脸书都在发布一种新的人工智能,以使事情变得更快或改善我们的体验。

不要让我开始谈论自动驾驶汽车公司的数量。这是一件好事。我不喜欢开车,道路很危险。

即使发生了这一切,人工智能到底是什么仍然没有一个一致的定义。

一些人认为深度学习可以被认为是人工智能,其他人会说除非它通过图灵测试,否则它不是人工智能。

这种定义的缺乏在一开始确实阻碍了我的进步。学习有这么多不同定义的东西很难。

定义说够了。

我是怎么开始的?

我和我的朋友正在建立一个网络创业公司。失败了。由于缺乏意义,我们放弃了。但是一路走来,我开始听到越来越多关于人工智能和人工智能的事情。

“电脑帮你学东西?”我简直不敢相信。

偶然发现了 Udacity 的深度学习纳米学位。一个叫 Siraj Raval 的有趣角色出现在其中一个宣传片中。他的能量具有感染力。尽管没有达到基本要求(我以前从未写过一行 Python),我还是签了名。

在课程开始前 3 周,我给 Udacity 支持部门发了电子邮件,询问退款政策。我害怕自己无法完成这门课程。

我没有得到退款。我在指定的时间内完成了课程。这很难。有时候真的很难。我的前两个项目晚交了四天。但是参与世界上最重要的技术之一的兴奋驱使我前进。

完成深度学习纳米学位后,我保证被 Udacity 的人工智能纳米学位、自动驾驶汽车纳米学位或机器人纳米学位录取。所有伟大的选择。

我又迷路了。

经典。“我下一步去哪里?”

我需要一个课程表。我已经用深度学习纳米学位建立了一个基础,现在是时候弄清楚下一步是什么了。

我自创的人工智能硕士学位

我没有打算近期重返大学。反正我也没有 10 万美元去读一个真正的硕士学位。

所以我做了一开始做的事。向我的导师谷歌寻求帮助。

我在没有任何该领域知识的情况下就投入了深度学习。我没有爬到人工智能冰山的顶端,而是被一架直升机送到了顶端。

在研究了一堆课程之后,我在特雷罗列出了我最感兴趣的课程。

Trello is my personal assistant/course coordinator.

我知道在线课程的辍学率很高。我不想让自己成为这个号码的一部分。我有任务在身。

为了让自己负起责任,我开始在网上分享我的学习历程。我想我可以练习交流我学到的东西,并找到和我有相同兴趣的人。我的朋友们仍然认为我是一个外星人,当我进行一次人工智能的恶作剧时。

我公开了特雷罗董事会,并写了一篇关于我的努力的博客。

自从我第一次写这本书以来,课程略有变化,但它仍然是相关的。我会每周多次访问 Trello 板来跟踪我的进展。

找工作

我是澳大利亚人。所有的骚动似乎都发生在美国。

于是我做了最符合逻辑的事,买了一张单程票。我已经学习了一年,我想是时候开始把我的技能付诸实践了。

我的计划是去美国,然后被雇佣。

然后阿什莉在 LinkedIn 上给我发消息说,“嘿,我看了你的帖子,他们真的很酷,我想你应该见见迈克。”

我遇见了迈克。

我告诉他我在网上学习的故事,我是多么喜欢 healthtech 和我去美国的计划。

“你最好在这里呆一年左右,看看你能找到什么,我想你会喜欢见到卡梅伦。"

我遇到了卡梅隆。

我们进行了一次类似迈克和我所谈论的谈话。健康,科技,在线学习,美国。

"我们正在研究一些健康问题,你为什么不在星期四来?"

星期四来了。我很紧张。但是有人曾经告诉我紧张和兴奋是一样的。我变得很兴奋。

我花了一天时间会见了 Max Kelsen 团队以及他们正在解决的问题。

两个星期四后,我和首席执行官尼克、机器学习首席工程师阿森去喝咖啡。

"你愿意加入这个团队吗?"尼克问道。

“当然,”我说。

我的美国航班推迟了几个月,我买了一张返程票。

分享您的作品

在网上学习,我知道这是非传统的。我申请的所有职位都要求硕士学位,或者至少是某种技术学位。

这两样我都没有。但我确实拥有从大量在线课程中收集到的技能。

一路上,我在网上分享我的作品。我的 GitHub 包含了我做过的所有项目,我的 LinkedIn 已经被摊开,我已经练习过通过 YouTube 和 Medium 上的文章来交流我所学到的东西。

我从没给麦克斯·凯尔森交过简历。“我们看到了你的 LinkedIn 个人资料。”

我的工作就是我的简历。

不管你是在网上学习还是通过硕士学位学习,拥有一个你所从事的工作的作品集是在游戏中建立皮肤的一个很好的方法。

人工智能和人工智能技能很受欢迎,但这并不意味着你不必展示它们。没有货架,再好的产品也卖不出去。

无论是 GitHub、Kaggle、LinkedIn 还是博客,都要有一个人们可以找到你的地方。另外,拥有自己的网络空间也很有趣。

你如何开始?

你去哪里学习这些技能?什么课程最好?

没有最佳答案。每个人的路都会不一样。有些人通过书本学得更好,有些人通过视频学得更好。

比你如何开始更重要的是你为什么开始。

先说为什么。

为什么要学这些技能?

你想赚钱吗?

你想造东西吗?

你想有所作为吗?

没有正确的理由。所有这些都有其自身的合理性。

从为什么开始,因为有一个为什么比如何更重要。有一个“为什么”意味着当事情变得困难并且将会变得困难时,你就有了可以求助的对象。提醒你开始的原因。

知道为什么吗?很好。是时候来点硬技能了。

我只能推荐我试过的。

我已经完成了以下课程(按顺序):

  • 树屋 Python 简介
  • Data camp—Python 简介和 Python 数据科学专题讲座
  • Udacity —深度学习和人工智能纳米学位
  • coursera——吴恩达深度学习
  • fast.ai —第 1 部分,即将成为第 2 部分

他们都是世界级的。我是视觉学习者。看到事情被做,我学得更好。所有这些课程都是这样。

如果你是一个绝对的初学者,从一些 Python 入门课程开始,当你更有信心时,进入数据科学、机器学习和人工智能。DataCamp 非常适合初学 Python,但希望以数据科学和机器学习为重点的人。

多少数学?

我接受过的最高水平的数学教育是在高中。其余的我通过可汗学院学到了,因为我需要它。

关于进入机器学习和 AI 需要知道多少数学,有很多不同的观点。我会分享我的。

如果你想将机器学习和人工智能技术应用于一个问题,你不一定需要对数学有深入的理解才能获得好的结果。TensorFlow 和 PyTorch 等库允许有一点 Python 经验的人构建最先进的模型,而数学则在幕后处理。

如果你想通过博士项目或类似的方式深入机器学习和人工智能研究,拥有深入的数学知识是最重要的。

就我而言,我并不打算深究数学,将算法的性能提高 10%。我会把这个留给比我聪明的人。

相反,我非常乐意使用可用的库,并在我认为合适的时候操纵它们来帮助解决问题。

机器学习工程师实际上是做什么的?

一个机器工程师在实践中所做的可能不是你所想的。

尽管许多在线文章的封面照片,它并不总是涉及与有红眼的机器人一起工作。

这里有几个机器学习工程师每天都要问自己的问题。

  • 背景——如何使用 ML 来帮助了解您的问题?
  • 数据 —你还需要更多数据吗?它需要什么样的形式?当数据丢失时,您会怎么做?
  • 建模 —您应该使用哪种模型?它在数据上工作得太好了吗(过度拟合)?或者为什么不太好用(欠拟合)?
  • 生产——你如何将你的模型投入生产?它应该是一个在线模型还是应该定期更新?
  • 正在进行的——如果你的模型坏了会怎么样?你如何用更多的数据来改进它?有没有更好的做事方法?

我从 Rachel Thomas 的一篇很棒的文章中借用了这些,她是 fast.ai 的联合创始人之一,她在全文中进行了更深入的探讨。

另外,我制作了一个视频,记录了我们周一在 Max Kelsen 通常会做些什么。

没有设置路径

进入 ML 或 AI(或其他)没有对错之分。

这个领域的美妙之处在于我们可以接触到一些世界上最好的技术,我们所要做的就是学会如何使用它们。

你可以从学习 Python 代码(我最喜欢的)开始。

你可以从学习微积分和统计学开始。

你可以从学习决策哲学开始。

机器学习和人工智能让我着迷,因为它们在所有这些的交汇点相遇。

我了解得越多,就越意识到还有很多东西要学。这让我很兴奋。

有时当我的代码不能运行时,我会很沮丧。或者说我不懂一个概念。所以我暂时放弃。我放弃了,让自己远离问题,打个盹。或者去散步。当我回来的时候,我感觉我用不同的眼光看着它。兴奋感又回来了。我一直在学习。我告诉自己。我是一台学习机器。

这个领域发生了如此多的事情,以至于一开始就让人望而生畏。太多的选择导致没有选择。忽略这个。

从你最感兴趣的地方开始,并遵循它。如果它导致了一个死胡同,很好,你已经找到了你不感兴趣的东西。折回原路,走另一条岔路。

计算机很聪明,但是它们仍然不能自己学习。他们需要你的帮助。

我在找房子,所以我用 Python 做了一个 web scraper!—第二部分(EDA)

原文:https://towardsdatascience.com/i-was-looking-for-a-house-so-i-built-a-web-scraper-in-python-part-ii-eda-1effe7274c84?source=collection_archive---------6-----------------------

这篇文章是另一篇文章的后续,在那篇文章中,我构建了一个网络抓取器来寻找里斯本的待售房屋。这一次,我将重点介绍我们之前收集的数据集的转换和清理过程。然后,我将尝试对数据集执行一些探索性数据分析(EDA)。我的目标是给你一些可以做什么的例子,而不是提供一个超级复杂的分析。但是请随意评论和提出建议!我们将在本文中看到的一些内容:

  • 获取每栋房子的房间数量
  • 得到每平方米的价格
  • 去除异常值和“奇怪”的观察值
  • 使用 Seaborn 来可视化我们的数据

先来看看之前从刮萨珀网站得到了什么。

数据集中有一个日期,代表广告发布的日期。我已经知道有一些 2018 年之前的广告,我认为这些房子不再出售是安全的。为了有一个快速过滤的方法,我们可以添加年和月两列。

lisboa_clean = lisboayears = []
months = []for x in lisboa_clean['Date']:
    months.append(str(x.year) + '-' + str(x.month))
    years.append(str(x.year))

lisboa_clean['Year'] = years
lisboa_clean['Month'] = months

搞定了。我还将把“Size (m)”转换成数值,对于不包含数值的记录(如“-”),我将把它们转换成 NaN(用强制),然后我将删除它们,因为在本练习中它们的值将是 none。

lisboa_clean['Size (m²)'] = pd.to_numeric(lisboa_clean['Size (m²)'], errors='coerce')lisboa_clean.dropna(subset=['Size (m²)'], inplace=True)

虽然我也获得了“URL”和“Image”列,但是本文不需要它们,所以我们可以简单地删除它们。

lisboa.drop(['URL', 'Image'], axis=1, inplace=True)

如果你对房地产数据做过任何类型的分析,你可能会注意到我们仍然没有每个房产的房间数量…这些信息在搜索页面中是不可用的(至少是直接不可用的),所以我们需要有点创造性。

在每个标题中,都有一个类似“T2”的字符串,它告诉我们这个房子有两个房间。T3 是 3 个房间,以此类推。我的目标是得到数字,它可以有一个或两个数字。输入(可怕的)正则表达式。接下来的几行代码看起来并不漂亮,我几乎可以肯定一定有更简单或更有效的方法来完成它,但是经过一些测试后,这似乎可以很好地完成工作!

该代码遍历数据集中的每个标题,并将匹配下面正则表达式的字符串检索到一个新列表(房间),即“任何以‘T’开头且后面有 1 或 2 个数字的字符串”。我们最终拥有这些独特的价值:

似乎有些房子“没有”房间。我们应该可以放弃它们并继续,但是为了以防万一,这段代码告诉我们这样做我们损失了多少房子。

A total of 2010 houses were dismissed. Not a serious issue for us though!

在去掉“无”之后,我们可以继续得到数字。多一个带有用于循环的单元将会解决这个问题。这个循环将把字母 t 后面的字符转换成整数。

搞定了。在这之后,加上每平方米的价格应该是小菜一碟。然后我们可以检查描述告诉我们对数据集做了什么。

lisboa_clean['Price/m²'] = lisboa_clean['Price'] / lisboa_clean['Size (m²)']

with all this process, we are down to 19796 properties

该打扫了!

这可能是整个过程中最重要的部分。最终,这一阶段的工作质量将决定您的分析或模型的质量。事实上,没有确切的规则,这使得我们很难决定应该保留/丢弃多少数据,这就是一点常识派上用场的地方。一个很好的经验法则是去掉不到 3%的数据。如果您丢弃越来越多的数据,您将会限制您必须处理的信息量。

这里的目标是在预处理数据时,始终为您所做的选择提供某种推理。

对于这篇文章,我的选择是不太关心那 3%!我们马上可以看到我们的数据中有一些奇怪的值,更准确地说是一栋价值超过 8000 万欧元的房子,或者是一栋 93 平方公里的房子。这些极值(异常值)将对平均值等测量产生巨大影响。“证据”是,虽然中位价在 35 万左右,但均价在 58.2 万左右。

中位数对异常值不太敏感,这使得它在这种情况下是一个很好的工具。

让我们在清理之前使用 Seaborn 来检查我们的数据。不难发现我们有很多清洁工作要做!由于离群值的数量,联合图看起来不太好。请注意,价格和规模之间的皮尔逊相关性非常低,p 值也是如此(这是一个统计显著性指标,基本上,如果低于 0.05,则意味着相关系数显著)。

“not looking good” is an understatement…

经过一些测试后,我为数据集设计了以下过滤器:

  • 我还没打算买城堡,所以我会拆除任何超过 600 平方米的房子
  • 超过 5 个房间的房屋也是如此
  • 180 万欧元以上的价格也有点超出我的预算…

另一方面,我确实觉得很奇怪,可能会有百万富翁在这样一个普通的网站上买房。这似乎不是买卖豪宅的合适平台,所以我们实际上可以说,这些房产并不代表我们在这里试图分析的市场。

简而言之,这就是我对数据科学的描述。想出这些关于你的数据的故事,并检验你的理论(或假设)。

回到我们的数据,让我们去掉我上面提到的观察。通过 len 我们可以看到我们丢弃了多少张唱片。

lisboa_clean = lisboa_clean[lisboa_clean['Size (m²)'] < 600]lisboa_clean = lisboa_clean[lisboa_clean['Price'] < 1800000]lisboa_clean = lisboa_clean[lisboa_clean['Rooms'] < 6]

新创建的价格/大小的分布情况如何?我们这里也有一些清洁工作要做。每平方米的平均价格在 5k 左右(见之前的描述方法),所以我会移除这个值高于 10k 的房子。在相反的极端情况下,我也会删除低于每平方米 300 欧元的观察值。

lisboa_clean = lisboa_clean[lisboa_clean['Price/m²'] < 10000]lisboa_clean = lisboa_clean[lisboa_clean['Price/m²'] > 300]lisboa_clean.reset_index(inplace=True, drop=True)

再次检查接合处的时间到了。我们基本上是通过从数据中移除极值来平滑分布。例如,如果我们要建立一个预测房价的模型,这将允许更好的模型。

notice how the pearson correlation coefficient suddenly improved to 0.69, just by cleaning noise from the dataset

the price per square meter is also more balanced

本着多样性的精神,我将分享另一种图表,即 pairplot 。这一个真的很酷,但是如果你加入太多的变量会变得不可读。这里没有很多有价值的见解,但看起来确实很花哨!

我们还可以探索剩余的分类变量,如“身份”、“城市”和“房间”。

fig, ax =plt.subplots(3,1, figsize=(12,20))
sns.countplot(lisboa_clean['Rooms'], ax=ax[0])
sns.countplot(lisboa_clean['Status'], ax=ax[1])
sns.countplot(lisboa_clean['Municipality'], ax=ax[2])
ax[2].set_xticklabels(ax[2].get_xticklabels(), rotation=50, ha="right")
plt.show()

不出所料,里斯本地区的主要城市是里斯本、卡斯凯什和欧伊拉斯。对于不熟悉这个城市的人来说,这可能没什么意义,但这些基本上都是该区的黄金地段。

2 室的房子比 1 室的房子多一倍以上。我想大多数房子都有不止一个房间是有道理的,我以前从来没有想过这个问题!

让我们用这些变量的一些箱线图来总结一下。

plt.figure(figsize=(15,10))
ax = sns.boxplot(x='Rooms', y='Price', data = lisboa_clean)
ax.tick_params(labelsize=13)
plt.show()

同样,很明显的结论,因为我们预计随着房间数量的增加,房产的价值会上升。这些图表中有趣的一面可能是 1 室和 2 室的房子在相同的价格范围内竞争。事实上,我们有无限的方法可以进一步探索这些信息。

最终盒图,我保证!让我们来看看在一组特定的城市中每平方米价格的差异

areas = lisboa_clean.loc[lisboa_clean['Municipality'].isin(['Lisboa', 'Amadora', 'Cascais', 'Oeiras', 'Sintra', 'Loures', 'Odivelas', 'Mafra', 'Torres Vedras'])]

当涉及到探索和表示数据时,有大量的可能性。我希望这篇文章能给你一些有用的提示,让你更好地理解你的数据!尽管我们没有发现任何关于里斯本房地产市场的令人震惊的事实,但我认为我们能够看到一些简单的步骤,如去除极值,可以大大提高我们分析的质量。

感谢阅读!如果你喜欢这篇文章,我邀请你看看我的其他故事。我主要感兴趣的是数据科学,Python,区块链和数字货币,技术,还有其他一些东西像 摄影 !如果你想取得联系,你可以在这里联系我或者直接回复下面的文章。

我参加了一个超出我能力范围的技术会议,它既令人羞愧又鼓舞人心。洛杉矶数据科学沙龙

原文:https://towardsdatascience.com/i-went-to-a-tech-conference-that-was-over-my-head-it-was-humbling-and-motivating-f18327ec2f2?source=collection_archive---------14-----------------------

会议前— 我现在每月都会参加 Python Meetup 小组,尽管我不得不错过下一次会议,因为那天是我妻子的生日……优先事项。一天,meetup 的组织者问 meetup.com 的小组是否有人有兴趣免费参加数据科学会议。对我来说这是一个不需要动脑筋的问题,所以我马上发了电子邮件,因为前三个是先到先得的。我很幸运被选中,所以我在日历上做了标记,然后等了大约一个半月去参加洛杉矶数据科学沙龙。老实说,我从未听说过这个会议,但我很高兴尝试一些新的东西。

关于我和我为什么选择参加一个我知之甚少甚至一无所知的会议。我是计算机科学领域的大器晚成者,更不用说数据科学了。30 岁时,我重返校园,开始全职工作,现在我即将进入大学三年级,但有一个问题仍然困扰着我,我最终想做什么?我希望我能回到过去的十年,更快地进入编程,但我一直把托尼·罗宾斯的话记在脑子里,我会尽可能地转述:

有人问他需要多长时间才能擅长一件事,他回答说这取决于那个人和他们每天投入的时间。你可以每天花一个小时,在 4 年内变得伟大,或者每天花 4 个小时,在 1 年内变得伟大。

今天,我知道我正在追赶,这正是为什么我每天都在不断地学习和学习,而且我从来不觉得这是我“必须”做的事情,因为我真的觉得编程是我应该做的,我喜欢它。回到会议上,我仍然在考虑我的所有选择,数据科学一直非常有趣,我觉得这次会议可能是真正的数据科学的展示。

会议日— 终于到了参加洛杉矶数据科学沙龙的日子,但首先,如果没有交通,洛杉矶就什么都不是。开车 40 英里花了大约 2 个小时,我比我预期的晚了 20 分钟,因为我想去那里利用那里的停车场,但幸运的是,停车场很充足。

这个节目给我的第一印象是一位名叫 Jorge 的先生,他正在做登记,碰巧是一个非常好的人,非常乐于助人。他的举止肯定让我感觉很受欢迎,这减轻了我去另一个我不认识任何人的会议时的轻微焦虑。这是真的,去一个你不认识任何人的地方,更不用说对他们将要谈论的话题知之甚少,有时会令人生畏,但如果我在 JSConfUS 会议上学到了什么,介绍你自己,问是否可以加入他们,大多数时候,人们是欢迎的。

桌子是站立式的,可以容纳大约 4 个人,碰巧发现一个只有 3 个人一起吃早餐,所以我走近他们,介绍了自己,加入了他们。这将是我一天中第一次与一些极其聪明的人打交道。一个是麻省理工学院的毕业生,另一个在一家大公司的旧金山工作,最后一个有一个迷人的故事,他是如何在 2008 年前成为一名教师的。崩溃发生后,他连续三年被校区解雇,这让他决定从事数据科学方面的职业。他做了一段时间 api 文档的单调工作,最终在一家成功的初创公司找到了一份工作。当我分享的时候,我从我是会员的 meetup 上拿到了票,他说他也是橘子郡的一个 Python 团体的成员,我看着他说,“你是三个中的一个吗?!"。另外两个家伙笑了,因为他认为我的意思是 Python Meetup 中只有三个成员,然后我们都笑了。所以,是的,显然他们中的一个是同事,我们只是没有见过面,但我们现在有了…网络。

会谈(午餐前)—— 人们去参加会议的第二个原因,除了交流就是会谈,对我来说,我终于要看到数据科学是如何在真实的商业世界中使用的,我不会撒谎,有些概念超出了我的理解。现在我不会谈论太多,因为他们将在网上,还有更多真正可以说的,此外,这么多聪明的头脑,有时太聪明了,我跟不上。我并不觉得这本身令人沮丧,因为你永远也不想成为房间里最聪明的人,因为那样你就没什么可学的了。会议主要关注娱乐行业,一般来说是如何使用他们从作为消费者的我们这里收集的所有数据,并像任何成功的企业一样,调整它以提供更好的服务。如果我不谈一个真正给我留下深刻印象的演讲者,那我就失职了。我希望有一天能成为我所观察的演讲者中的一员,但是要成为一名出色的演讲者,你不仅需要知道你要演讲的主题,还要成为一名出色的演讲者。Jen Walraven 是网飞大学科学与分析的经理,起初它几乎像是照本宣科,但即使她在与观众的随意交谈中,她的演讲和词汇也是如此流畅,这是我打算效仿的一个亮点和例子。

午餐— 又到了建立关系网的时刻,我又一次抓起食物,环顾四周,寻找可以加入的人。最后,我和另一组男士坐在一起,我再一次问他们做了什么。一个是大学一年级学生,另一个是研究生,最后一位是来自瑞典的数据科学家博士,现在为一家游戏公司工作。与他交谈是一次非常有启发性的经历,当我站在那里,听他讲述在一家规模虽小但极其成功的游戏公司工作的经历时,我环顾四周,意识到我的同龄人当时的渴望程度。简单地说,学士学位相当于高中文凭。我的意思是说,我周围的这些人都渴望知识,正是这种渴望推动他们取得如此成功。起初,我确实觉得我可能不属于这里,但我改变了我的心态,转而思考我是如何被几十年的经验所包围的,如果有任何时间可以问问题,时间就是那时和那里。最后,我问罗伯特,他是游戏公司的瑞典绅士博士,他会对像我这样的三个人和另外两个还在上学的人说些什么,他给出了具体、务实的建议。他说学习 R 或 Python,学习 SQL 数据库,这促使我问了一个关于 NoSQL 的问题,他的观点是,现在有了 SQL 的新功能,NoSQL 可能会过时。这可能只是一个观点,但尽管如此,这是一个有多年经验的人的观点,至少值得考虑。再说一次,我可能是房间里最笨的,但这意味着我可以问更多的问题,你会发现人们非常愿意给出建议,这次会议也不例外。哦,罗伯特最后成了演讲者之一。

会谈(午餐后)—— 实际上,在我注册之后,我们就开始了一个关于聊天机器人的研讨会,我对聊天机器人了解不多,所以我认为这将是一个很好的关于它们做什么和如何工作的速成班。教授这个研讨会的先生们设置了一个演示,基本上和我想的一样,但令人惊讶的部分是关于如何使用框架创建自己的机器人的讨论。他漫不经心地说,但对我来说,这是我见过的最神奇的事情之一。我知道机器学习风靡一时,对业内许多人来说,它只不过是一种工具,但对我来说,它仍然是某种正在发生的魔法。不要误解我的意思,我对它的工作原理有一个非常非常一般的想法,但是让我吃惊的是,有人或一些人如此聪明地想到创造这个,这是鼓舞和激励成为那些创造者之一。

研讨会结束后,我们有一个短暂的休息时间,进行了更多的会谈,但在午餐前的会谈中,有一个人坐在两个座位之间,我们互相打了个简短的招呼,但没有更多的交谈。午饭后我又见到了他,这是一个尴尬的时刻,当你见过对方不止一次,大多数人仍然不知道谁应该先打招呼。我伸出手介绍自己,我再一次被他的故事和他为什么会在那里所吸引。他的名字叫乔丹,我记得当主持人问他为什么在那天开始的时候在那里,他说他刚刚完成一门课程,所以我问他这个问题。他的学士学位实际上是经济学,我相信他想真正进入数据科学,所以他参加了数据科学的大会课程。有趣的是,我的妻子一直在考虑 UI/UX 的大会,所以我当然代表她问了所有我能想到要问的问题,他不可能比我更了解情况和更乐于交谈。我告诉他很多事情我都不知道,但是他说因为他一个月前刚刚完成,他真的可以很好地理解,所以我又问了另一个问题。对每个人来说,最基本的话题之一就是回归。显然,我坐在后面,就像这样,是的…回归,显然每个人都知道。我问 Jordan 这是什么,他解释得很简单,就是用你拥有的信息和模式猜测其他变量。我想大会为他提供了很好的服务,实际上他对这个课程非常满意。

最后一位演讲者是珍妮·霍尔姆,她是洛杉矶市长的高级技术顾问。她展示了洛杉矶市如何利用技术来帮助城市变得更好。其中一个项目是 Hack LA,听起来很棒,能够成为帮助当地政府改善城市的团体的一员。我住在奥兰治县,到目前为止,我还没有找到一个类似的地方,但它确实激励我思考我能做些什么来帮助我的城市。去年,我们在火灾期间被疏散,这让我想到,也许我可以创建一个应用程序,可以直接向消防队员发送 SOS,消防队员可以获得 SOS 的 gps 位置,当他们靠近时,他们可以激活一个环,帮助他们定位被困人员。更好的办法是让消防队员利用这项技术来定位彼此。我对今天消防队员用的东西知之甚少,但是我哥哥想加入消防队,我可以问问他。不朽的工程,但现在至少我有一个想法,可以慢慢地建立它。

闭幕式— 这一天结束了,现在,因为是洛杉矶,是时候等待交通缓解一些了,所以我决定在附近等一等,做一些网络工作。遇见了安迪,他来自辛辛那提,和他的妻子在一起。他来自克利夫兰,我从他那里学到了宝贵的一课,在辛辛那提,你可以穿任何球队的球衣,除了巴尔的摩,这结束了我的第一次数据科学沙龙 LA conference。参加一个我无法理解的会议的最大好处是,即使你不明白人们在做什么,你也会了解他们是多么的聪明,但在提问的过程中,你会对日常生活有一个实际的了解,这是非常有价值的,尤其是如果数据科学起初看起来很神秘的话。

作为软件工程师,我和一位数据科学家一起工作。下面是我的经验。

原文:https://towardsdatascience.com/i-worked-with-a-data-scientist-heres-what-i-learned-2e19c5f5204?source=collection_archive---------2-----------------------

谈论我作为一名 Java/Kotlin 开发人员与我们的数据科学家一起工作的经历

Photo by Daniel Cheung on Unsplash

背景

2017 年末,我开始对机器学习领域产生兴趣。我讲了我开始旅行时的经历。总之,它充满了有趣的挑战和大量的学习。我是一名 Android 工程师,这是我与我们的数据科学家合作 ML 项目的经验。

我记得我试图解决我们的一个应用程序中出现的图像分类问题。我们需要根据一组定义好的规则来区分有效和无效的图像。我立刻从 Deeplearning4J (dl4j)修改了这个例子,并尝试用它来处理分类任务。我没有得到我期望的结果,但我保持乐观。

我使用 dl4j 示例代码的方法并不成功,因为我获得的准确性和训练模型的最终大小。这不可能,因为我们需要一个紧凑的文件大小的模型,这对于移动设备特别重要。

进入数据科学家

Photo by rawpixel on Unsplash

大约就在这个时候,我们聘请了一位数据科学家,他带来了丰富的相关经验。我后来从他身上学到了很多东西。在我发现大多数 ML 问题可以用 Python 解决之后,我很不情愿地开始学习 Python 的基础知识。我后来发现有些东西在 Python 中更容易实现,因为在 Python 社区中已经有了对 ML 的巨大支持。

我们从小型学习会议开始。此时,我的其他团队成员开始感兴趣,也加入了会议。他给我们介绍了 Jupyter 笔记本云机器学习引擎。我们很快就开始尝试使用花数据集的例子进行图像分类。

在团队中的每个人都具备了培训和部署模型的基础知识之后,我们直接进入了未完成的任务。作为一名团队成员,我当时专注于两项任务:图像分类问题和分割问题。这两种方法后来都使用卷积神经网络(CNN)来实现。

准备培训数据并不容易

Photo by Jonny Caspari on Unsplash

这两项任务都需要大量的训练数据。好消息是我们有很多数据。坏消息是它们没有分类/没有注释。我终于明白 ML 专家说的花最多时间准备训练数据而不是训练模型本身。

对于分类任务,我们需要将成千上万的图像分成不同的类别。这是一项乏味的工作。我不得不调用我的 Java Swing 技能来构建使这项任务更容易的 GUI,但是总的来说,这项任务对于参与人工分类的每个人来说都是单调的。

分割过程有点复杂。我们很幸运地找到了一些擅长细分的模型,但不幸的是它们太大了。我们还希望该模型能够在规格非常低的 Android 设备上运行。这位数据科学家灵光一现,建议我们使用巨大的模型来生成训练数据,这些数据将用于构建我们自己的 mobilenet。

培养

我们最终换成了 AWS 深度学习 AMI 。我们已经对 AWS 很满意了,他们提供这样的服务是一个优势。为图像分割训练模型的过程完全由我们的数据科学家处理,我站在他旁边做笔记:)。

Those are not the actual logs, LOL.

训练该模型是一项计算密集型任务。这是我看到在有足够的 GPU 和 RAM 的计算机上训练的重要性的时候。训练所花的时间相当短,因为我们在训练中使用了这样的计算机。如果我们使用一台基本的计算机,即使不是几个月,也要花几个星期。

我负责图像分类模型的训练。我们不需要在云上训练它,事实上,我是在我的 Macbook pro 上训练的。这是因为我只训练了神经网络的最后一层,而不是我们为分割模型所做的完整网络训练。

我们成功了

经过严格测试后,这两种型号都进入了我们的生产环境🎉。一名团队成员负责构建 Java 包装库。这样做是为了使模型可以以一种抽象的方式使用,这种方式涉及到向模型提供图像和从概率张量中提取有意义的结果。这是包含模型对单个图像进行预测的结果的数组。在这一点上我也参与了一点,因为我之前写的一些代码在这里被清理和重用了。

挑战,挑战无处不在

挑战让生活变得有趣。克服它们才是有意义的。—匿名

我还记得我最大的挑战是处理三维数组的时候。我仍然小心翼翼地接近他们。与我们的数据科学家一起从事 ML 项目是我继续 ML 冒险所需要的鼓励。

在从事这些项目时,我面临的最大挑战是尝试使用 Bazel 从源代码中为 32 位系统构建 Tensorflow Java 库。我在这方面一直不成功。

我也经历了其他挑战,其中一个是常见的:将 Python 解决方案翻译成 Java。因为 Python 已经内置了对数据科学任务的支持,所以代码在 Python 中感觉更简洁。我记得当我试图逐字翻译一个命令时,我的头发都被拔了出来:缩放 2D 阵列,并将其作为透明层添加到图像中。我们终于让它工作了,每个人都很兴奋。

现在,在我们的生产环境中,大多数模型都做得很好,但是当它们产生一个错误的结果时,这些错误的结果就大错特错了。这让我想起了我在这篇精彩帖子上看到的关于将 ML 模型转化为真实产品和服务的引言。

…如果没有新数据的持续输入,模型的质量实际上会下降,而且速度会很快。被称为概念漂移,这意味着随着时间的推移,静态机器学习模型提供的预测变得越来越不准确,越来越没用。在某些情况下,这甚至会在几天内发生。大卫·塔尔比

这意味着我们将不得不不断改进模型,而且没有最终的模型,这很有趣。

我甚至不确定我是否有资格被称为 ML 新手,因为我主要专注于移动开发。今年,我有一次令人兴奋的经历,与一个 ML 团队一起运送帮助解决公司问题的模型。我还想再做一次。

【ICLR 2015】力求简单:带交互码的全卷积网【带 TF 的手动背道具】

原文:https://towardsdatascience.com/iclr-2015-striving-for-simplicity-the-all-convolutional-net-with-interactive-code-manual-b4976e206760?source=collection_archive---------7-----------------------

GIF from this website

我已经假设很多人已经知道这篇文章,“力求简单:所有卷积网络 ”它非常有名,目前它是第二个对 CIFAR 10 数据集分类最准确的网络。

Image from this website

从上面,我们可以看到全卷积网络是多么有效。在这篇文章中,我们将实现两种不同类型的网络架构,像往常一样,让我们看看所有不同的优化方法进行比较。

案例 a)具有自动微分动量的 conv pool-CNN
案例 b)具有自动微分动量的 conv pool-CNN
案例 c)具有手动回推
AMSGrad 案例 d)具有手动回推AMSGrad(扩张

情况 e)全 CNN 带自动分化动量
情况 f)全 CNN 带自动分化亚当
情况 g)全 CNN 带手动回推
AMSGrad 情况 h)全 CNN 带手动回推AMSGrad(扩张

网络架构

从上图中,我们可以看到本文提出的总体架构,因为今天我将只关注 ConvPool-CNN 模型和 All-CNN 模型。值得注意的一个有趣事实是,在最终卷积运算之后会发生什么,如下所示,我们将执行全局平均池运算。

Image of General Base Model Presented in the Paper

蓝线 →全局平均池操作

在继续阅读之前,请注意两件事。
a)我将使用均值池而不是最大池
b)我将执行数据扩充标准均值归一化

现在,让我们更深入地了解一下这个全局平均池操作是什么。

全球平均池

Image from this website

如上所述,我们可以观察到全局平均池操作减少了给定输入的维度。所以我们可以怀疑这个操作是平均池操作的极端版本。现在让我们看看如何在 Tensorflow 中实现它。

Image from this website

从上图中,我们可以看到如何在 Tensorflow 中实现这个操作。现在让我们看看这个操作做了什么。

如上所述,我们可以观察到全局平均池操作与取矩阵的平均值相同。(因此,通过适当的信道维数,我们可以将矩阵简化为向量。)此外,如果有人感兴趣,请查看这篇博客文章了解更多信息。(亚历克西斯·库克也做了一项了不起的工作,解释了全球平均汇集[差距]。)此外 AndersonJo 做了一项令人惊叹的工作,解释 GAP 请点击此处或此处。(注一是韩语)。

结果:案例 a)具有自动微分动量的 conv pool-CNN

**

左图 →随时间训练精度/随时间成本
右图 →随时间测试精度/随时间成本

如上所述,我们可以看到,只有在 20 个历元之后,我们才能达到 88%的准确度。考虑到训练图像上的准确率仍然是 96 %,有 4%的机会增加,有可能达到 90%的准确率。

结果:病例 b)具有自动微分的 ConvPool-CNN 亚当**

**

左图 →随时间训练精度/随时间成本
右图 →随时间测试精度/随时间成本

对于 Adam,我们可以在测试图像上观察到 88%的相似准确性,当与动量比较时,看到结果如此相似是非常有趣的。(我认为它会非常合适)

结果:案例 c) ConvPool-CNN 带手动回柱AMSGrad

**

左图 →随时间训练精度/随时间成本
右图 →随时间测试精度/随时间成本

与传统的 ADAM 相比,AMS Grad 被认为在正规化方面做得更好,然而对于这个实验来说,情况并非如此。如下所示,该模型能够达到 88%的准确率,同时在训练图像上具有 96%的准确率。

蓝线 →第 19 个历元的准确率为 88%。

结果:案例 d) ConvPool-CNN 带手动回柱AMSGrad(散瞳)**

**

左图 →随时间训练精度/随时间成本
右图 →随时间测试精度/随时间成本

对于前馈操作和反向传播的简单膨胀,结果没有显著改善。然而,它能够在第 12 个历元达到 89%的准确率,如下所示。

结果:情况 e)具有自动微分动量的全 CNN**

**

左图 →训练随时间的准确性/随时间的成本
右图 →测试随时间的准确性/随时间的成本

当我们用步长为 2 的卷积层替换所有池操作时,我们可以看到精度下降了 3%。(在测试图像上)。

结果:情况 f)具有自动微分的全 CNN Adam**

**

左图 →列车随时间的准确性/随时间的成本
右图 →测试随时间的准确性/随时间的成本

即使使用 Adam optimizer,我们也可以观察到,在相同的 epoch 数量下,测试图像的准确性下降了 1 ~ 2%。

结果:案例 g) All-CNN 带手动回柱AMSGrad

**

左图 →一段时间内的训练精度/一段时间内的成本
右图 →一段时间内的测试精度/一段时间内的成本

AMS Grad 的最高准确率约为 85%。在训练图像上具有相似的精度。

结果:案例 h) All-CNN 带手动背道具AMSGrad(散瞳)**

**

左图 →随时间训练精度/随时间成本
右图 →随时间测试精度/随时间成本

最后,对于扩张反向传播的 AMS Grad,它比任何其他方法都差,只能达到 84%的准确性。

交互式代码/透明度

对于谷歌 Colab,你需要一个谷歌帐户来查看代码,而且你不能在谷歌 Colab 中运行只读脚本,所以在你的操场上做一个副本。最后,我永远不会请求允许访问你在 Google Drive 上的文件,仅供参考。编码快乐!同样为了透明,我在训练期间上传了所有的日志。

要访问全球平均池的代码,请单击此处。

要访问案例 a 的代码,请点击此处,要访问日志,请点击此处。
访问案例 b 的代码请点击此处,访问日志请点击此处。
要访问案例 c 的代码,请点击此处,要访问日志,请点击此处。
要访问案例 d 的代码,请点击此处,要访问日志,请点击此处。

要访问案件 e 的代码,请点击这里,要访问日志,请点击这里。
访问案例 f 的代码请点击此处,访问日志请点击此处。
要访问案例 g 的代码,请点击此处,要访问日志,请点击此处。
要访问案例 h 的代码,请点击此处,要访问日志,请点击此处。

最后的话

另外,如果你希望看到这个网络的 keras 实现,请查看这个博客帖子。Mate Labs 在解释这个话题方面做得非常出色!)

如果发现任何错误,请发电子邮件到 jae.duk.seo@gmail.com 给我,如果你想看我所有的写作清单,请在这里查看我的网站。

同时,在我的 twitter 上关注我这里,访问我的网站,或者我的 Youtube 频道了解更多内容。我还实现了广残网,请点击这里查看博文 t。

参考

  1. 斯普林根贝格,j .,多索维茨基,a .,布罗克斯,t .,&里德米勒,M. (2014)。追求简单:全卷积网。Arxiv.org。检索于 2018 年 5 月 11 日,来自https://arxiv.org/abs/1412.6806
  2. cy donia 999/all _ 卷积 _net。(2018).GitHub。检索于 2018 年 5 月 11 日,来自https://github.com/cydonia999/all_convolutional_net
  3. 示例:基础— imgaug 0.2.5 文档。(2018).img aug . readthe docs . io . 2018 年 5 月 11 日检索,来自http://img aug . readthe docs . io/en/latest/source/examples _ basics . html
  4. NumPy . ndarray . dtype—NumPy 1.14 版手册。(2018).Docs.scipy.org。检索于 2018 年 5 月 11 日,来自https://docs . scipy . org/doc/numpy-1 . 14 . 0/reference/generated/numpy . ndarray . dtype . html
  5. (2018).[在线]可在:https://www.quora.com/What-is-global-average-pooling[2018 年 5 月 11 日访问]。
  6. 池层 Keras 文档。(2018).keras . io . 2018 年 5 月 11 日检索,来自https://keras.io/layers/pooling/
  7. 这些研究人员是如何尝试一些非传统的东西来得到一个更小但更好的图像…(2017).中等。检索于 2018 年 5 月 11 日,来自https://medium . com/@ mate labs _ ai/how-these-researchers-trying-something-outstanding-to-out-a-small-better-image-544327 f30e 72
  8. 优化器— Keras 文档。(2018).keras . io . 2018 年 5 月 11 日检索,来自https://keras.io/optimizers/
  9. 库克,A. (2017)。用于对象本地化的全局平均池层。alexisbcook . github . io . 2018 年 5 月 11 日检索,来自https://alexisbcook . github . io/2017/global-average-pooling-layers-for-object-localization/
  10. TensorFlow?,H. (2018)。如何在 TensorFlow 中进行全球平均池化?。堆栈溢出。检索于 2018 年 5 月 11 日,来自https://stack overflow . com/questions/42054451/how-do-I-do-global-average-pooling-in-tensor flow
  11. Anderson jo/全球平均池。(2018).GitHub。检索于 2018 年 5 月 11 日,来自https://github . com/Anderson jo/global-average-pooling/blob/master/global-average-pooling . ipynb
  12. Anderson jo/全球平均池。(2018).GitHub。检索于 2018 年 5 月 11 日,来自https://github.com/AndersonJo/global-average-pooling
  13. 贝嫩森河(2018)。分类数据集结果。rodrigob . github . io . 2018 年 5 月 13 日检索,来自http://rodrigob . github . io/are _ we _ there _ yet/build/classification _ datasets _ results . html # 43494641522d 3130
  14. 误差,A. (2018)。避免 tensorflow 打印在标准错误上。堆栈溢出。检索于 2018 年 5 月 19 日,来自https://stack overflow . com/questions/35869137/avoid-tensor flow-print-on-standard-error
  15. 2017 年深度学习优化实现亮点(feat。塞巴斯蒂安·鲁德)。(2018).中等。检索于 2018 年 5 月 19 日,来自https://medium . com/@ SeoJaeDuk/implementation-of-optimization-for-deep-learning-highlights-in-2017-feat-sebastian-ruder-61e 2 CBE 9 b 7 CB
  16. 超越 Tensorflow 的默认自动微分优化器,具有交互式代码[手动…(2018).走向数据科学。检索于 2018 年 5 月 19 日,来自https://towards data science . com/outpering-tensor flows-default-auto-difference-optimizer-with-interactive-code-manual-e 587 a82d 340 e
  17. aleju/imgaug。(2018).GitHub。检索于 2018 年 5 月 19 日,来自https://github.com/aleju/imgaug
  18. 通过 Numpy 和 Tensorflow 中的示例和交互式代码理解批处理规范化。(2018).走向数据科学。检索于 2018 年 5 月 19 日,来自https://towards data science . com/understanding-batch-normalization-with-examples-in-numpy-and-tensor flow-with-interactive-code-7f 59 bb 126642

【ICLR 2016】通过带交互代码的指数线性单元(ELUs)进行快速准确的深度网络学习【带 TF 的手动回推】

原文:https://towardsdatascience.com/iclr-2016-fast-and-accurate-deep-networks-learning-by-exponential-linear-units-elus-with-c0cdbb71bb02?source=collection_archive---------11-----------------------

GIF from this website

我知道这份文件存在的时间最长,但是,直到现在我才有时间来实现这个网络。所以在这里,我终于实现了这个完全卷积神经网络与 ELU。非常简单但性能卓越的网络。

最后,为了好玩,让我们使用不同的方法来训练我们的网络,例如……
情况 a)使用标准反向传播的自动微分
情况 b) 反馈对准
情况 c) 扩张反向传播使用 L2 正则化
情况 d)使用反向传播的自动微分、 L2 正则化
情况 f) 使用不同优化器的组合的扩张反向传播

指数线性单位

红框 →激活功能的导数

本文的主要贡献是新颖的激活函数。它可能看起来很简单,但不要让表面水平愚弄你,作者实际上有一个完整的部分来解释为什么这种激活工作得这么好。总之,1)使用负梯度是个好主意,或者 2)激活函数的输入值以零为中心,以避免不必要的偏移。现在让我们看看这个函数在绘图时是什么样子的。

Graph using this website

红线 → Alpha 值设为 1
蓝线 → Alpha 值设为 2
绿线 → Alpha 值设为 5
橙线 → Alpha 值设为 0.5

根据α值,我们可以观察到负值的陡度彼此不同。这个函数的求导非常简单,正如我们在上面已经看到的,现在让我们来看看实现。

红框 →为小于 0 的输入增加 Alpha 值

从添加的 alpha 值中,我们可以知道 tensor-flow 的 elu()实现将 alpha 值默认设置为 1。

数据集(CIFAR 10)

Screen Shot from this website

我们将使用 CIFAR 10 数据集来测试该网络的性能。然而,请注意,本文的作者已经执行了 1) 全局对比度归一化 2) ZCA 白化的预处理,以及进一步的数据增强(填充和翻转),但我只是要归一化图像的每个通道。

Data Augmentation of the Paper

最后请注意,作者用 CIFAR 10 数据集做了两个实验,一个用 11 个卷积层,另一个用 18 个卷积层。我将实现 11 层网络。

网络架构

红色矩形 →输入尺寸为 32 * 32 的图像
黑色矩形 →与 ELU 激活的卷积运算
绿色矩形 →均值/最大池运算
橙色矩形 →用于分类的 Softmax

网络本身并不复杂,它由 11 层组成,但原始论文的作者有特定的超参数设置,如下所示。

不幸的是,对我来说,为 165,000 次迭代训练一个模型将花费太多的时间。因此,我不打算这样做,但你可以检查交互代码部分,以准确了解我的超级参数是如何设置的。此外,还有一件事让我感到疑惑:2 * 2 max-在每个堆栈之后应用了跨距为 2 的池。如果我们从 32 *32 的图像开始,我们不能有 6 个池操作(这就是为什么我用了 5 个池层,如上所示。).如果有人知道作者的意思,请在下面评论。

案例 a)使用标准反向传播进行自动微分的结果
(迭代:1K,优化器:动量)

左图 →一段时间内的训练精度/成本
右图 →一段时间内的测试精度/成本

使用动量优化器对该模型进行 1k 次迭代训练,如原始论文中所报告的那样设置退出率。即使在 1k 迭代之后,网络也做得不好,训练图像和测试图像的准确率都是 62%。虽然模型没有过度拟合是件好事,但这也表明收敛速度很慢。

情况 b)结果为 (迭代:85,优化器:Adam)

我甚至没让模特完成训练。这是因为模型没有学到任何东西。在训练图像上达到 35%的准确率后,模型停止了改进。如果您希望查看培训的详细信息,请点击此处查看日志。

****注意我在这个案例中使用的网络架构与原始论文略有不同。

案例 c)结果为 扩张反向传播 L2 正则化 (迭代:300,优化器:Adam)

****

左图 →一段时间内的训练精度/成本
右图 →一段时间内的测试精度/成本

请注意两件事,1)我忘记标准化成本,因此图表的 y 轴是如此倾斜 2)这个模型是使用 Adam 优化器训练的。然而,再次,该模型并没有表现得像我想的那样好。由于 Adam Optimizer,它能够在训练图像上实现高精度,但它未能泛化,在测试图像上表现不佳。(这是一个严重的过度拟合案例。)

****注意我在这个案例中使用的网络架构与原始论文略有不同。

情况 d)具有反向传播的自动微分的结果, L2 正则化 (迭代:200,优化器:Adam)

****

左图 →一段时间内的训练精度/成本
右图 →一段时间内的测试精度/成本

即使有了 L2 正则化,当用 Adam optimizer 训练时,网络似乎过度适应。我们可以观察到,在第 25 次迭代之后,测试图像的成本开始增加。

尽管该网络在测试图像准确性上比其他网络稍好,但是它遭受过拟合。

****注意我在这个案例中使用的网络架构与原始论文略有不同。

情况 d)使用不同优化器组合的 扩张反向传播 的结果(迭代:200,优化器:亚当/动量)

紫色框 →使用 Adam 优化器优化的图层

对于这个网络,我真的想尝试一些不同的东西,为每一层设置不同的优化器。如上所示,用 Adam optimizer 优化了周围有紫色矩形的层,并使用 momentum optimizer 训练了其他层。

****

左图 →一段时间内的训练精度/成本
右图 →一段时间内的测试精度/成本

该网络的表现不如我所希望的那样好,尽管与情况 c)相比,该模型没有任何正则化技术方法,如 L2 正则化,但该模型能够在测试图像上实现 65%的准确性。

****注意我在这个案例中使用的网络架构与原始论文略有不同。

互动代码/透明度

对于谷歌 Colab,你需要一个谷歌帐户来查看代码,而且你不能在谷歌 Colab 中运行只读脚本,所以在你的操场上做一个副本。最后,我永远不会请求允许访问你在 Google Drive 上的文件,仅供参考。编码快乐!

要访问案例 a 的代码,请点击此处,要访问的日志,请点击此处。
访问案例 b 的代码请点击此处,访问日志请点击此处。
要访问案例 c 的代码,请点击此处,要访问日志,请点击此处。
要访问案例 d 的代码,请点击此处,要访问日志,请点击此处。
要访问案例 e 的代码请点击此处,要访问日志请点击此处。

最后的话

从这个实验中,我能够看到数据预处理和超参数调整对性能增益的重要性。因为最初的作者能够通过他们的超参数设置获得超过 90%的准确性。

蓝线 →在原作者论文上测试 CIFAR 10 的错误率

如果发现任何错误,请发电子邮件到 jae.duk.seo@gmail.com 给我,如果你想看我所有写作的列表,请在这里查看我的网站。

同时,在我的 twitter 上关注我这里,访问我的网站,或者我的 Youtube 频道了解更多内容。我还实现了广残网,请点击这里查看博文 t。

参考

  1. Clevert,D. A .,Unterthiner,t .,& Hochreiter,S. (2015 年)。通过指数线性单元(elus)进行快速准确的深度网络学习。 arXiv 预印本 arXiv:1511.07289
  2. 作为神经网络激活函数的 ELU。(2018).赛菲克·伊尔金·塞伦吉尔。2018 年 5 月 6 日检索,来自https://sefiks . com/2018/01/02/elu-as-a-neural-networks-activation-function/
  3. tf.nn.elu |张量流。(2018).张量流。检索于 2018 年 5 月 6 日,来自https://www.tensorflow.org/api_docs/python/tf/nn/elu
  4. 分段。(2018).德斯莫斯图形计算器。检索于 2018 年 5 月 6 日,来自https://www.desmos.com/calculator/v9hyi8qj0o
  5. CIFAR-10 和 CIFAR-100 数据集。(2018).Cs.toronto.edu。检索于 2018 年 5 月 6 日,来自https://www.cs.toronto.edu/~kriz/cifar.html
  6. 托马斯,M. (2017)。ZCA 美白。马丁·托马斯。检索于 2018 年 5 月 6 日,来自https://martin-thoma.com/zca-whitening/
  7. aleju/papers。(2018).GitHub。2018 年 5 月 6 日检索,来自https://github . com/aleju/papers/blob/master/neural-nets/elus . MD
  8. IFT 6266 H13 博客。(2013).IFT 6266 H13 博客。2018 年 5 月 6 日检索,来自https://caglarift6266.wordpress.com/
  9. aleju/papers。(2018).GitHub。2018 年 5 月 6 日检索,来自https://github.com/aleju/papers
  10. Matplotlib . py plot . legend-Matplotlib 2 . 2 . 2 文档。(2018).Matplotlib.org。检索于 2018 年 5 月 6 日,来自https://matplotlib . org/API/_ as _ gen/matplotlib . py plot . legend . html
  11. 张量流正则化。(2018).ritchieng . github . io . 2018 年 5 月 6 日检索,来自http://www . ritchieng . com/machine-learning/deep-learning/tensor flow/regulation/
  12. Only Numpy:对深度神经网络实施 L1 /L2 范数/正则化的不同组合…(2018).走向数据科学。2018 年 5 月 6 日检索,来自https://towards data science . com/only-numpy-implementing-different-combination-of-L1-norm-L2-norm-L1-regularity-and-14b 01a 9773 b
  13. 机器学习的 L1 和 L2 正则化。(2018).Msdn.microsoft.com。检索于 2018 年 5 月 7 日,来自https://msdn.microsoft.com/en-us/magazine/dn904675.aspx
  14. [ NIPS 2016 ]直接反馈对齐为深度神经网络中的学习提供了交互式学习。(2018).中等。检索于 2018 年 5 月 7 日,来自https://medium . com/@ SeoJaeDuk/nips-2016-direct-feedback-alignment-provides-learning-in-deep-neural-networks-with-interactive-32d 59045 e8e
  15. 超越 Tensorflow 的默认自动微分优化器,具有交互式代码[手动…(2018).走向数据科学。检索于 2018 年 5 月 7 日,来自https://towards data science . com/outpering-tensor flows-default-auto-difference-optimizer-with-interactive-code-manual-e587 a82d 340 e
  16. 金马博士和巴律师(2014 年)。亚当:一种随机优化方法。Arxiv.org。于 2018 年 5 月 7 日检索,来自https://arxiv.org/abs/1412.6980

ICLR 2016 —用交互代码在 Tensorflow 中实现上下文模块【用 Tensorflow 手动背道具】

原文:https://towardsdatascience.com/iclr-2016-implementing-context-module-in-tensorflow-with-interactive-code-manual-back-prop-with-a2c84b3ae444?source=collection_archive---------5-----------------------

Image from pixabay

因为我在上一篇文章中提到了膨胀卷积运算,所以只有我用它制作了一个网络才有意义。所以我认为我最好实现本文中提出的上下文模块通过扩张卷积进行多尺度上下文聚合。在2016国际学习代表大会上发表。

有两件事我想指出来。原始论文的作者使用他们自己的方法初始化权重,对于这篇文章,我将从正态分布初始化。
2。为了好玩,让我们用扩张反向传播和 l 来训练网络。

网络架构(表格形式)/实验设置

Screen shot from this paper

基本上,上下文模块是一个具有扩展卷积运算的全卷积神经网络。我们的实验设置非常简单,我们将对 MNIST 数据集执行多类分类。为了实现这一点,我们将在上下文模块网络的输出端添加一个完全连接的神经网络。

网络架构(OOP 形式)

Left Image Context Layer / Right Image Fully Connected Neural Network

红线→ 扩张卷积运算

除了上面的红线执行扩张卷积运算外,网络架构与卷积神经网络完全相同。其前面有卷积层,后面有完全连接的神经网络。

膨胀系数/前馈操作

红线 →放大系数以匹配原稿

因此,为了保持膨胀因子与本文相同,我们将因子分别设置为 1、1、2、4、8、16、1 和 1。

训练结果自动微分(ADAM 优化器)

左图 →训练图像随时间变化的成本图
右图 →训练图像随时间变化的精度图

左图 →测试图像随时间变化的成本图
右图 →测试图像随时间变化的精度图

这是我见过的最有趣的结果,尤其是对汽车差异化而言。大约在 50 世纪,我们可以看到这个模型表现得非常好。然而过了 100th?)纪元模型的性能开始下降。最终训练和测试图像的准确率都达到了 77%左右。

训练结果(破损)扩张背道具(ADAM 优化器)

左图 →训练图像随时间变化的成本图
右图 →训练图像随时间变化的精度图

左图 →测试图像随时间变化的成本图
右图 →测试图像随时间变化的精度图

在让模型训练的同时,我去了健身房。在我的锻炼过程中,我意识到,我对扩展卷积层的反向传播的实现是错误的。因此,我将这个模型命名为(破碎的)扩张反向传播。然而,非常有趣的是,当这个过程可能被中断时,这个模型仍然能够学习。虽然与自动微分相比,它的表现不尽人意,但它仍能达到约 75%的准确率。

交互代码

为了交互代码,我搬到了 Google Colab!所以你需要一个谷歌帐户来查看代码,你也不能在谷歌实验室运行只读脚本,所以在你的操场上做一个副本。最后,我永远不会请求允许访问你在 Google Drive 上的文件,仅供参考。编码快乐!

要获取(破裂)扩张反向传播的代码,请点击此处
要访问自动区分代码,请点击此处。

最后的话

因为,这篇文章更多的是关于实现上下文模块,我不会进一步优化它。但是,如果你能够获得更好的结果,请在下面评论,并说明你是如何达到这个结果的。

如果发现任何错误,请发电子邮件到 jae.duk.seo@gmail.com 给我,如果你想看我所有写作的列表,请在这里查看我的网站。

同时,在我的 twitter 上关注我这里,访问我的网站,或者我的 Youtube 频道了解更多内容。如果你感兴趣的话,我还做了解耦神经网络的比较。

参考

  1. 贴标”?,W. (2018)。相对于「分段」和「场景标注」,什么是「语义分段」?。Stackoverflow.com。检索于 2018 年 3 月 12 日,来自https://stack overflow . com/questions/33947823/what-is-semantic-segmentation-comparated-to-segmentation-and-scene-labeling
  2. 于,冯,科尔敦,伏(2015)。基于扩张卷积的多尺度上下文聚合。arXiv 预印本 arXiv:1511.07122。
  3. 2017 年深度学习语义分割指南。(2017).Blog.qure.ai .检索于 2018 年 3 月 12 日,来自http://blog . qure . ai/notes/semantic-segmentation-deep-learning-review # dilation
  4. sk learn . utils . shuffle-sci kit-learn 0 . 19 . 1 文档。(2018).Scikit-learn.org。检索于 2018 年 3 月 12 日,来自http://sci kit-learn . org/stable/modules/generated/sk learn . utils . shuffle . html
  5. 在 Tensorflow 中用 DeepLab 实现语义图像分割。(2018).研究博客。检索于 2018 年 3 月 12 日,来自https://research . Google blog . com/2018/03/semantic-image-segmentation-with . html
  6. 使用具有交互代码的神经网络去噪 CT 扫描——第 3 部分,卷积残差神经网络。(2018).走向数据科学。检索于 2018 年 3 月 12 日,来自https://towards data science . com/de nosing-lung-CT-scans-using-neural-networks-with-interactive-code-part-3-convolutionary-residual-6 dbb 36 b 28 be
  7. 以数值模拟和张量流为例理解 2D 展开卷积运算。(2018).走向数据科学。检索于 2018 年 3 月 12 日,来自https://towards data science . com/understanding-2d-expanded-convolution-operation-with-examples-in-numpy-and-tensor flow-with-d376b 3972 b25
  8. 于,冯,科尔敦,伏(2015)。基于扩张卷积的多尺度上下文聚合。Arxiv.org。检索于 2018 年 3 月 12 日,来自 https://arxiv.org/abs/1511.07122
  9. TF . nn . conv 2d _ back prop _ filter | tensor flow。(2018).张量流。检索于 2018 年 3 月 12 日,来自https://www . tensor flow . org/API _ docs/python/TF/nn/conv2d _ back prop _ filter
  10. TF . nn . conv 2d _ back prop _ input | tensor flow。(2018).张量流。检索于 2018 年 3 月 12 日,来自https://www . tensor flow . org/API _ docs/python/TF/nn/conv2d _ back prop _ input
  11. 只有 Numpy:扩张的反向传播和谷歌大脑的梯度噪声与交互代码。(2018).黑客正午。检索于 2018 年 3 月 12 日,来自https://hacker noon . com/only-numpy-expanded-back-propagation-and-Google-brains-gradient-noise-with-interactive-code-3a 527 fc 8003 c
  12. 价值观?,H. (2018)。如何获取 Tensorflow 张量维数(形状)作为 int 值?。Stackoverflow.com。检索于 2018 年 3 月 13 日,来自https://stack overflow . com/questions/40666316/how-to-get-tensor flow-tensor-dimensions-shape-as-int-values

【ICLR 2016 /论文摘要】无监督学习的卷积聚类

原文:https://towardsdatascience.com/iclr-2016-paper-summary-convolutional-clustering-for-unsupervised-learning-4741707e4b28?source=collection_archive---------6-----------------------

GIF from this website

这篇论文是两年前提出的,是利用无监督学习算法学习更高层次结构的另一种方法。(k 表示)

请注意,这篇帖子是给未来的自己看的,回顾这篇论文上的材料,而不是从头再看一遍。

Paper from this website

摘要

标记给定数据的任务是一个劳动密集型过程,在这项工作中,作者决定利用无监督学习算法来放松这一限制。其中,他们基于 k-means 聚类算法的增强版本来训练深度卷积神经网络,这减少了类似过滤器形式的相关参数的数量,从而提高了测试分类的准确性。他们能够在 STL 和 MNIST 数据集上获得较好的精度。

简介

为了使网络运行良好,需要大量的数据,但是标记数据是一个劳动密集型的过程。因此,需要一些方法来利用未标记的数据。(以前需要无监督的预训练来训练非常深的神经网络。).在这项工作中,作者提出了一种改进的无监督聚类算法,允许过滤器学习不同的特征。(稀疏连接并防止算法学习冗余滤波器,这些滤波器基本上是彼此的移位版本。)

相关工作

虽然存在不同的无监督学习方法来学习将要使用的滤波器,但是它们忽略了滤波器将以卷积方式使用的事实。这可能导致过滤器学习重复的特征检测器。为了克服这一点,提出了具有对比散度和卷积稀疏编码的卷积限制玻尔兹曼机。最近,使用 k-means 算法的滤波器得到了关注,然而,很少关注减少学习滤波器中的冗余。(已经提出了诸如随机连接或分组相似特征的小工作,但是它们没有提供显著的改进。)在这项工作中,作者通过设计一种优化的学习算法来解决这个问题,该算法避免了相似过滤器的复制。

学习过滤器

K 意味着算法通过使用上述算法从数据向量 w (NM)中学习字典 D (NK)。(S 是与输入 W 相关的码向量,D(j)是字典 D 的第 j 列,矩阵 W 的维数为(NM ),而 S 的维数为(KM)。然而,利用 k 均值学习算法,在学习的滤波器之间会有冗余,因此作者提出了卷积 k 均值。

卷积 K 意味着学习算法选择大得多的图像块来执行聚类,具体来说,选择比滤波器大小大两倍的窗口,并从输入图像中随机选择。然后,质心对整个窗口进行卷积,以计算提取区域的每个位置处的相似性度量,并且具有最大激活值的区域意味着是与质心最相似的特征。这从窗口中提取并分配给相应的质心。(修改后的算法见下图。)

如下所示,当我们比较由两种算法学习的滤波器时,我们可以观察到通过 k 均值算法学习的滤波器之间的冗余,而学习的卷积 k 均值算法学习更多的本质基础。

为了比较性能,作者使用 STL 数据集,为了学习过滤器,他们只使用未标记的图像。(对于编码方案,他们对输入图像应用了全局对比度归一化。)

如上所述,当作者比较通过 k 均值和卷积 k 均值学习滤波器的网络性能时。我们可以看到,通过卷积 k-means 学习的网络具有更好的性能。这表明过滤器在从给定图像中提取有用信息方面做得更好。

学习连接

作者还研究了一种学习各层之间联系的方法。虽然完全连接的体系结构完全使用前面各层的所有功能,但非完全连接在计算方面更高效。(作者使用稀疏连接矩阵来实现这一点。).通过限制感受野之间的连接,可以扩展算法。

使用如上所示的架构,作者首先添加了具有预定义的不完全连接的卷积层,并在卷积层之后附加了线性分类器,并使用反向传播算法来训练系统。在这个阶段,通过监督学习来学习连接矩阵,当训练完成时,仅保留连接矩阵,并且通过卷积 k 均值算法来学习卷积滤波器。

如上所述,当两个卷积层都通过卷积 k 均值算法学习时,会产生最佳结果。

此外,我们可以再次确认卷积 k 均值算法是多么有效。当通过反向传播训练网络时,它过度适应训练数据,因此在测试图像集上具有非常低的性能。

最终分类结果

最后,作者比较了他们的方法与其他国家的艺术算法。(对于 STL 和 MNIST 数据集)。

Results for STL

如上所述,当我们比较无监督的学习过滤方法时,我们可以看到作者的方法显著地提高了测试精度。(注意,对于上述算法,作者使用了多字典方法,而不是使用单个字典。).

甚至对于 MNIST 数据集,我们可以看到作者的方法已经实现了最低的错误率。

结论

总之,本文作者提出了一种学习算法,该算法结合了监督学习算法和非监督学习算法的优点。作者修改了 k 均值学习算法,减少了网络学习的冗余滤波器。此外,作者提出了一种学习设置来学习层之间的正确连接。与其他无监督学习方法相比,该方法更简单,性能更好。

最后的话

这种方法的一个非常好的优点是,我们不需要在执行 k-means 聚类之前白化数据。然而,从与 deco 相关的批量标准化中,我们已经知道创建一个增白层是完全可能的。

如果发现任何错误,请发电子邮件到 jae.duk.seo@gmail.com 给我,如果你希望看到我所有写作的列表,请在这里查看我的网站

同时,在我的 twitter 这里关注我,并访问我的网站,或我的 Youtube 频道了解更多内容。我也实现了广残网,请点击这里查看博文 pos t。

参考

  1. Dundar,a .,Jin,j .,& Culurciello,E. (2015 年)。无监督学习的卷积聚类。Arxiv.org。检索于 2018 年 8 月 20 日,来自https://arxiv.org/abs/1511.06241

[ ICLR 2017 /论文摘要]使用强化学习设计神经网络架构

原文:https://towardsdatascience.com/iclr-2017-paper-summary-designing-neural-network-architectures-using-reinforcement-learning-e6f099bcf2ec?source=collection_archive---------13-----------------------

GIF from this website

仅仅从名字你就已经知道这种纸有多酷了。

请注意,这个姿势是为了我未来的自己回顾和复习这篇论文上的材料,而不是从头再看一遍。

Paper from this website

摘要

设计新的网络架构不仅需要人类的专业知识,还需要劳动时间。本文的作者介绍了一种可以设计高性能卷积神经网络的代理。并且使用 Q-learning 和 e-greedy 探索策略和经验重放来训练代理。

简介

CNN 多年来取得了巨大的成功,典型的 CNN 由卷积层、池层和全连接层组成。(同样由于所有的选项,搜索空间相当大。).本文的作者制作了一个代理,旨在无需人工干预的情况下创建新的卷积神经网络架构。(代理正在对以何种顺序放置何种层做出顺序决策。)最后,他们在 MNIST 和 CIFAR 10 等图像分类数据集上测试了创建的网络。

相关工作

创建新网络架构的自动化在学术界并不是一个新概念,一些相关的作品是“卷积神经结构”和“遗传算法和神经网络的组合:技术发展水平的调查”。然而,不幸的是,通常情况下,手工制作的网络比生成的网络性能更好。最近在强化学习和深度学习的交叉领域有很多工作。其中,Q-learning、e-greedy 策略和经验重放取得了巨大的成功。

背景

在这一部分,作者很好地解释了马尔可夫决策过程,贴现报酬函数,以及它们是如何结合在一起的。关于这个话题的更简单的解释可以在这里找到。此外,如果您希望了解更多关于贝尔曼方程的信息,请点击此处

利用 Q-learning 设计神经网络架构

作者为智能体选择的任务是依次选择神经网络层。其中 C(n,f,l)对应于滤波器的数量、感受野大小和步幅,P(f,l)对应于具有相同符号的池层。当代理完成生成不同类型的网络架构时,(换句话说,到达终端状态),生成的网络得到训练。并且验证准确性充当代理的奖励值,网络体系结构也被存储在代理的重放存储器中,并且经验被周期性地从重放存储器中采样以更新 Q 值。

作者描述了每个状态空间、动作空间和 Q-Learning 训练过程的实现/配置细节。其中状态空间通过所有相关层参数的元组来定义。(每个参数的细节可以在上面看到。).对于动作空间,它们限制了完全连接层的数量,并使代理能够在任何给定的时间点移动到终止状态。最后,ε递减时间表如下所示。(Q 学习率为 0.01)。

实验细节

在这里,作者给出了他们在训练网络时选择的超参数的详细描述,以及他们添加了退出层的事实。一个有趣的事实是,如果他们的学习速度不是他们的最佳选择,网络有 5 次机会重新开始他们的训练。(如果他们不能学习,学习率就会降低。而且用了 10 个 nvidia GPU 用了 10 天。)最后,作者描述了他们如何为每个数据集优化超参数。(MNIST、CIFAR 10 和 SVHN。)

结果

如上所述,随着代理从探索阶段进入开发阶段,每个数据集的模型的准确性开始增加。(特别是对于 SVHN,它从 52%增加到 88%。).一个有趣的事实是,代理通常选择 C(n,1,1)类型的卷积层作为第一层,这作为预处理步骤(即,将 RGB 图像转换为 YUV 图像)。).

如上所述,我们可以注意到,与类似类型的网络(没有更高级的池层等)相比,代理生成的网络表现良好。甚至当比较由更复杂的网络结构组成的不同网络时,我们可以观察到由代理生成的网络仍然是有竞争力的。

最后,作者还对 MetaQNN 的迁移学习能力做了一些实验。

结束语

总之,为不同的用例设计网络架构是一项耗时的任务。这篇论文的作者提出了一种新的解决方案,他们训练了一个代理,该代理可以对下一步放置什么层做出顺序决策,以设计一个卷积神经网络。此外,作者指出了在未来更优化版本的代理的可能性。

遗言

创建不同类型网络的非常酷的方法。

如果发现任何错误,请发电子邮件到 jae.duk.seo@gmail.com 给我,如果你希望看到我所有写作的列表,请在这里查看我的网站

同时,在我的推特这里关注我,并访问我的网站,或我的 Youtube 频道了解更多内容。我也实现了广残网,请点击这里查看博文 pos t。

参考

  1. b .贝克、o .古普塔、n .纳伊克和 r .拉斯卡尔(2016 年)。使用强化学习设计神经网络结构。Arxiv.org。检索于 2018 年 6 月 28 日,来自https://arxiv.org/abs/1611.02167
  2. 遗传算法和神经网络的结合:技术现状的调查——IEEE 会议出版物。(2018).Ieeexplore.ieee.org。检索于 2018 年 6 月 28 日,来自https://ieeexplore.ieee.org/document/273950/
  3. (2018).Arxiv.org。检索于 2018 年 6 月 28 日,来自https://arxiv.org/pdf/1606.02492.pdf
  4. David Silver 的 RL 课程—第 1 讲:强化学习简介。(2018).YouTube。检索于 2018 年 6 月 28 日,来自https://www.youtube.com/watch?v=2pWv7GOvuf0&list = plweqsiczjac 7 pfiyymvyihfpg 9um 82 b
  5. 贝尔曼方程-1。(2018).YouTube。检索于 2018 年 6 月 28 日,来自https://www.youtube.com/watch?v=b1GvQcjDwBU

【ICLR 2017 /论文摘要】探索具有循环学习率的损失函数拓扑

原文:https://towardsdatascience.com/iclr-2017-paper-summary-exploring-loss-function-topology-with-cyclical-learning-rates-4213655ba65?source=collection_archive---------16-----------------------

GIF from this website

我想知道更多关于循环学习率的信息。

请注意,这篇帖子是让我未来的自己回顾和回顾这篇论文上的材料,而不是从头再看一遍。

Paper from this website

摘要

本文作者训练了一个具有循环学习率(CLR)的残差神经网络。使用线性网络插值,他们能够观察到奇怪的现象。他们还发现 CLR 可以产生更高的测试准确度,尽管他们的学习率很高。

简介

在大多数神经网络论文中,作者提供了 top-k 准确度分数以及训练/测试进行情况的图表。这篇论文的作者认为,必须报告额外的行为。如上图(左图)所示,当学习率设置为 0.14 时,我们可以观察到一个奇怪的现象。训练开始后,准确性实际上在再次上升之前下降了。在右边的图表中,当学习率设定在 0.25 到 1.0 之间时,网络在这些范围内表现很好。本文作者希望用循环学习率来进一步研究这一现象。

超收敛

该论文的作者首先尝试了三角循环学习率(图表的左侧部分)。我们可以观察到,随着学习率从 0.1 增加到 0.35,训练损失急剧增加(当学习率在 0.25 左右时)。此外,我们可以观察到测试准确性和测试损失之间奇怪的分歧行为。

在图表的右边可以看到另一个令人惊讶的结果。我们可以看到,通过循环学习率,网络实际上能够比典型的学习率更快地收敛。其中仅在 20,000 个时期内就达到了 93%的准确率。然而,不幸的是,训练以较低的准确率结束。本文作者创造了术语“超收敛”来指代这种现象,即与传统训练相比,网络被训练到更好的最终测试精度,但迭代次数更少,学习率更高。

网络插值

如果网络的权重初始化不同,则有理由认为网络找到的最优解(最小点)可能不同。将每个网络的权重与下面的等式结合起来,我们可以看到这些最佳点是否彼此相似。

正如上文所见(图片和图表),当作者将两种不同状态下的训练(常规学习率)网络结合起来时,我们可以看到一个单一的凹形,指示相似的最小点。但是,当我们结合使用 CLR 训练的网络的两个不同状态的权重时,我们可以观察到网络找到的最优解是不同的。

结论

总之,本文作者报道了用循环学习率训练残差网络时的一些奇怪现象。作者认为这些模式出现的根本原因是损失函数拓扑。令人惊讶的是,这篇论文中报道的现象只是作者所看到的所有现象的一小部分。

最后的话

没有多少研究者研究学习速率的动态如何影响网络性能。很高兴看到这些研究正在进行。

参考

  1. l .史密斯和 n .托平(2017 年)。探索具有循环学习率的损失函数拓扑。Arxiv.org。检索于 2018 年 6 月 29 日,来自https://arxiv.org/abs/1702.04283

ICLR 2018 海报亮点(第一部分)

原文:https://towardsdatascience.com/iclr-2018-posters-highlight-part-1-386e674f2f9a?source=collection_archive---------5-----------------------

今年的国际学习代表会议(ICLR)在加拿大美丽的温哥华举行,这是我和我的团队分享的一份快速旅行报告。由于我还没有找到任何关于 ICLR2018 的博文,所以我决定在 Medium 上分享这份报告。但在继续阅读之前,请注意,这是通过我的偏见镜头,只对我感兴趣的领域。

你可以在这里观看每一个主题演讲和演讲(谢谢脸书!):https://www.facebook.com/pg/iclr.cc/videos/?ref=page_internal

下面是我已经做了深入阅读标记的海报。其中大部分是“研讨会”论文。在我看来,“研讨会论文”和“会议论文”实际上是一样的。他们只是在不同的房间,但都同样拥挤。我个人更喜欢“研讨会”论文。

1。在机器学习中放一个 bug:一个蛾的大脑学习阅读 MNIST。

关键词:神经网络

为什么我觉得这张海报很有趣?

即使是这种最简单的生物神经网络,它也大大优于标准的机器学习方法,如最近邻、SVM 和卷积神经网络(CNN)

将生物工具包移植到 ML 任务的潜在好处

实施细节

1)给蛾嗅觉(嗅觉)网络的计算模型分配学习阅读 MNIST 数字的任务。“蛾网”与飞蛾已知的生物物理学密切相关。

2)为了学习,MothNet 只使用了生物神经网络工具中广泛存在的一些结构元素:一个嘈杂的前置放大网络,具有由高维稀疏层调节的竞争抑制和可塑性

  • 【初学者友好】“竞争性抑制”或“Hebbian”听起来很花哨,但它们并不是那么难的概念。竞争性抑制是酶抑制的一种形式,其中抑制剂的结合阻止了酶的目标分子的结合。赫比安法则认为,如果两个神经元同时放电,它们之间的联系可能会得到加强。

2。不衰减学习速率,增加批量

关键词:批量大小,学习率

为什么我觉得这张海报很有趣?

该论文声称,在训练期间以线性速率增加批量大小与学习速率下降一样有效。

很好地证明了在 SGD 优化中调整学习率和增加批量之间的等价性

它显示了评估势头、Adam 等的努力。

实施细节

  1. 作者是理论物理博士(!)并且他用他在随机微分方程方面的深入知识(SDE。还记得布朗运动吗?)将随机梯度下降(SGD)解释为 SDE。
  2. 如果你看海报,这部作品的核心是左下角的“SGD 作为随机微分方程”一节。其他的都只是展示结果而已。
  3. 它定义了“噪声尺度”g = eN/B(1-m)其中 g 是噪声尺度,e 是学习率,N 是训练集大小,B 是批量大小,m 是动量系数。噪声使 SGD 远离尖锐的最小值,因此存在一个最佳批量,使测试集精度最大化。这个最佳批量大小与学习率和训练集大小成比例。
  4. 这个噪音等级来自于他之前的论文关于一般化和随机梯度下降的贝叶斯观点。这是一个相当长的数学推导过程,从 dW/dt = dC/dW+η(t)(该部分的第一个等式)开始,其中 W 是参数,C 是成本函数,η(t)是白噪声。你可以看到 dC/dW 是一个梯度。
  5. 然后他引入 F(W),这是一个描述梯度协方差的矩阵,也是当前参数值的函数。如果我冗长的解释让你感到困惑,看看中的等式 11、12、13,关于一般化和随机梯度下降的贝叶斯观点。
  6. 最后,它吹嘘用 64 个 TPU 在 29 分钟内训练了 ImageNet)然后我在上面看到了 Quoc Le 这个名字:)

3.强化行走:用蒙特卡罗树搜索学习在图中行走

关键词:蒙特卡罗树搜索,知识图,强化学习

为什么我觉得这张海报很有趣?

因为这是我们团队的论文!我们可以把它做成销售图,然后生产出来。

结合 RNN 和 MCTS(蒙特卡罗树搜索)的策略梯度在知识图推理中的新颖应用

实施细节

  1. 问题定义:学习遍历一个图 G = (N,E),其中 N 是一组节点,E 是一组边,以便为给定的一对源节点 Nt ∈ N 和查询 q 找到一个目标节点 Nt ∈ N
  2. 训练数据集是
  3. RNN 将先前状态、先前动作和目标节点的历史编码到向量 q 中
  4. 用全连接 NN 把 q_t 和 N&E 一起编码成一个高层嵌入向量 h 的(我讨厌介质还是不支持下标。看海报“模特”部分。)
  5. 为什么把 RNN 和 MCTS 结合起来,而不是正常的政策梯度?策略梯度法一般样本效率较低,尤其是在报酬信号稀疏的情况下,比如在这个问题中,报酬({0,+1})只出现在一个轨迹的末端。MCTS 有助于生成具有更多积极回报的轨迹,我们可以使用这些轨迹来进一步改进政策。
  • [初学者友好]什么是 MCTS?
    非常简单地说:1。建立一个前瞻树(如博弈树。)
    2。使用推广(模拟)来产生奖励。
    3。将类 UCB(置信上限)公式应用于树的内部节点。

4。负责任地预测:通过学会推迟来增加公平性

关键词:公平,学会推迟

为什么我觉得这张海报很有趣?

本文件提出了一个确保分类公平的框架。它探索了学习推迟的模型。

把学会推迟作为实现公平的一种手段的想法相当新颖。

实验表明,这种策略不仅可以提高预测的准确性,还可以减少决策中的偏差。

实施细节

1)看橙色图。当 IDK 模型预测时,系统输出该模型的预测。当模型显示 IDK 时,系统输出决策者的预测。

2)因此,第一阶段是标记疑难案例以供审查。

3)在数学上,我们可以将 IDK 模型描述如下。

4)然后,该模型可以被训练为使用示例损失函数(例如,分类误差、交叉熵)来最小化以下损失函数。

5)我让它听起来很简单,但这并不是本文中数学的终结。它从上述思想中分支出来,建立可微的 IDK 学习模型,并使 s_i 成为“延迟概率”,而不仅仅是 0 和 1。

6)他们选择“完全不同的影响”作为公平标准。

5.学习深度模型:临界点和局部开放性

He was the only author who didn’t bring the proper poster. I liked how indifferent (read: cool) he is being about the presentation.

关键词:非凸优化

为什么我觉得这张海报很有趣?

这是一项“理论构建”工作。

它使用“局部开”的概念来绘制局部最优和全局最优之间的等价关系。

本文不要求对激活函数的可微性进行假设。

实施细节

1)为 Burer-Monteiro 的经典结果提供一个简单的证明,并将其推广到非连续损失函数。

2)证明了两层线性网络的每个局部最优解都是全局最优解。与文献中的许多现有结果不同,他们的结果不需要对目标数据矩阵 Y 和输入数据矩阵 x 进行假设。

3)发展多层线性神经网络的局部/全局最优等价的几乎完整的特征。

我没有详细检查这个结果的证明,但它似乎是正确的。

6。隐式模型的梯度估计器

关键词:隐性模型

为什么我觉得这张海报很有趣?

它为用于数据采样的生成模型(如 GANs)提供了一种估计某些训练目标梯度的方法。

想法是这可用于培训程序。

提出“Stein 梯度估计器”,直接估计隐式定义分布的得分函数。

实施细节

1)隐式概率模型由随机过程定义,该随机过程允许直接生成样本,但不允许评估模型概率。

2)这个想法基于 Stein 的身份:内核化的解决方案。本文介绍了贝叶斯神经网络和遗传神经网络的应用。

3)大多数现有的学习隐式模型的方法依赖于对基于梯度的优化的难以处理的分布或优化目标进行近似,这易于产生不准确的更新,从而产生差的模型

7。TensorFlow 中批量学习的弹性反向传播(Rprop)

关键词:张量流

为什么我觉得这张海报很有趣?

它在 Tensorflow 中实现了弹性反向传播(Rprop)算法,并表明在用 RNN 解决简单任务时,它的性能优于 Adam。

实施细节

Rprop 算法只考虑要优化的函数 f 的偏导数的符号,而不考虑它们的绝对值

2)在每次迭代中,如果偏导数的符号

8。修剪,还是不修剪:探索模型压缩中修剪的功效

关键词:模型稀疏性,模型压缩

为什么我觉得这张海报很有趣?

这是一个有益的实验。大型稀疏模型(为了减少模型的内存占用而进行修剪的大型模型)被修剪成目标大小。他们表明,这些模型比小型密集模型性能更好。(比简单的缩小模型架构的规模更有效。)

结果显示在 conv 模型和 seq2seq 的各种数据集上。

作者甚至公开了代码。

除了我亲手挑选的,这里还有 2018 年 ICLR 最佳论文:

良好的..今天到此为止!我的手机里还有一些其他的海报照片,所以如果时间允许,我可能会写第二部分。感谢阅读!

ICML 2018:转移、多任务和半监督学习的进展

原文:https://towardsdatascience.com/icml-2018-advances-in-transfer-multitask-and-semi-supervised-learning-2a15ef7208ec?source=collection_archive---------5-----------------------

机器学习国际会议于去年 7 月在斯德哥尔摩举行。总之,它展示了机器学习中许多有趣的趋势和方向。由于 ICML 是一个如此大的会议,我将把我的注意力集中在会议上发生的一些有趣的事情上。

具体来说,今年的 ICML 将口头演讲分成了几个不同的“曲目/时段”我很高兴看到其中的三次会议集中在“迁移和多任务学习”上,因为这一直是我感兴趣的领域。此外,大量的海报涉及到这些概念以及其他曲目的一些口述。

缺乏大量干净的标记数据仍然是深度学习潜在影响的障碍。对于许多任务来说,总体上缺乏数据点(例如,预测选举、诊断罕见疾病、翻译成稀有或灭绝的语言……)。在其他情况下,数据是存在的,但有噪音或标记不良(例如,在特定关键字下从 Google 抓取的图像,通过 NLP 分配标签的医疗案例,仅部分注释的文本语料库)。不管是什么原因,找到从有限的或有噪声的(半相关)数据中学习的方法都有明显的好处。

三种这样的方法是迁移学习、多任务(从技术上来说,这是迁移学习的一个子类,就像领域适应一样,但是在本文中,我将它们作为独立的实体对待)和半监督学习。还有其他方法(主动学习、元学习、完全无监督学习),但本文将集中讨论与这三者相关的 ICML 文章(尤其是前两种)。由于这些领域之间的界限并不总是很清楚,我们也可能会涉足其他一些领域。对于需要复习的读者,这里有一个简单的概述。更详细的概述,请参见 Sebastian Ruder 关于迁移学习多任务学习的精彩博文。

Overview of the various idioms. (As an aside a neat trick I just discovered you can actually render markdown in Medium. So if you have need of nested lists or other things just embed a Github gist with a .md extension).

我总是发现迁移学习和多任务学习是非常重要的工具,不管是在哪个行业或领域。无论您是在医学、金融、旅游还是娱乐领域工作,也无论您是在处理图像、文本、音频还是时间序列数据,您都有可能从采用通用的预训练模型并根据您的特定领域对其进行微调中受益。根据您的数据,也很可能有多个相关的任务,您可以训练您的神经网络来学习联合解决,从而提高整体性能。

那些关注医学深度学习(但对其他人也有用)的人特别感兴趣的是一篇题为“ 不要喊狼来了:远程监督的多任务学习重症监护 ”的论文在 ICU 病房中,经常会出现假警报的问题,以至于护士/医生对它们变得麻木不仁。本论文的重点是使用多任务和半监督学习来检测真正威胁生命的 ICU 事件,而不是虚警。该论文的作者着眼于使用带有辅助任务的多任务学习来提高模型的性能,而不需要花费大量时间进行注释。具体来说,他们的模型“结合了大量远程监督的辅助任务,以显著减少训练所需的昂贵标签的数量。”其次,他们开发了一种新的方法“远程监督多任务学习,自动从多元时间序列中识别大量相关的辅助任务,以从标记和未标记的数据中联合学习。”演讲的视频可以在 YouTube 上找到。

如果你想要多任务学习的好处,但只有一个任务怎么办?论文“ 伪任务增强:从深度多任务学习到任务内共享——再回到 ”就是针对这个问题。作者建议利用伪任务来帮助提高主任务的性能。这是可能的,因为在基本层面上,多任务学习通常通过在中间层和上层之间共享特征以及学习用于特定任务的特定任务解码器来工作。因此,训练具有多个解码器的模型应该带来相同的好处,即使解码器都用于相同的任务,因为每个解码器以不同的方式学习任务;这些额外的解码器被称为“伪任务”该论文的作者在 CelebrityA 数据集上实现了 SOTA 结果。我很高兴地看到他们也在 IMDB 情感数据集上进行了测试。他们使用了一个基线模型,并通过使用他们的技术进行训练显示出显著的改善。这表明该技术可以潜在地与多种不同的神经网络架构一起工作。

GradNorm:深度多任务网络中自适应损耗平衡的梯度归一化

本文描述了一种新的多任务神经网络的规范化技术,帮助他们更快地收敛和提高整体性能。它还将需要调整的超参数总数减少到一个。使用 GradNorm,他们在 NYU2 数据集上获得了 SOTA。总体而言,这是一篇有助于降低训练 MLT 算法的复杂性和难度的扎实论文。最后,作者做了有趣的观察,“GradNorm 可能有超出多任务学习的应用。我们希望将 GradNorm 方法扩展到类平衡和序列到序列模型,在所有情况下,梯度信号冲突的问题都会降低模型性能。”

通过学习转移学习

A diagram from the paper describing how L2T works.

到目前为止,大多数迁移学习论文只研究了从源域到目标域的知识迁移,或者通过预初始化权重和冻结层,或者通过降低学习速率。这篇论文最好被描述为“元迁移学习”或学习如何最好地执行迁移学习任务(L2T)。作者描述说:

与 L2T 不同,现有的迁移学习研究都是从零开始,即只考虑感兴趣的领域对,而忽略先前的迁移学习经验。更好的是,L2T 甚至可以收集所有算法的智慧,考虑到上面提到的任何算法都可以应用于迁移学习体验

这自然会引出一个问题,这和“元学习”有什么不同事实上,L2T 可以被视为一种特殊类型的元学习;像元学习一样,它利用过去的历史来改进学习方式。然而,在这个上下文中,历史指的是从源域到目标域的迁移学习任务。

A diagram of the difference between different types of learning. From the article (Figure #)

该论文的作者在 Caltech-256 上评估了 L2T 框架并绘制了数据集草图。该模型改进了以前的 SOTA 结果,特别是在例子很少的情况下。

我很高兴看到用卷积网络进行迁移学习的显性归纳偏差【在被 ICLR 拒绝(我认为不公平)后进入 ICML。本文描述了一种应用正则化来有效地进行迁移学习而不是修改学习速率的方法。作者提出了几种新的正则化方法,这些方法基于预训练模型中的权重应用不同的惩罚。他们取得了很好的实验结果,我目前正致力于将其应用到我的几个医学成像模型中。****

通过迁移学习进行课程学习:深度网络的理论和实验 ”主要是一篇研究“课程学习”的理论论文,这是一种借鉴自教育/心理学的学习习语,旨在以渐进和有组织的方式学习更难的概念。具体而言,本文着眼于迁移学习和课程学习之间的关系,以及课程学习和为训练提供的示例顺序之间的关系及其对随机梯度下降的影响。这里需要注意的是,这种类型的转移不同于迄今为止讨论的其他类型。在这种情况下,迁移学习指的是研究“知识从一个分类器到另一个分类器的迁移,如教师分类器学生分类器。”因此,在这种类型的迁移学习中,“迁移的不是实例表示,而是训练实例的排序。”作者的结论是,课程学习的学习速度总是更快,有时最终的概括能力会得到提高,特别是对于困难的任务。****

学习无监督领域适应的语义表示

Figure 1 from the paper.

(无监督的)域适应中的一个问题是目标和源分布之间的对齐。无监督的领域适应是一种迁移学习。作者在这里开发了一个语义转移网络,它通过对齐标记的源质心和伪标记的目标质心来学习“未标记的目标样本”的表示更简单地说,他们的方法旨在通过语义损失函数,基于最小化源域和目标域之间的整体映射差异来对齐源域和目标域的分布。结果包括在 ImageCLEF-DA 和 Office31 数据集上的 SOTA 性能。他们的代码可以通过点击这里在线获得

用黑盒预测器检测和校正标签偏移 是另一篇关于领域适应的有趣论文。它的重点是如何检测训练和测试之间 y 分布的变化,这在医学中非常有用,如果某种疾病的流行或爆发会极大地影响分布。

面对训练集和测试集之间的分布偏移,我们希望检测到量化这种偏移,并且校正我们没有测试集标签的分类器****

本文的具体主题主要是协变量转移。作者开发了几个有趣的标签移动模拟,然后应用于 CIFAR-10 数据集和 MINST。与未校正的模型相比,他们的方法能够大大提高精确度。

用语义映射纠正异构模型

Diagram from the paper describing the modeling of feature spaces.

我发现这篇论文很有意思,因为它结合了最优运输来调整分布。

最优运输成为改革的主要工具,它具有调整分配的能力

总之,本文在人工数据集和真实数据集(包括亚马逊用户点击数据集和学术论文分类数据集)上提出了新颖的观点并取得了良好的结果。

这些只是 ICML 2018 的一些有趣的论文;还有许多其他伟大的论文。我确实希望在某个时候总结一下元学习和其他半监督学习论文。我发现这些论文也很吸引人。

公告

我仍在努力完成关于将机器学习模型部署到生产中的系列文章中的下一篇文章。在那篇文章中,我将讨论使用 SeldonCore 和 Kubeflow 以可扩展的方式部署机器学习模型。

northern New England Data and Analytics 将于 8 月 15 日举办一次数据会议,我们将在会上通过 Seldon Core 和 Kubeflow 部署一个最近的 NLP 模型,以便在聊天机器人中使用它。Meetup 将在 Zoom 上进行流媒体播放。

IcoOmen:使用机器学习预测 ICO 价格

原文:https://towardsdatascience.com/icoomen-using-machine-learning-to-predict-ico-prices-29fa4cec6d86?source=collection_archive---------16-----------------------

在真实世界的数据上使用机器学习。

介绍

加密货币无需介绍。加密货币曾经是在线聊天论坛上书呆子社区的专利,现在几乎已经成为主流。另一方面,ico 鲜为人知。

最初的硬币发行,通常被称为 ICO 或代币销售,是一种筹资手段,其中新发行的加密货币中的代币与公众交换为比特币或以太坊等其他加密货币。

这些旨在用于资助早期阶段的加密货币项目,但是它们是相当高风险的投资,因为在 ICO 中筹集的超过 10%的资金已经丢失或被黑客攻击,并且只有 10%发行的 ICO 代币在 ICO 后用于实际的代币生态系统,而其余的只是简单的交易。

直到最近,对 ICO 的监管还很少,市场非常繁荣,ICO 基金增长迅速。2017 年末和 2018 年初尤其如此,如下图所示。这一增长此后迅速放缓,因为整个加密货币市场变得相当悲观。

Source: Elementus.io

ico 和加密货币的不可预测性通常会产生一个有趣而困难的问题——我们能对这些行为建模甚至预测它们吗?

更具体地说:

能否用机器学习来预测 ico 的成功/价格?

让我们找出答案。

方法学

  1. 选择输入和输出。
  2. 收集和汇总数据。
  3. 准备数据。
  4. 探索并尝试理解数据。
  5. 选择一个机器学习模型。
  6. 衡量模型的性能。
  7. 保存模型。
  8. 使用模型进行预测。

1.选择输入和输出

输入

选择正确的输入和输出(在监督 ML 的情况下)对于机器学习算法的成功至关重要。在输入和你试图预测的输出之间,需要有某种关联。做到这一点的最好方法是尝试并获得一些领域知识。我对 ico 的各个方面做了一些研究,以衡量可能影响其未来价值的因素。

影响其绩效的 ICO 主要建议因素如下:

  • 开发团队的质量— 更好的团队,更好的 ICO 产品质量。
  • 社交媒体上的受欢迎程度,如 Twitter 上的关注者数量— 一个 ICO 的知名度越高,它获得资金的机会就越大。
  • 与 ICO 相关的因素具体来说——价格、总供应量、市值……
  • ICO 推出时的市场相关因素—ICO 推出时,加密货币市场是否表现良好?

然后,我创建了一个我认为可能影响 ICO 价值的特性列表并检查了我是否可以从任何来源收集这些数据,并创建了一个最终的输入列表。

不幸的是,很难从数字上收集某些数据——例如,度量从事 ICO 工作的开发团队的质量——您度量多年的经验吗?这是衡量质量的有效方法吗?

此外,很难找到其他指标的数据,如 ICO 推出时的受欢迎程度。例如,很难获得 Twitter 的历史数据,即使使用 Wayback Machine ,它不会对每个页面进行索引,这使得在一个 ICO 推出时很难获得 Twitter 追随者的数量。

最终使用的功能列表:

  • 美元价格。
  • BTC 的价格。
  • 总供给。
  • 市值——代币销售期间可以购买的代币数量。
  • 可用供应。
  • 美元上调。
  • 以太坊上市时的价格。
  • 推出时的比特币价格。
  • 月 ICO 上线。
  • ICO 发布的日期,例如当月的第 8 天。
  • ICO 从哪个国家推出。
  • ICO 持续天数。

输出

ico 通常仍然是一种新的筹资方式,所以没有多少 ico 可以用来收集数据。选择六个月的期限,因为这足以观察到 ICO 价格的潜在增长,并且从可用数据来看,有足够多的 ICO 超过六个月。

最终输出:

一个 ICO 六个月后的价格。

ICOs 上收集的部分数据示例

此处提供完整数据集

2.收集和汇总数据

这个项目的很大一部分是数据收集。ICOs 上没有可用的数据集,因此必须创建数据集。

使用了 restful API,用 C#编写,遵循 dotnet 核心框架。这个 API 汇集了来自不同站点的数据,并将其存储在一个 Mongo 数据库中。

有些数据,如 ICO 发布的国家/地区,必须手动收集,因为无法始终从特定来源获得这些数据,因此必须使用多个网站。数据是在 2 885 个 ico上收集的。

3.准备数据

一旦数据被收集并存储在 Mongo 数据库中,就必须将数据转换成可用的数据集。从各种来源收集的所有数据都使用数据库视图进行聚合。

如上所述,收集了 2 885 个 ico 的数据,但这些数据很少,因此需要进行数据准备。

一旦数据被清除,我们就有了 189 个 ico 的信息。最后,进一步过滤,只包括存在时间超过六个月的 ico 数据,最终我们的数据集中有 109 个 ico。

准备数据时遇到的问题:

  • 不洁数据

ICO 的开始和结束日期、ICO 持续时间和 ICO 月份的值无效,已通过手动更正这些字段进行了清除。

  • 缺失数据

处理缺失数据的常用方法通常是使用平均值或中位数。然而,由于数据的稀疏性(不到 10%的数据具有大部分必需的字段),这种方法没有被采用。

相反,选择具有大多数必填字段的数据,然后从各种网站手动收集缺少的值,如 ICO 推出的国家。

  • 数据冲突

一些数据是相互矛盾的,例如,网站上有不同的开始和结束日期的 ICO 或国家推出。这是通过检查多个来源并采用一致的值来处理的。

  • 分类数据

一种热编码应用于分类数据字段——ICO
日期、ICO 发布月份和 ICO 国家。

数据收集和准备阶段的工作流程

4.探索并试图理解数据

我们可以通过计算相关系数和绘制散点图来研究输入和输出之间的关系。

以美元/BTC 计价的 ICO 推出时的价格与六个月后的期货价格密切相关(显然!),而其他投入与产出并不密切相关。

此外,至关重要的是,要确保 ICOs 数据的分布能够代表当前市场,以便有一个能够很好地概括的模型。这一目标已经实现,收集的数据与按国家划分的 ICO 分布相关的统计数据相互关联。

Distribution of ICO Data Per Country in ICO Omen.

5.选择机器学习模型

岭回归

一旦对数据进行了一次性编码,输入矩阵就形成了所谓的待定矩阵或胖矩阵。这实质上意味着特征比示例多(128 个特征对 109 个数据点)。

这意味着我们的回归模型易受过度拟合和多重共线性的影响。

"多重共线性是自变量之间高度相关或关联的状态。因此,这是数据中的一种干扰,如果在数据中存在,对数据做出的统计推断可能不可靠。”— 统计解决方案

为了避免这种情况,我们应用正则化。在我们的案例中,我们应用了岭回归(L2 正则化),它惩罚了非常大的权重。你可以在这里阅读更多关于岭回归的内容。

岭回归公式:

Source : Penn State

神经网络

我们还使用神经网络将结果与回归模型获得的结果进行比较。

对于神经网络,我们使用 tanh 激活函数,对于解算器,我们使用 Adam 解算器和梯度下降解算器。

6.衡量模型的性能

使用了两种性能测量方法— RSquared(R )均方根误差 ( rMSE)。

R ,度量模型可以解释的“方差的百分比”。高 R 值通常是好的,但并不总是如此,因为这可能意味着您的模型与数据过度拟合。你可以在这里阅读更多关于 R 的内容

rMSE,测量我们的模型达到的均方误差的根(误差——我们的模型预测值和实际值之间的差)。

结果

所有结果都是使用维持方法计算的,性能是根据测试数据(即模型从未见过的数据)测量的。

该图描绘了预测结果与测量结果。这显示了预测值和测量值之间的相关性。越靠近虚线的值表示相关性越好。

线性回归模型的 rMSE 得分为 0.86,R 得分为 0.62。

神经网络模型的 rMSE 分数为 0.58,R 分数为 0.73。

7.保存模型

一旦我们有了满意的模型,我们就应该保存这个模型,这样我们就可以在以后重新使用它来进行预测。

我使用了 Joblib ,这是一个 python 助手类,它是 SciPy 包的一部分,为流水线操作提供了实用程序。它使得保存和加载模型变得简单。

8.使用模型进行预测

一旦保存了模型,就可以加载该模型并进行预测,而无需重新训练模型。

以下是如何使用保存的模型进行预测的示例:

结论和最终想法

现实世界中的机器学习很大程度上依赖于你的数据。与处理模型相比,您通常会花费更多的时间来清理、准备和聚合数据。

在本文中,我们设法创建了一个模型,它可以相当好地预测 ICO 的价格。我们还展示了将机器学习应用于现实世界问题的一般步骤。

感谢您阅读这篇文章,如果您有任何想法或意见,请告诉我。😃

你可以在推特和/或这里找到我。

源代码

所有源代码都是可用的,以文档化的格式。ML 模型还包含一个 Google Colab 链接

我会选择点数,而不是小节

原文:https://towardsdatascience.com/id-go-with-points-not-bars-f48b64030564?source=collection_archive---------18-----------------------

Aaron Carroll 在结果/NYT 中写道尼文等人 2015 年的研究发表在 JAMA Internal Medicine 上,该研究表明,在一项研究表明严格控制血糖是一个好主意后,医疗实践如何增加,但在第二项更大规模的研究推翻了指导方针后,没有减少。卡罗尔的观点是,唯一比说服医生开始做某事更难的事情可能是说服他们停止。

但是让我们开始真正有趣的东西:情节!

原始图在左边,NYT/Upshot 版本在右边。按照典型的 NYT 风格,他们剥离情节,揭示一些更令人愉悦的东西。

他们坚持使用条形图——也许是为了尽可能忠实于原文——但我认为点数在这里最有效。这部分是个人偏好,部分是 Tufte 启发的关于数据-油墨比率的智慧。基本原理是这样的:所有的数据都存在于棒线的尖端,那么为什么不仅仅绘制尖端呢?

我使用ggplot2()包在 R 中创建了这个图。JAMA 的作者可能在某处共享了底层数据,但是我什么也没找到。所以我用 WebPlotDigitizer 从公布的图中提取近似值。如果你想修改的话,下面是代码。

通过患者相似性的拓扑数据分析识别二型糖尿病亚组

原文:https://towardsdatascience.com/identification-of-type-2-diabetes-subgroups-through-topological-data-analysis-of-patient-similarity-91838f2ccf74?source=collection_archive---------3-----------------------

这篇原创的博客于 2015 年首次出现在 Ayasdi 网站上。

Ayasdi 的合作者昨天取得了另一项重大胜利,如 Fast Company 所述,西奈山的 Ichan 医学院在超负盛名的期刊Science:Translational Medicine上发表了论文,表彰他们利用拓扑数据分析识别先前未知的糖尿病亚型的工作。

这篇论文包含了突破性的研究,是对精准医疗超越癌症的验证。西奈山伊坎医学院的生物医学信息学主任 Joel Dudley 博士使用 Ayasdi Core 来确定新的患者亚组,这将最终实现对这种广泛传播、昂贵和毁灭性疾病的更精确的诊断和治疗。

对科学、医学和病人来说都是惊人的。在全球范围内,糖尿病是一种发病率很高的流行疾病,我们中的许多人都有家人受其影响。

医生知道,T2D 诊断患者有多种表现型,对糖尿病相关并发症具有易感性。

西奈山的伊坎医学院有一个大型数据库,将 30,000 多名患者的遗传、临床和医疗记录数据配对。西奈山的数据集不仅庞大,而且复杂,因为它包含许多不同的数据类型。除了基因组测序数据,它还包括每个患者的年龄、性别、身高、体重、种族、过敏、血液测试、诊断和家族史等信息。Joel 和他的团队使用精准医学方法,基于高维电子病历(EMRs)和来自 11,210 个个体的基因型数据(遗传标记和临床数据,如血液水平和症状),来表征 T2D 患者群体的复杂性。

使用拓扑数据分析,西奈山在患者-患者网络中发现了三个不同的 T2D 亚组。

  • 亚型 1 以 T2D 并发症糖尿病肾病和糖尿病视网膜病变为特征;
  • 亚型 2 富含癌症恶性肿瘤和心血管疾病;
  • 亚型 3 与心血管疾病、神经系统疾病、过敏和 HIV 感染密切相关。

他们的网络登上了杂志的封面,并且可以在 STM 网站上找到。

因此,使用 Ayasdi Core,他们能够发现大型复杂数据集中的隐藏模式,使创新研究机构和制药公司(如 Mount Sinai)能够加快生物标志物发现、疾病类型细分和目标药物发现。

因为 Ayasdi 的方法不需要开发广泛的临床假设,并且可以根据数百种先进的数学算法自动绘制相关的患者亚组,所以 Dudley 博士的初步研究结果表明,二型糖尿病不是一种单一的疾病。

相反,它由几个小组组成,每个小组都有自己独特的复杂因素。

这一新的见解可能会为所有二型糖尿病患者带来更有效的治疗方案和更好的患者结果,并推进精准医疗的实践。

“通过使用 Ayasdi,我们看到目前二型糖尿病的临床定义太不精确,”Dudley 博士说。“我们的数据表明,根据患者人群的亚组,可能存在 3 型、4 型、5 型或更多型糖尿病,每个患者都可以从不同的治疗方法中受益。这些是令人兴奋的发现,有可能改变我们治疗这种主要疾病的方法。”

这是大医院的医生使用我们的软件改善患者护理并在顶级期刊上发表文章的第三个例子。

除了在糖尿病方面的工作,西奈山团队还利用 Ayasdi 研究了其他主要疾病。例如,在精神分裂症研究中,研究人员整合了从数百个病例中收集的 MRI 数据,并将其与分子途径数据配对。他们生成了大脑形状的数据模型,揭示了精神分裂症患者与对照组相比有显著差异的一小块区域。在未来,这一发现可能允许医生通过查明精神分裂症患者大脑中哪些分子路径被破坏来更有效地识别和治疗精神分裂症。

随着我们的合作者继续使用我们的软件改变世界,敬请关注下一季度的更多新闻。

要成为合作者,请发电子邮件给我们,姓名为collaborations@ayasdi.com

识别 Quora 上的重复问题| ka ggle 上的前 12%!

原文:https://towardsdatascience.com/identifying-duplicate-questions-on-quora-top-12-on-kaggle-4c1cf93f1c30?source=collection_archive---------0-----------------------

如果你像我一样是一个普通的 Quoran 人,你很可能会无意中发现重复的问题,问同样的基本问题。

这对于作者和搜索者来说都是一个糟糕的用户体验,因为答案在同一问题的不同版本中变得支离破碎。其实这是一个在 StackOverflow 等其他社交问答平台上非常明显的问题。一个现实世界的问题,求人工智能解决:)

在过去的一个月左右的时间里,我和其他 3000 名卡格勒人一起,整夜都在为这个问题绞尽脑汁。这是我连续第二次参加严肃的比赛,有时会有压力,但总体来说我学到了很多——获得了前 12%的位置,一枚讨论金牌和几枚核心铜牌:)

一个 关于问题——Quora 已经给出了一个(几乎)真实世界的问题对数据集,每个问题对都带有 is_duplicate 的标签。目标是最小化测试数据集中重复预测的对数损失。训练集中大约有 40 万个问题对,而测试集中大约有 250 万个问题对。对,250 万!这些问题中的大部分是计算机生成的问题,以防止作弊,但有 250 万,天啊!我每隔一个小时就把我那可怜的 8GB 机器用到了极限

我的方法——我从@anokas 的 xgboost starter 开始,并逐渐在它的基础上构建。我的特征集包含了大约 70 个特征,与顶级 Kagglers 的方法相比,这是一个相当低的范围。我的特征可以大致分为基于 NLP 的特征、基于单词嵌入的距离和基于图形的特征。让我详细说明一下:

N 我尝试继续使用 tfidf 分数,但这既没什么用,又计算量大。相反,最重要的特征之一是加权单词匹配份额,其中每个单词的权重是该单词在语料库中的频率的倒数(基本上是 IDF)——如果我在两个问题中都有一个罕见的单词,他们可能会讨论类似的话题。我还有余弦距离、jaccard 距离、jarowinkler 距离、hamming 距离和 n-gram 匹配(shingling)等特性。

我在 NLP 任务中广泛使用的一个库是 Spacy,它最近开发了一些很棒的功能——Spacy 相似性也是一个很好的特性。我想到的一些有创意的问题与问题的类型有关——无论是“如何”的问题还是“为什么”的问题——取决于句子的第一个单词。奇怪的是,在建模的时候,我本应该想到建立“最后一个单词的相似度”,但是完全没有想到!命名实体是理解问题上下文的关键——因此 common_named_entity 得分和 common_noun_chunk 得分是显而易见的选择。我推出了一个关于通过 wordnet 语料库计算相似度的内核,但是 wordnet 在易用性、速度和词汇量方面都有所欠缺。

字嵌入基础距离 :

做 NLP 比赛的时候,Word2Vec 能不能留下!我觉得 word2vec 可能是我读过的最酷的计算机科学概念,我总是被它的有效性所震撼。每时每刻。

Word2Vec Magic!

总之,我将问题映射到 Sent2Vec 格式的 300 维向量中,结果每个问题都有一个向量。自然地,基于距离的矢量特征被建立起来——余弦、城市街区、jacard、堪培拉、欧几里得和布雷柯蒂斯。必须提到@abhishek 的脚本作为这些功能的灵感来源。不幸的是,我不能构建真正的嵌入层,我可以在 keras 中传递到 lstm 层——我的 RAM 不允许我这样做。我很快就会有真正的硬件了!

G 图形特征:在 NLP 比赛中,这些图形特征玩得相当扫兴!然而,这很好地提醒了我们,社交网络的理论可能如何应用于像 Quora 的问题对这样的数据集。

A typical graph structure in social media

这里,每个问题都是图中的一个节点,数据集中的一个问题对表示两个节点之间的一条边。我们也可以使用测试数据的图结构,因为我们没有在任何地方考虑 is_duplicate 标签——这 200 万条边对图贡献了很多!卡格勒夫妇就基于图表的功能是否应该是“神奇的功能”展开了激烈的讨论,这些功能应该被释放出来以创造公平的竞争环境。总之,所有这些特性都极大地提升了大多数模型:

  • 一个节点的度:本质上,问题的频率,这个问题在数据集中出现多少次,就有多少条边。这个特性带来了巨大的收益,因为 Quora 所做的问题抽样(对重复项进行上抽样)很可能依赖于这个频率。
  • 邻居交集:问题对的一级邻居的百分比,例如,Q1 的邻居是 Q2,Q3,Q4,Q2 的邻居是 Q1,Q3。(Q2 Q1)的共同邻居是 Q3,占所有一级邻居的一半。
  • 分离度:这是我通过广度优先搜索想到并实现的一个特性,但并没有带来很大的改进。
  • PageRank:我实现了这个功能,甚至在 kaggle 上发布了一个内核——page rank 较高的问题链接到重要的(page rank 较高的)问题,而垃圾问题链接到垃圾问题。
  • kcore/kclique: K-core 基本上是最大的子图,其中每个节点都连接到至少“K”个节点,但没有给我太多的收获。我曾经想过 kclique,但是因为时间不够而没有实现:(结果证明这是一个相当重要的想法!
  • 加权图:在比赛的后期,kagglers 的同事分享了一个加权图的想法,其中每个节点的权重是 weighted_word_share(我们之前讨论过)。这个加权图中的邻居交集是有用的。

传递性魔法——继续图结构,对问题之间的传递性建模是一种显而易见的方法。例如,如果 Q1 与 Q2 相似,Q2 与 Q3 相似,这意味着 Q1 与 Q3 更相似(根据我们的数据集)。这是我开始构建的功能之一,但中途放弃了,这是一个代价高昂的错误。许多顶级解决方案以某种形式使用了这一功能,一个更简单的版本是平均每个问题与其对应的邻居之间的重复概率。

我的白板会议

Part 1 of 2

Part 2 of 2

一些混蛋

当一个像我这样的菜鸟一头扎进一个大圈子时,肯定会有麻烦。尽管我有意识地努力保持管道的模块化和版本控制,但由于管道中的一个严重错误,我损失了几乎一个周末的工作。经过艰苦的学习,我在 ipython 笔记本上恢复并改造了管道。我在构建特性时面临的一个主要挑战是编写内存高效的代码,而不是重新构建以前的特性,模块化是关键。这导致了另一个混乱——因为我无法在我的 RAM 中处理我的整个测试数据集,我将它分成六个子集,并迭代地构建特性。这意味着我在旧的数据框架和新的特性之间做一个 pandas concat,我很少关注索引:(花了几天时间对所有 NaN 特性挠头。没有错。

QID 难题:

训练数据集的每个问题都有一个 ID,因此每行都有一个 QID1 和 QID2。然而,测试数据集的情况并非如此,这意味着“QID”不能直接用作一个功能。一位 kaggler 的同事发布了一个令人难以置信的创造性的观察,随着 QID 的增加,平均重复率(滚动平均值)下降——很可能是 Quora 随着时间的推移改进算法的迹象,从而随着 ID 的增加减少重复问题的数量。这一推断基于这样的假设,即 QID 值没有被屏蔽,并且真正代表了发布问题的时间。为了在我们的测试数据集中对 qid 建模,我有一个将问题文本映射到 qid 的哈希表。现在迭代 test_df 中的所有问题——如果我遇到一个存在的问题,相应的 QID 被分配给它。否则,我们假设这是一个新问题,按照发布的时间顺序,将 QID 加 1。这导致了各种各样的特征,如 QID 差异、平均 QID、最小 QID,以期模拟随着时间的推移重复率的下降。

阶层失衡:

讨论的主要部分集中在猜测测试数据框架中的类别划分,这与测试划分并不明显相似。数学专家通过几个恒定值的提交,这里的和这里的,计算出一个狭窄的分割范围。训练集中大约有 34%的正重复,而测试集中估计有 16%-17%的正重复——这可能是改进的 Quora 算法的结果,或者是计算机生成的问题对的结果。无论如何,一个错误的训练数据集不会有所帮助——人们想出了过采样的解决方案(复制训练中的负行),或者通过适当的因子重新调整他们的预测。

我的模特——XGBoost 是爱情,XG boost 是生活

承认这一点非常尴尬,但我提交的只是一个单一模型解决方案,一个 2000 轮的 xgboost。公平地说,我没有在参数调整或构建多样化模型上花太多时间,因为太晚了。我尝试了默认的随机森林和 GBM,效果并不比 XGB 好。堆叠和集成也在路线图中,但只是停留在那里:(

相反,我花了一个很长的周末来学习 Keras 和建立密集的神经网络——这是我的第一次!通过了解各种超参数和理想的架构,激活函数,辍学层和优化背后的理论!非常有趣的东西!我用我的两层 sigmoid 神经网络和我的 70 个特性来完善它,但它从未接近 xgboost。正如我前面提到的,我无法用我的硬件构建嵌入层或 LSTMs,那肯定会有帮助。很快。

我为自己的建模管道感到自豪,不必为每个模型都创建一个函数而烦恼——当我构建数百个模型进行堆叠时,这会很有帮助。很快。

顶级解决方案:

金牌得主的赛后评论让我觉得自己完全是个菜鸟!我必须真正提高我的比赛水平,更加努力地去达到那个高度,铜牌离我不远了!从赢家解决方案中获得的一些主要经验:

  • 大多数团队根据加权图的边或节点的频率来重新调整他们的最终预测
  • 每个顶级团队都建造了一个有数百个模型的堆垛机,并有一个可重复使用的模型构建管道。
  • 使用了最先进的神经网络架构(Siamese/Attention NNs)、LightGBMs,但甚至像 ExtraTrees 或 Random Forests 这样的低性能模型也有帮助!
  • 图形特性是许多解决方案的核心,因为团队使用各种技术从中获取价值。一些去除了虚假的(不太频繁的)节点,一些使用邻居权重的平均值/中值,而大多数模拟了传递性。
  • 显然,问题 1 或问题 2 也很重要。令人惊讶!
  • NLP:以多种不同的方式处理文本——小写和不变,以不同的方式替换标点,包含和排除停用词,词干化和不词干化,等等。
  • 堆叠很重要,但人们也用单个 xgb 型号实现了 0.14 倍。
  • 第一名。真令人羞愧。

结论:

我应该更好地管理我的时间,为探索、特征工程、模型构建和堆叠分配适当的时间。上周我确实感到了压力,因为我提交的材料不够了。

  • 我的建模管道很适合测试,但是我需要在不同的超参数/数据子集上建立更多的模型。
  • 不要中途放弃构建特性,有些特性会导致代价高昂的失误。
  • 不要仅仅因为你花了时间在一个功能上,就过于沉迷于它。这有点好笑,哈哈!
  • 花大量时间在 Kaggle 内核和讨论上。他们太酷了:)

所以是的,就是这样。一场比赛结束,另一场比赛开始。Kaggle 会上瘾!

It’s true!

这篇文章最初发表在我的 博客 上。每周一篇博客

在背景噪音中识别希格斯玻色子

原文:https://towardsdatascience.com/identifying-higgs-bosons-from-background-noise-pyspark-d7983234207e?source=collection_archive---------17-----------------------

Large Hadron Collider

背景

在这篇简短的博客中,解释什么是希格斯玻色子是非常困难的。然而,为了保持它的基本性,根据一个大爆炸理论,在一个叫做玻色子的导火索导致它爆炸之前,整个宇宙曾经是一个单一的粒子。希格斯玻色子是以物理学家彼得·希格斯的名字命名的,他在 1964 年和其他六位科学家一起提出了这种机制,这表明了这种粒子的存在。这种亚原子粒子是在大型强子对撞机的一次实验中产生的。彼得·希格斯将因此发现获得 2013 年的诺贝尔奖。

历史说够了。现在进行一些有趣的机器学习!这是一个分类问题,以区分产生希格斯玻色子的信号过程和不产生希格斯玻色子的背景过程。

资料组

网址:http://archive.ics.uci.edu/ml/datasets/HIGGS#

这些数据是使用蒙特卡罗模拟产生的。前 21 个特征(第 2-22 列)是由加速器中的粒子探测器测量的运动特性。后 7 个特征是前 21 个特征的函数;这些是由物理学家得出的高级特征,有助于区分这两个类别。人们有兴趣使用深度学习方法来消除物理学家手动开发这些特征的需要。基准测试结果使用贝叶斯决策树从一个标准的物理包和 5 层神经网络提出了在原来的文件。最后 500,000 个示例用作测试集。

导入库

希格斯数据集是巨大的!因此,我们需要使用 Spark 来运行它。对于本文,我使用 Python 包装器 for Spark,或 PySpark。

**from** **time** **import** time
**from** **string** **import** split,strip
**from** **plot_utils** **import** ***from** **pyspark.mllib.linalg** **import** Vectors
**from** **pyspark.mllib.regression** **import** LabeledPoint

**from** **pyspark.mllib.tree** **import** GradientBoostedTrees 
**from pyspark.mllib.tree** **import** GradientBoostedTreesModel
**from** **pyspark.mllib.tree** **import** RandomForest, RandomForestModel

**from** **pyspark.mllib.util** **import** MLUtils

准备数据

接下来,我们对数据集中感兴趣的要素列表进行硬编码

feature_text='lepton pT, lepton eta, lepton phi, missing energy magnitude, missing energy phi, jet 1 pt, jet 1 eta, jet 1 phi, jet 1 b-tag, jet 2 pt, jet 2 eta, jet 2 phi, jet 2 b-tag, jet 3 pt, jet 3 eta, jet 3 phi, jet 3 b-tag, jet 4 pt, jet 4 eta, jet 4 phi, jet 4 b-tag, m_jj, m_jjj, m_lv, m_jlv, m_bb, m_wbb, m_wwbb'features=[strip(a) **for** a **in** split(feature_text,',')]

接下来,我们把数据转换成火花 RDD

inputRDD=sc.textFile(path_to_data) #Replace with actual pathinputRDD.first()

如果每行都是一个字符串,那么数据就没有用。因此,为了使用 PySpark 的机器学习库,我们需要用逗号将它分开,并将每个单元格分配给一个 LabeledPoint。第一列是目标,因此需要从模型特征中分离出来。

Data=(inputRDD.map(**lambda** line: [float(strip(x)) **for** x **in** line.split(',')]).map(**lambda** line: LabeledPoint(line[0], line[1:])))Data.first()

为了更清楚地看到过度拟合的影响,我们将数据的大小减少了 100 倍。然后,我们将 70%–30%分成培训和测试。

Data1=Data.sample(False,0.01).cache()(trainingData,testData)=Data1.randomSplit([0.7,0.3])

**print (**'Sizes: Data1=**%d**, trainingData=**%d**, testData=**%d**'%(Data1.count(),trainingData.cache().count(),testData.cache().count()))

梯度增强树

第一个分类器将使用梯度增强树来构建。

errors={} **for** depth **in** [1,3,6,10]:     
    start=time()        
    model=GradientBoostedTrees.trainClassifier(Data1,                                              
            categoricalFeaturesInfo={}, numIterations=3)        
    errors[depth]={}     
    dataSets={'train':trainingData,'test':testData}     
    **for** name **in** dataSets.keys():  
        *# Calculate errors on train and test sets*           
        data=dataSets[name]         
        Predicted=model.predict(data.map(**lambda** x: x.features))         
        LabelsAndPredictions=(data.map(**lambda** lp: 
                               lp.label).zip(Predicted))
        Err=(LabelsAndPredictions.filter(**lambda** (v,p):v != 
              p).count()/float(data.count()))         
        errors[depth][name]=Err     
    **print** depth,errors[depth],int(time()-start),'seconds' 
**print** errors

B10=errors
make_figure([B10],['10Trees'],Title='Boosting using 10**% o**f data')

随机森林

接下来,我们尝试随机森林分类器进行比较。

errors={}
**for** depth **in** [1,3,6,10,15,20]:
    start=time()
    model = RandomForest.trainClassifier(Data1, numClasses=2, 
           categoricalFeaturesInfo={}, numTrees=3,  
           featureSubsetStrategy="auto", impurity='gini', 
           maxDepth=4, maxBins=32)
    errors[depth]={}
    dataSets={'train':trainingData,'test':testData}
    **for** name **in** dataSets.keys():  
        *# Calculate errors on train and test sets*
        data=dataSets[name]
        Predicted=model.predict(data.map(**lambda** x: x.features))
        LabelsAndPredictions=(data.map(**lambda** lp: 
                               lp.label).zip(Predicted))
        Err=(LabelsAndPredictions.filter(**lambda** (v,p):v != 
             p).count()/float(data.count()))
        errors[depth][name]=Err
    **print** depth,errors[depth],int(time()-start),'seconds'
**print** errors

RF_10trees = errors
*# Plot Train/test accuracy vs Depth of trees graph*
make_figure([RF_10trees],['10Trees'],Title='Random Forests using 10**% o**f data')

一起想象

make_figure([B10,RF_10trees],['B10','RF_10Trees'],Title='Random Forests using 10**% o**f data')

利用深度学习识别交通标志

原文:https://towardsdatascience.com/identifying-traffic-signs-with-deep-learning-5151eece09cb?source=collection_archive---------2-----------------------

交通标志的成功检测和分类是自动驾驶汽车需要解决的重要问题之一。想法是让汽车足够智能,以达到成功自动化最少人类互动。在图像识别、自然语言处理、自动驾驶汽车等相关领域,深度学习相对于经典机器学习方法的优势迅速上升,并辅之以 GPU(图形处理单元)的进步,这令人震惊。

深度学习

Attendance at the Annual Conference on Neural Information Processing Systems (NIPS)

图表只显示了 2015 年和 2016 年 NIPS 有超过 6000 人参加。图表显示对深度学习和相关技术的兴趣激增。

深度学习是一种机器学习技术,其中人工神经网络使用多个隐藏层。这要归功于两位著名的神经生理学家大卫·胡贝尔和托尔斯滕·威塞尔,他们展示了视觉皮层中的神经元是如何工作的。他们的工作确定了具有相似功能的神经元如何组织成列,这些列是微小的计算机器,将信息传递到大脑的更高区域,在那里视觉图像逐渐形成。

通俗地说大脑结合低级特征,如基本形状、曲线,并从中构建更复杂的形状。深度卷积神经网络也类似。它首先识别低级特征,然后学习识别和组合这些特征,以学习更复杂的模式。这些不同级别的功能来自网络的不同层。

Feature Visualization of Convnet trained on ImageNet from [Zeiler & Fergus 2013]

我们不会进一步深入深度学习和反向传播如何工作的数学解释。跟随 cs231n 和本博客深入了解。让我们看看简单的深度卷积神经网络如何在交通标志数据集上执行。

Traffic Sign Images and Classification Probabilities

模型架构和超级参数

Tensorflow 用于实现交通标志分类的深度 conv 网。RELU 用于激活以引入非线性,不同百分比的退出用于避免不同阶段的过拟合。很难相信简单的深度网络能够在训练数据上达到高精度。以下是用于交通标志分类的架构。这里是链接到我的源代码。架构灵感来自 LeNet ,也被视为深度学习中的“Hello World”。

在探索了 LeNet 之后,我决定从简单的架构开始。想法是从简单开始,如果需要,增加更多的复杂性。架构与上面张贴的图表相同。将图像转换为灰度确实有助于获得更好的准确性。使用 【亚当】 优化器为 256 批量 训练模型 40 个历元 ,学习率最初设置为 0.0001,后来进一步增加到 0.001 以收敛到目标精度。我发现这个博客真的很有助于理解不同的梯度下降优化算法。这是我在 tensorflow 上面的第一个模型。下面是这个模型的一个小片段。

**def** deepnn_model(x,train=**True**):
    *# Arguments used for tf.truncated_normal, randomly defines variables for the weights and biases for each layer*
    x =   tf.nn.conv2d(x, layer1_weight, strides=[1, 1, 1, 1], padding='VALID')
    x =   tf.nn.bias_add(x, layer1_bias)
    x =   tf.nn.relu(x)
    x = tf.nn.max_pool(x,ksize=[1, 2, 2, 1],strides=[1, 2, 2, 1],padding='SAME')
    **if**(train):
        x = tf.nn.dropout(x, dropout1)

    x =   tf.nn.conv2d(x, layer2_weight, strides=[1, 1, 1, 1], padding='VALID')
    x =   tf.nn.bias_add(x, layer2_bias)
    x =   tf.nn.relu(x)
    conv2 = tf.nn.max_pool(x,ksize=[1, 2, 2, 1],strides=[1, 2, 2, 1],padding='SAME')
    **if**(train):
        conv2 = tf.nn.dropout(conv2, dropout2)

    fc0   = flatten(conv2)
    fc1 = tf.add(tf.matmul(fc0, flat_weight),bias_flat)
    fc1 = tf.nn.relu(fc1)
    **if**(train):
        fc1 = tf.nn.dropout(fc1, dropout3)

    fc1 = tf.add(tf.matmul(fc1, flat_weight2),bias_flat2)
    fc1 = tf.nn.relu(fc1)
    **if**(train):
        fc1 = tf.nn.dropout(fc1, dropout4)
    fc1 = tf.add(tf.matmul(fc1, flat_weight3),bias_flat3)
    logits = tf.nn.relu(fc1)

    **return** logits

结果

我的目标是从简单的架构开始,达到 90%的准确性,我惊讶地发现在第一次运行中,它接近 94%的准确性。进一步向模型中添加更多的层和复杂性,并辅以数据扩充,可以实现高达 98%的准确性。

讨论

深度学习真的令人印象深刻,它带来的结果看起来很有前途。从图像识别到自然语言处理,可能性是无穷无尽的。在了解了反向传播和卷积神经网络等相关概念后,我个人很难相信它完全是这篇文章中提到的黑箱。请随时提问,评论和建议。迫不及待地想在这个领域探索更多。

参考

Udacity 自动驾驶汽车工程师纳米学位。

G ithub 回购源代码。

CS231n 课程和 Andrej Karpathy 关于卷积神经网络的视频讲座

交通标志分类器项目

交通标志 d 数据来源

这首诗是什么时候写的?我的电脑可以告诉你

原文:https://towardsdatascience.com/identifying-when-poems-were-written-with-natural-language-processing-a40ff286bcd?source=collection_archive---------6-----------------------

用数据科学来理解诗歌中的动作

我最近的项目真的很令人兴奋。我热爱诗歌已经有一段时间了,所以我选择它作为我第一次涉足自然语言处理(NLP)的主要领域。

数据科学最酷的事情之一是它的普遍性和多功能性。你可以“数据科学”几乎任何东西。所以我用这个项目来拓展我的数据科学经验,并用一种非常酷的方式来阐述这个想法。

To be or not to be?

你也许能分辨出莎士比亚的诗和艾米莉·狄金森的作品。莎士比亚死于 1616 年,狄金森死于 1886 年,在这 270 年里,英语的使用方式发生了相当大的变化。但是狄金森和罗伯特·弗罗斯特之间的区别呢?罗伯特·弗罗斯特一直活到 1963 年。他们两人都用今天仍可理解的语言写作,没有“thous”和“thys”。在他们所处的时代,英语发生了多大的变化?毕竟,1886 年并不算太久。那是可口可乐被发明的那一年。

但也许你是诗歌专家。也许你对弗罗斯特的风格超级熟悉。如果是这样的话,你也许能分辨出其中的区别,但这远不像对莎士比亚那样容易。但是你,专家先生,如果我给你 1500 首诗,然后问你哪些是 18、19 和 20 世纪的呢?你现在有多自信?

对我们大多数人来说,这是相当困难的。风格和用词的差异并不明显。

这个项目旨在发现这些差异是否实际上是可以区分的。机器学习模型可以学习几个世纪之间的风格和单词选择的差异吗?如果有,准确度如何?剧透警告:可以。也很好。

获取数据:

我的第一个挑战是获得足够大的诗歌语料库来训练模型。起初,我期望这在互联网的某个地方很容易得到。我是说,互联网什么都有,对吧?不对。如果有,我没找到。

下一个可能性是网络抓取。有很多网站上有大量的诗歌。问题是他们中的一些人喝太多了。我指的是用户提交的内容。让任何一个汤姆、迪克或哈利出版他们杰作的网站。伟大的家伙,汤姆,迪克和哈利。但是为了这个项目,我没有要他们的大作。

经过一番搜索,我找到了一个合适的网站,但不幸的是,这个网站做得不是很好。一个完全不合逻辑的 URL 方案和一个过时的 HTML 结构使它成为一个挑战。但是我刮了。我想出了大约 30,000 首诗,并对其进行删减以创建我的最终数据集。

数据清理:

下一步是清洗和预处理。有几个步骤。

由于数据来自一个网站,我必须在不丢失任何内容的情况下删除所有的 HTML 标签。我还去掉了所有的标点符号和数字,把所有的字母都改成了小写。这很重要,因为计算机将大写和小写字母视为不同的字母,即使它们代表相同的字符。

在这个过程的最后,我留下了大约 4000 首诗,每一首都只是一滴原始文本,没有标点符号或大写字母。看起来像这样:

If you can figure out what ‘bughts’ are, you get ten points.

建模:

下一步是建模。我决定使用计数矢量器来分析这些诗歌。计数矢量器是 NLP 任务中常用的一种相对简单的方法。它基本上从整个语料库中的每个单词创建一个特征,然后为每首诗中的每个特征分配一个频率计数。它通常被称为“单词包”,因为它只是简单地统计每个单词在每次观察中的出现次数。还有更复杂的文本分析方法,但我选择这种方法主要是因为它简单。大多数自然语言处理任务集中在分析文本的内容,但是在这个任务中,我关注的是 T2 风格。

关于这一点,我在这个项目中做了另一个有趣的决定。NLP 项目中的一个标准步骤是去除“停用词”。停用词是像“the”这样的词,它们在所有文本中如此普遍,以至于不能提供任何见解。如果你看词频的话,几乎总是最常见的一个,但它并不能真正告诉我们什么。这个项目是不同的。因为我寻找的是风格,而不是内容,所以我可以从“the”中学到很多。也许 20 世纪的诗人比 18 世纪的诗人更经常使用特定的连词。所以我决定留下停用词。这被证明是一个好的决定,因为去掉它们会损害模型的性能。

预处理之后是模型构建阶段。scikit-learn 和 nltk 中有许多现成的建模技术,适用于文本分类项目。在尝试了许多方法并试验了它们的不同参数后,我选定了一个多项式朴素贝叶斯分类器。

朴素贝叶斯模型之所以被称为朴素贝叶斯模型,是因为它们假设所有特征都是独立的,即使这并不完全正确。通过这样做,他们可以查看每个特征属于每个类的概率。然后,他们将每个观察值分配给其组合特征具有最高概率的类。尽管有天真的假设,但它们通常在文本数据上表现得非常好。

朴素贝叶斯模型获得了 82%的总准确率。不同班级的分数有一个有趣的分类。下面是一个混乱矩阵,显示了正确和错误分类的诗歌。

It’s appropriately called a confusion matrix because it can be confusing. A more detailed description below.

看这个矩阵,看起来 18 世纪和其他阶级最有区别。该模型正确预测了 91%的 18 世纪诗歌。有趣的是,虽然它确实将一些 18 世纪的诗歌误归类为 19 世纪和 20 世纪,但它没有将任何 20 世纪的诗歌误归类为属于 18 世纪。

这个模型在 19 世纪和 20 世纪遇到了更多的麻烦。你可以看到它只正确识别了 72%的 19 世纪诗歌,和 81%的 20 世纪诗歌。夹在另外两个阶级中间的 19 世纪,给这一模式造成了最大的混乱。时间上更远的几个世纪比中间的几个世纪更容易区分,这肯定是有道理的。

下面是一些最有可能属于每个世纪的特征。许多单词可能会出现在不止一个类中,这似乎有悖常理。但它确实有意义,因为为了识别类别,模型结合了这首诗中所有单词的概率。但是每个单词对于每个类别都有一个可能性。通过观察某些单词在不同类别中的概率差异,你仍然可以获得一些有趣的见解。当停用词被实际取出时,下面的单词属于每一类的概率最高。即使我把它们留在我的最具预测性的模型中,我还是把它们拿出来放在一个模型中,以便对特定的单词有所了解。看一看:

Looks like God went out of style!

如果你注意到其他有趣的东西,请在下面留言。

后续步骤:

这个项目让我着迷,我会继续探索和发展它。

下一步是动态主题建模,这是一种提取数据中正在谈论的主题,并观察它们如何随时间变化的方法。请继续关注这方面的新闻。

在那之后,我计划收集更多的数据,创建额外的功能,并在分类上做出一些深思熟虑的决定。

Jupyter 笔记本和原始诗歌数据可以在我的 Github 这里找到。如果你对这些数据有任何创造性的使用,我很乐意听到并贡献出来。

有问题吗?评论?喜欢吗?讨厌?在下面留言。

意识形态 Vs 现实?特朗普总统会见约旦国王后的讲话

原文:https://towardsdatascience.com/ideology-vs-reality-insights-from-the-remarks-by-president-trump-after-meeting-the-king-of-jordan-85bad28e7a71?source=collection_archive---------7-----------------------

本周中期,特朗普总统在白宫会见约旦国王的消息铺天盖地。这通常表明,正如媒体广泛指出的那样,在处理中东问题时,国家之间的联盟越来越重要。

这篇文章的目的是分享一种更深层次的政治洞察力,这种洞察力可以通过应用于政治演讲文稿的认知分析技术获得。总统讲话的会议记录可以在白宫发布的公共领域找到。

该分析和方法基于我在认知和社会心理学领域的研究,包括从公开可用的数据中研究数百种认知取向,以及我在非结构化政治数据上应用高级分析工具和技术的经验。

认知文本分析

在对总统讲话的分析中,有三个重要的基于心理取向的洞察力维度,它们可能会阐明这种会议的重要性,如下所示。,

  1. 政治信任:观察到一种积极的倾向,表明通过伙伴关系和合作与约旦建立了更密切的关系。
  2. 对外关系:态度上取向是有可能定位在左边(左翼政治支持社会平衡方面和 平均主义 )。此外,在从属关系的驱动下,对外关系的倾向于和平(而非战争)。我们在合作中的角色可能是调停者/整合者,而不是影响者或积极独立的角色扮演者(基于参考文献。数据来自赫尔曼 1987 年 b)

3.订婚的方法?(对外交易):这种定位是关于一个人如何在外部世界交易/参与,并表明特朗普可能会谨慎(相对于雄心勃勃),但在处理合作目标中的实际问题时,他的方法是自信和正式的。

动机分析(回答为什么?)

人类的动机表现为寻求改变的愿望或挫折,关注自我、物质或社会/人际世界。在我对总统讲话的分析中发现的主要动机如下。

  1. 成就 (76%) —这种动机情绪有寻求结果的愿望(获得胜利),关注物质或任务导向的世界(而不是关注自我或社会世界)
  2. ****精通(70%)——这是另一个动机,人们渴望或寻求的变化变得不同寻常(以精通),以便川普能够更好地同化和处理中东局势(通过约旦合作)。掌握动机关注自我(与物质或社会世界相对的内在自我)
  3. ****归属感(68%)——这种动机表示与对未来的期望相关的愿望,关注社会或人际关系世界。这就像是在说,在实现目标的过程中,我们将是值得信赖和可靠的(真诚的)伙伴。这也暗示了约旦对美国的支持。
  4. 养成 (52%) —有与体验关怀和支持相关的愿望。(养育和被养育的概念)。这个动机的重点在社交/人际世界。我相信在给定的环境下,这更多的是关于培养约旦和约旦在中东目标上对美国的回报。这一动机也表明了美国邀请约旦国王访问白宫的重要性。

来自文本分析的线索

  1. 上下文发现

为了从总统的会议讲话中分析上下文,我把讲话记录分成三个部分,即。a)基于过去 b)现在和 c)将来时态。因为我很想知道这次会议可能会产生什么,所以我把分析的重点放在了文本中与未来相关的线索上,我的发现列举如下。

摘录 演讲正文 传达将来时方面

**一个非常特别的地方,我可以告诉你。我已经很了解它了。就此而言,美国与我们在全球的盟友一起谴责这一恐怖袭击和所有其他恐怖袭击。
陛下,约旦人素以热情好客著称,我们将尽最大努力成为同样热情的东道主。
然而,我不得不说,他们也因他们的战斗能力而闻名。通过所有这些,美国将约旦视为一个宝贵的伙伴,一个文明价值观的倡导者,以及稳定和希望的源泉。
我坚定地致力于维护我们牢固的关系——我会的——并加强美国对约旦的长期支持。
通过这一切,美国将约旦视为一个重要的合作伙伴,一个文明价值观的倡导者,以及稳定和希望的源泉。我坚定地致力于维护我们牢固的关系——我将这样做——并加强美国对约旦的长期支持。我可以告诉你,在我们国家,你确实拥有巨大的支持。约旦军人在这场与文明敌人的战斗中做出了巨大牺牲,我要感谢他们所有人,感谢他们令人难以置信的勇气。国王是呼吁一劳永逸地击败 ISIS 的领导者。

上下文发现—动作词(将来时文本)

上面引用的文本中的单词及其含义暗示了一种谨慎、合作和防御的姿态,而不是任何进攻的姿态。积极词汇与消极词汇的比率表明了一种预期的/积极的合作。

上下文发现—唯一&重要术语 术语—词语和短语
这些是从上述文本中提取的重要关键词。如果你看到,无论是意义,然后积极的比率与消极的话是倾向于积极的方面有关方面的合作和联盟与约旦。文本“约旦服务成员”是一个有趣和独特的观察,因为合作可能与军事方面有关。(编辑注:我认为 AMN 在这篇文章发表两天后发布的这条 特别新闻与这意味着什么有关,并暗示了新兴合作的性质)

Unique & Important terms from the speech (with future orientation)

2。语言风格&语气分析(将来时文本)

a.人们发现这种语言风格反映了自信和希望。
b .情绪基调表明存在喜悦(在 0-100%的范围内为 56 ),表示没有任何重大负面情绪的伙伴关系方面。

在上下文中,术语“恐怖袭击”与恐惧情绪有关,而恐惧情绪与战斗或逃跑反应有关。因此,很明显,在恶劣天气下,任何应对措施都可能以战斗(军国主义)姿态出现。(打架)。“谴责”这个词与愤怒的情绪有关。(对情况做出反应)。根据 CMU 的一项研究,尤其是愤怒的情绪可能会让人愿意冒更大的风险。

总结

总体分析主要指向“关系”因素,这意味着美国与约旦的政治伙伴关系的持续和日益增长的重要性。这种关系如何体现和出现将是一件有趣的事情,这取决于中东正在发生的变化。

虽然这种分析具有预测性,但考虑到问题的复杂性、人类思维和文本数据的较小/有限大小,最好将分析结果视为可能有助于准备工作的线索,而不是真正预测确定性的东西。

免责声明:
这里提到的观点是我自己的。
本文使用的数据来自公共领域的可用信息。但对其准确性、完整性、及时性或正确性不做任何明示或暗示的陈述或保证。我不对任何错误或不准确负责,不管是什么原因造成的。(读者)。

如果数据是新的黑金,那么医疗数据就是新的黄金!

原文:https://towardsdatascience.com/if-data-is-the-new-black-gold-then-medical-data-is-the-new-gold-f2459df2d888?source=collection_archive---------1-----------------------

Paper based Medical Records

作为一名热情的计算科学家和未来学家,我监视、跟踪和预测即将到来的、正在快速融合的重大趋势。根据学术界和工业界专家的说法,我们已经进入了大数据时代,并正在向人工智能(AI)时代过渡,人工智能有可能改变所有主要的行业和部门。这尤其与搜索引擎(谷歌)、电子商务(亚马逊、Flipkart)、社交网络(脸书、LinkedIn)等领域相关。

我们在brain pan Innovations,正在大力分析发展中国家的医疗保健领域。我们倾向于顺应潮流,认为我们正处于一个‘少数据、旧数据、无数据’的时代,因为作为一个社会,我们仍然停留在一项 5000 年的技术上,那就是纸。

令我们困惑的是,大多数印度医生都在“新金矿”的顶端,但并不完全了解他们所拥有的资产的潜力和价值。根据我们在二线城市(HRA 分类中的 Y 级)的调查,私人诊所每天的患者数量从 10 到 25 不等,医院从 50 到 200 不等,每年产生几千个医疗数据记录。但是,这些数据存在于纸质处方和医疗报告中,而不是电子形式,即 EHR。

在我国,电子医疗数据的价值被惊人地低估和利用不足。从作为药物开发项目的催化剂到定制的私人护理,它们的效用是无穷的。例如,理解 EHR 系统的数千个数据点中保存的医疗数据的结构可以快速找到相关的模式,从而帮助我们揭示定义治疗方案的最有利方式,同时确定哪些药物、测试和其他程序有助于获得最佳结果。以下是一些支持事实,供参考。

在 2011 年,赛诺菲安万特成功地证明了 EHR 使许多二型糖尿病和心脏病患者得到了改善。这是一个为期 12 个月的项目,在两个试点跟踪 119 名患者,为期 6 个月。

2016 年,辉瑞使用匿名的 EHR 数据开发了 Xalkori 作为第一种专门针对 ALK 基因突变的肺癌患者的美国 FDA 药物。

为了能够改变人们的生活,解决未满足的患者需求,医疗保健公司需要访问健康数据,以便实施机器学习算法等人工智能技术来改善他们的医疗诊断。

在人口超过 12.5 亿的印度,非传染性疾病呈上升趋势,心血管疾病(24%)、慢性呼吸道疾病(11%)、癌症(6%)和糖尿病(2%)是导致死亡的主要原因。

问我们所有人一个问题——为什么印度的医生不利用这个巨大的数据库来加速人工智能、机器学习或更准确地说是计算机辅助诊断(CAD)?如果有一种算法可以分析胸部 CT,检测肺部的肺气肿区域,或者在有肺动脉高压迹象时发出警报,岂不是更好?从妇科角度来看,在心脏病、中风的急性病例中的其他可能用途,或量化高危妊娠、纤维瘤将是突破性的。

我们的初创公司brain pan Innovations(隐形模式)正在不断开发和改进数据驱动预防性 EHR 平台’医生日记,该平台旨在通过弥合生命科学和计算之间的差距来应对所有这些科学挑战。

如果机器学习不能帮你省钱,那你就做错了

原文:https://towardsdatascience.com/if-machine-learning-isnt-saving-you-money-you-re-doing-it-wrong-902053c3c898?source=collection_archive---------6-----------------------

注来自《走向数据科学》的编辑: 虽然我们允许独立作者根据我们的 规则和指导方针 发表文章,但我们不认可每个作者的贡献。你不应该在没有寻求专业建议的情况下依赖一个作者的作品。详见我们的 读者术语

我们都同意,机器学习是新的热点。或许你读过的每一个标题都很吸引人的故事,比如“ 7 种将主导 2018 年的技术趋势”,都会以这样或那样的方式提到机器学习或人工智能。

事实是,机器学习是伟大的,但如果你没有以正确的方式进行,它真的很容易很快被剥夺。我从亲身经历中了解到这一点。

Photo by NeONBRAND on Unsplash

以一个问题开始

首先,也可能是最重要的,机器学习仍然只是触及了可能的表面。令人沮丧的是,你绝对不会听到有人试图向你出售机器学习能力或服务。即使是你雇佣的热门数据科学家和 ML 工程师(可以理解)可能也不会立即鹦鹉学舌当前技术水平的局限性。

我无法告诉你我从大大小小的企业那里听到了多少根本不可能的使用案例和请求。我可能听到过同样多的请求,这些请求实际上并不需要机器学习来完成。

把机器学习扔给任何老问题都不会奏效。你最终会浪费很多时间和金钱。

相反,仔细考虑你试图解决的问题。你能把问题变得越简单,机器学习就越有可能奏效。不要想象你认为只有计算机会擅长的问题。先看看手动解决这个问题需要多少努力,然后评估计算机系统是否可以独立完成这项任务。

训练就是一切

从零开始学习机器仍然非常非常困难。我认为最难的部分是训练。当我试图训练一个机器学习模型来检测电影和视频中的吸烟时,我学到了这一点。我最初认为,我只需要向它展示数百张香烟的图片,然后它就会知道香烟的样子。

失败了。

然后我发现我需要给它两个标签;吸烟不吸烟。所以我找了一堆随机的不是香烟的东西的图片,然后把它们放了进去。

那也失败了。

然后我尝试了一种不同的方法。我决定从人们吸烟的电影中截取定格画面。因为这是模型运行的环境,我想我有更好的机会让它工作。为了我的不吸烟标签,我使用了不同电影中对话场景的定格画面。

差点就成功了。问题是,事实证明,我所做的是训练模型检测我用来训练的电影。所以它本质上是一个是不是这 5 部电影中的一部模型。

One of my favorite scenes from Silicon Valley

我在这上面花的时间和精力都白费了。我也从其他顾客那里听到过类似的趣闻。他们雇佣了 ML 工程师和专家来建造定制模型,这花了一年的时间,结果却是一些不太好的东西。

这个问题的解决方案与上面的部分相同。首先考虑问题,并确保一个好的训练集是你可以得到的。

我最终使用机器盒中的标签盒解决了这个问题,但我仍然必须考虑我的训练数据,并决定边缘情况发生的可能性有多大。

不要花的钱比你存的多

这似乎是显而易见的,但值得重复。谷歌、微软、IBM 等公司有一些非常棒的机器学习 API。但在实践中,这些工具的成本会迅速增加。我曾见过有人仅仅为了一个月的开发工作就得到 45,000 美元的账单。我采访过的一家主要广播公司告诉我,通过这些云 API 运行他的所有内容比付钱给高中生手动标记所有内容要昂贵得多。

这是一个巨大的投资回报率问题。(这也是我加入机器盒子的原因,因为我们解决了这个问题,不管使用与否,所有东西都要支付统一的订阅费)。在 GPU 和其他地方训练机器学习模型的成本已经下降,但仍然需要一些成本。在许多情况下,有些东西可能比它的价值更高。

你从特定的机器学习模型中提取的价值将取决于你的用例。确保它经过深思熟虑和验证。

不要期待奇迹

Alexa 有没有理解过你说的话?真的很让人沮丧吗?我仍然看到这些语音助手有很多准确性问题。语音识别非常非常难实现。在机器学习中,当我们谈到一个特定的模型时,我们经常会引用一个百分比的准确率。如果准确率在 80%以上,我们会觉得我们得到了有用的东西。开车到 90%以上通常只是稍微调整一下。但我们真正做的是讨论我们的模型如何从我们搁置的训练数据子集预测一些东西,我们称之为验证集。当您的模型与不在训练集中的东西运行时,可能会出现问题。在很多情况下,不可能考虑到所有可能的边缘情况。当 Alexa 被激活时,它处于数百万种不同的听觉情况中。背景噪音、口音、回声和许多其他东西会干扰语音识别系统。

A lot of false positives from an implementation of OpenCV face recognition: https://goo.gl/m9jpwR

当机器学习模型错过一些东西时,很容易认为这是一个错误,或者可能是模型中的缺陷。非常重要的是,你要明白事实并非如此。误报和漏报是机器学习的一部分。它有时也会犯错,就像我们一样。每个企业都必须为机器学习中偶尔出现的误报和漏报做好准备。这就是生活的现实。作为企业执行任务的人类总是会犯错误。

我们在机器盒子帮助缓解这些问题的方法之一是让我们的盒子可教。也就是说,您可以简单地对模型进行修改或添加,而不需要进行任何类型的再培训。就像人类一样,机器学习模型需要随着时间的推移不断改进,以考虑所有可能的边缘情况。

但是你的业务和对机器学习的理解需要考虑偶尔的误报和漏报。仅仅因为你的系统漏掉了一些文本中的关键词,或者图片中的一张脸,并不意味着整个系统应该崩溃。如果你曾经在电视上看过隐藏式字幕,你就会知道人类总是会犯错。是否意味着隐藏式字幕没有用?当然不是。它仍然提供重要的服务。你的机器学习实现也应该如此。

我该不该用?

尽管如此,我想重申,机器学习是一种奇妙、强大的计算类型,可以给大大小小的企业带来很多价值。我已经看到了很多非常好的机器学习用例,用机器盒和其他工具廉价而有效地解决了这些问题。从提高安全性和合规性到改进搜索和发现,无所不包。使用得当,它可以节省人们大量的时间。它还可以帮助创造新的收入来源,识别威胁,找到丢失的数据,等等。

所有这些成功的实现都是如此,因为它们都是定义明确的问题,可以通过当前或以前最先进的机器学习来解决。投入的精力没有超过创造的价值。

如果你不确定你的用例是否能被机器学习解决,你能做的最好的事情就是实验。但是很明显,以一种不会破产的方式。你可以用机器盒或者一些云工具轻松做到这一点。

在你开始一个耗时的数据科学项目之前,尽你所能评估这个问题,并确保它是用例最简单的迭代。

什么是机器盒子?

Machine Box 将最先进的机器学习功能放入 Docker 容器中,以便像您这样的开发人员可以轻松整合自然语言处理、面部检测、对象识别等功能。到您自己的应用程序中。

这些盒子是为扩展而建造的,所以当你的应用真正起飞时,只需水平地添加更多的盒子,直到无限甚至更远。哦,它比任何云服务都要便宜得多(而且可能更好)……而且你的数据不会离开你的基础设施

有戏让我们知道你的想法。

如果出租车旅行是萤火虫:13 亿次纽约出租车旅行

原文:https://towardsdatascience.com/if-taxi-trips-were-fireflies-1-3-billion-nyc-taxi-trips-plotted-b34e89f96cfa?source=collection_archive---------1-----------------------

NYC Metro Area Taxi Dropoffs, 1.3 Billion points plotted. Click for full resolution

纽约市出租车和豪华轿车委员会(TLC)公开发布了一个从 2009 年 1 月到 2016 年 6 月的出租车出行数据集,其中包含起点和终点的 GPS 坐标。最初,Chris Whong 向 TLC 发送了一个 FOIA 请求,让他们发布数据,并制作了一个著名的可视化图像,纽约市出租车:生活中的一天Mark Litwintschik 使用这个 400GB 大小的数据集对各种关系数据库和大数据技术进行了基准测试。值得注意的是, Todd W. Schneider 制作了一些非常好的数据集摘要,其中一些与我在这里展示的作品相似。实际上,我是在这篇文章写出来之后才知道 Todd 在这个话题上的工作的,所以尽管有一些重叠,这篇文章和其中的图片都是原创的。

我从 TLC 网站下载了数据文件,并且使用 Python、Dask 和 Spark(非常 痛苦地)生成了一个清晰的 Parquet 格式的数据集,我在这篇文章的最后将它提供给 AWS 用户。

所以我很好奇,出租车在哪里接客,或者更准确地说,出租车接客地点的分布是什么样的?由于有 13 亿辆出租车,以不忽略细节的方式绘制分布图非常具有挑战性。由于过度绘制,散点图是无用的,2D 直方图是一种核密度估计形式,必然会模糊或像素化许多细节。此外,对于完整的数据集,仅拾取位置就有 21GB,这比我的 16GB 笔记本电脑的内存还多。核心外的工具可以很容易地解决这个技术问题(子采样比这更容易),但是视觉问题呢?人眼无法在一个情节中吸收 21GB 的信息。

这个问题的解决方案来自一个叫做 Datashader 的有趣的库。它会以您的显示器(或指定的画布)的分辨率动态生成 2D 直方图。显示器上的每个像素对应于数据中的特定直方图边界。该库为每个像素计算落入这些边界内的数据点的数量,该数量用于给像素的亮度着色。利用 Dask,直方图的创建可以扩展到万亿字节的数据,并分布在整个集群中。利用散景,最终的情节可以缩放和平移。使用来自高动态范围摄影的技术,强度范围被映射,使得最大动态对比度出现在任何变焦水平和任何给定的视窗中。

出租车接送位置

这是曼哈顿上空出租车上客点(13 亿个点)的地图,使用 Viridis 感知均匀色图绘制。

NYC Taxi pickups map for Manhattan Click for full resolution

我注意到的第一件事是我能多么清楚地看到街道图案。在布鲁克林和皇后区的部分地区,街道格局非常鲜明。在曼哈顿,这种模式是“模糊的”,尤其是在曼哈顿南端附近和中央公园以南的中城。根据全球定位系统的坐标,有相当多的货车掉在哈德逊河或东河,也有相当多的货车掉在中央公园没有道路的地方。显然,并没有很多出租车从曼哈顿周围的河流出发,但这个图显示的是 GPS 误差有多重要。这种模糊性来自于高层建筑,这使得很难获得良好的 GPS 定位,而且建筑物越高,街道看起来就越模糊。更广泛地说,中央公园以南的市中心区非常明亮,表明许多出租车旅行都是从那里开始的。

Taxi pickups map for NYC Metro Area Click for full resolution

第二个图像也是出租车皮卡,但在一个更广泛的规模。缩小后,曼哈顿的大部分地区像灯塔一样亮着,表明曼哈顿的皮卡数量远远超过周围地区。但是机场,特别是 JFK 和拉瓜迪亚机场,也亮起来了,显示出几乎和市中心区一样的视觉强度(从那里开始的单位面积的旅行次数)。

出租车下车地点

现在让我们使用地狱色图来检查衰减位置。

NYC Taxi dropoffs map for Manhattan Click for full resolution

乍一看,交货地点很像曼哈顿的交货地点。同样的地区,中央公园以南的中城和曼哈顿的南端展示了最明亮(也是最模糊)的街道。

Taxi dropoffs map for NYC Metro Area Click for full resolution

缩小到更广阔的都会区,布鲁克林和皇后区的街道更清晰、更明亮,这表明外围区的落客比皮卡多得多,也表明这些地区的 GPS 误差往往更低,这可能是因为高层建筑更少。事实上,在一些地方,它看起来足够好,可以用作街道地图,表明布鲁克林和皇后区的出租车乘客分布相对均匀。这与皮卡地图截然不同,表明在外区有相对较少的皮卡,但有很多落客。许多人从曼哈顿乘出租车去郊区,但很少有人从郊区乘出租车去曼哈顿。

出租车上下车地点

最后两个图逐个像素地比较了拾取和衰减。在拾取高于衰减的地方,像素用绿色和黄色色图着色。在衰减高于拾取的地方,像素用紫色和橙色的地狱色图着色。

Pickups (Yellow-Green) and Dropoffs (Orange) for Manhattan Click for full resolution

在曼哈顿,街道(南北向的街道)两旁都是绿色,这表明接送的人比下车的人多。十字路口(东-西)是橙色的,表示更多的下降。实际上,如果我想搭出租车,走到最近的大街上搭一辆可能更容易。

Pickups (Yellow-Green) and Dropoffs (Orange) for NYC Metro Area Click for full resolution

缩小到更广阔的区域,布鲁克林和皇后区的几条主要街道是绿色的,表明这些街道上有大量的皮卡,而其他街道仍然是橙色的,显示从曼哈顿开始的旅行有所减少。在 JFK 和拉瓜迪亚机场,机场内的上客区和下客区被突出显示,部分区域用绿色阴影表示(上客区),其他区域用橙色阴影表示(下客区)。

GPS 呢?

使用 Datashader 和 Bokeh 绘制出租车上客和下客位置表明,有时 GPS 坐标数据相当不准确,表明上客和下客位置在东河或哈德逊河。我们从曼哈顿的接送地图上看到,GPS 受到高楼的强烈影响。特别是下降显示了一个令人惊讶的均匀分布在外围行政区,每条道路,每座桥梁都被突出。我觉得这很令人惊讶,因为我不希望在桥上或其他不鼓励停车让乘客下车的地方出现很多下车现象,比如通往 JFK 的范威克高速公路。然而,这样的桥梁和道路被突出显示,这让我想知道这是不是 GPS 的一个怪癖?这都是我的推测,但是如果 GPS 设备只是以固定的时间间隔更新,比如每两分钟,或者只要它可以获得位置锁定,会怎么样呢?在这种情况下,出租车行程将在一个合理的位置结束,但数据将被记录为行程在沿途某处结束。这可以解释为什么大量的接送发生在看似不可能的地点。

鉴于数据集可以追溯到 2009 年,智能手机中的 GPS 接收器从那时起已经走过了很长的路,我非常好奇是否有可能在出租车数据集中看到 GPS 精度的提高。作为 GPS 误差的一个替代,我检查了在物理上不可能的位置上的上下车地点的数量,例如在哈德逊河和东河的中间。然后我把这种不可能的旅行的比例标绘成总旅行次数的比率。鉴于优步和 Lyft 等打车服务和拼车服务的增长,费率调整是必要的。

Rate of Pickups and Dropoffs outside of the Taxi Zones, but within the local NYC area

果不其然,自 2009 年以来,不可能的地点的接送率下降了 4 到 5 倍。我不清楚是什么导致了 2009-2012 年的年度周期,错误率在夏季月份增加。自 2011 年以来,错误率大幅下降,这可能是由于整个出租车车队的出租车计价器发生了变化,或者 GPS 报告方式发生了变化。掉线率高于接站率的事实表明,我的理论可能有一些支持,即 GPS 设备只在固定的时间间隔更新,或者每当它们可以锁定位置时更新。

值得一提的是,0.5% — 0.1%的误差率不一定代表特定位置的实际 GPS 误差。例如,中央公园以南中城的模糊街道表明,那里的位置误差远高于 0.5%。此外,全球定位系统的位置可能是错误的,在某种程度上不是把它放在水面上,而是放在不正确的陆地位置上,这不会被我的 GPS 误差的原始代理检测到。

摘要

我获取、清理并绘制了纽约出租车数据集。我制作了一些有趣的接送地点的可视化图像,显示大多数接送发生在曼哈顿、JFK 和拉瓜迪亚机场,但是从曼哈顿到布鲁克林和皇后区有大量的出租车行程。很少有旅行是从郊区开始,在曼哈顿结束的。我逐点比较了出租车的上客和下客情况,显示出曼哈顿的大街上出租车上客的数量比十字路口多,十字路口上客的数量比十字路口多。

我还展示了 GPS 位置的准确性如何有问题。在市中心区,这可以通过“模糊”的街道和相当数量的点看到,这些点显示了在像哈德逊或东河这样不可能的位置的皮卡。在不方便让乘客下车的地方,比如范怀克高速公路,也有大量的上下车点,这表明上下车点地图上对这些街道的清晰定义是 GPS 设备不经常更新的一个怪癖。对恰好在水中的上下车地点的数量进行分析显示,自 2009 年以来,4 5X 的数量显著下降,这可能要归功于出租车计价器中 GPS 技术的改进。尽管如此,GPS 定位的误差表明应该有所保留。

在接下来的几周里,我将发布更多关于这个数据集的数据分析。

数据可用性

我把代码放在我的 NYC-transport github 库中。你可以在 GithubNBViewer 上查看用于制作这篇文章情节的笔记本。

我已经将亚马逊 S3 上包含出租车数据和优步数据(不是本文的主题)的原始拼花格式数据帧放在一个请求者付费桶中。如果您在美国东部地区使用正确配置的s3cmd启动 EC2 实例,您可以如下复制文件。一定要在美国东部地区,否则你可能会招致巨额带宽费用

s3cmd sync --requester-pays s3://transit-project/parquet/all_trips_spark.parquet .

数据大约为 33GB,采用快速压缩的柱状拼花格式。如果用 Dask 读取,需要使用 PyArrow 后端。

如果您想联系我,请通过 LinkedIn 联系我。

如果你不能衡量它,你就不能改善它!!!

原文:https://towardsdatascience.com/if-you-cant-measure-it-you-can-t-improve-it-5c059014faad?source=collection_archive---------9-----------------------

如何用 python 中的 LightFM 为一个电商搭建一个可扩展的推荐系统?

photo credit: pixabay

在过去的几年里,网上购物发生了很大的变化。像亚马逊这样的在线商店,在更个人化的层面上对待他们的顾客。他们根据您的网上购物活动(查看商品、将商品添加到购物车并最终购买)了解您对某些商品的兴趣。例如,你在亚马逊上搜索一件商品,然后点击一些搜索结果。下次你访问亚马逊时,你可以看到有一个特定的部分,根据你上次搜索的内容为你推荐类似的产品。故事并未就此结束,随着你与在线商店的互动越来越多,你会收到更多个性化的推荐,包括“购买该商品的顾客也购买了”,它会向你显示经常一起购买的商品列表。此外,一些商店发送促销电子邮件,提供针对更有可能购买这些产品的客户的产品。

推荐系统是机器学习最常用的应用之一。由于这里的目标是关注如何使用 LightFM 软件包构建推荐系统,并提供清晰的度量标准来衡量模型性能,所以我将只简要提及不同类型的推荐系统。关于推荐系统的更多细节,我建议观看 Siraj Raval 的这个简短的视频,并查看 Chhavi Aluja 的这篇文章。有三种类型的推荐系统:

  • 基于内容
  • 协作过滤(基于项目、基于用户和基于模型)
  • 混合方法(将基于内容的方法添加到协同过滤中)

我最初的目标是建立一个混合模型,因为它可以将基于内容的推荐整合到协同过滤中,并且能够解决纯协同过滤推荐系统的冷启动问题。然而,没有多少公开可用的好数据集既有项目或用户的元数据,又有评级交互。所以我决定首先研究一个协同过滤模型,理解推荐系统的不同方面,在我的下一篇文章中,我将建立一个混合模型。

方法:

为什么选择 LightFM???

在研究推荐系统时,我遇到了许多相关的伟大项目,但是缺少一件事是缺乏一个明确的指标来评估模型的性能。我相信,如果你不能通过提供清晰的指标来评估你的模型的性能,你可能很难让你的读者相信这个模型(推荐系统)工作得足够好。因此,我选择了 LightFM ,因为它提供了清晰的指标,如 AUC 得分和 Precision@K,可以帮助评估训练模型的性能。这对于构建更好的模型和实现更高的准确性非常有用。

根据我们要解决的用例或问题类型,在 Precision@K 和 AUC score 之间做出选择可能会很棘手。在这种情况下,我们将使用 AUC 评分,因为它衡量整体排名的质量,并可以解释为随机选择的正面项目排名高于随机选择的负面项目的概率。

“LightFM 是许多流行的隐式和显式反馈推荐算法的 Python 实现,包括 BPR 和 WARP 排名损失的高效实现。它易于使用,快速(通过多线程模型估计),并产生高质量的结果。” LightFm 文档。

photo credit:pixabay

数据

对于这个项目,我们将使用图书交叉数据集实现一个基于矩阵分解方法的纯协作过滤模型。我们将利用 Chhavi Aluja 在她关于 towardsdatascience.com 的帖子中对这个数据集进行的惊人的数据清理和预处理。让我们来看看数据:

import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
from datetime import datetime, timedelta
from sklearn import preprocessing
from lightfm import LightFM
from scipy.sparse import csr_matrix 
from scipy.sparse import coo_matrix 
from sklearn.metrics import roc_auc_score
import time
from lightfm.evaluation import auc_score
import pickle
import re
import seaborn as snsbooks = pd.read_csv('BX-Books.csv', sep=';', error_bad_lines=False, encoding="latin-1")
books.columns = ['ISBN', 'bookTitle', 'bookAuthor', 'yearOfPublication', 'publisher', 'imageUrlS', 'imageUrlM', 'imageUrlL']
users = pd.read_csv('BX-Users.csv', sep=';', error_bad_lines=False, encoding="latin-1")
users.columns = ['userID', 'Location', 'Age']
ratings = pd.read_csv('BX-Book-Ratings.csv', sep=';', error_bad_lines=False, encoding="latin-1")
ratings.columns = ['userID', 'ISBN', 'bookRating']

size of each dataframe

books.drop(['imageUrlS', 'imageUrlM', 'imageUrlL'],axis=1,inplace=True)
books.loc[books.ISBN == '0789466953','yearOfPublication'] = 2000
books.loc[books.ISBN == '0789466953','bookAuthor'] = "James Buckley"
books.loc[books.ISBN == '0789466953','publisher'] = "DK Publishing Inc"
books.loc[books.ISBN == '0789466953','bookTitle'] = "DK Readers: Creating the X-Men, How Comic Books Come to Life (Level 4: Proficient Readers)"
books.loc[books.ISBN == '078946697X','yearOfPublication'] = 2000
books.loc[books.ISBN == '078946697X','bookAuthor'] = "Michael Teitelbaum"
books.loc[books.ISBN == '078946697X','publisher'] = "DK Publishing Inc"
books.loc[books.ISBN == '078946697X','bookTitle'] = "DK Readers: Creating the X-Men, How It All Began (Level 4: Proficient Readers)"
books.loc[books.ISBN == '2070426769','yearOfPublication'] = 2003
books.loc[books.ISBN == '2070426769','bookAuthor'] = "Jean-Marie Gustave Le Cl�©zio"
books.loc[books.ISBN == '2070426769','publisher'] = "Gallimard"
books.loc[books.ISBN == '2070426769','bookTitle'] = "Peuple du ciel, suivi de 'Les Bergers"
books.yearOfPublication=pd.to_numeric(books.yearOfPublication, errors='coerce')
books.loc[(books.yearOfPublication > 2006) | (books.yearOfPublication == 0),'yearOfPublication'] = np.NAN
books.yearOfPublication.fillna(round(books.yearOfPublication.mean()), inplace=True)
books.loc[(books.ISBN == '193169656X'),'publisher'] = 'other'
books.loc[(books.ISBN == '1931696993'),'publisher'] = 'other'
users.loc[(users.Age > 90) | (users.Age < 5), 'Age'] = np.nan
users.Age = users.Age.fillna(users.Age.mean())
users.Age = users.Age.astype(np.int32)

上面的代码块是常规的数据清理,以确保在将数据用于模型输入之前,数据的格式是正确的。此外,我们需要确保 ratings 数据框架中的所有行都代表来自用户和图书数据框架的数据。接下来,评级必须只包括有效的评级分数(1-10),我们应该去掉评级值为零的所有行。

ratings_new = ratings[ratings.ISBN.isin(books.ISBN)]
ratings = ratings[ratings.userID.isin(users.userID)]
ratings_explicit = ratings_new[ratings_new.bookRating != 0]

这是评分值的分布:

为了完成我们的数据预处理,我们可以做的最后一件事是为已经对图书进行评级的用户数量以及已经被用户评级的图书数量分配一个阈值。换句话说,我们必须有一个用户和书籍的最低评级计数。我认为,如果只有至少评价了 20 本书的用户和至少被 20 个用户评价过的书就好了。

counts1 = ratings_explicit['userID'].value_counts()
ratings_explicit = ratings_explicit[ratings_explicit['userID'].isin(counts1[counts1 >= 20].index)]
counts = ratings_explicit['bookRating'].value_counts()
ratings_explicit = ratings_explicit[ratings_explicit['bookRating'].isin(counts[counts >= 20].index)]**ratings_explicit.shape
(217729, 3)**

训练我们的模型:

在这一步,我们将训练我们的模型。但这个问题不一样。在协作过滤模型中,我们基于用户-项目交互来寻找表征每个项目(书)的潜在特征,并且我们寻找每个用户与所发现的每个潜在特征的相似性。这个过程是通过矩阵分解完成的。首先,我们需要将数据(ratings_explicit)分成训练集和测试集。这就是事情变得棘手的地方。很明显,纯粹的协同过滤方法不能解决冷启动问题。因此,必须进行训练和测试拆分,以便测试集中的用户或书籍的实例必须具有训练集中的剩余实例:

**def informed_train_test(rating_df, train_ratio):**
    split_cut = np.int(np.round(rating_df.shape[0] * train_ratio))
    train_df = rating_df.iloc[0:split_cut]
    test_df = rating_df.iloc[split_cut::]
    test_df = test_df[(test_df['userID'].isin(train_df['userID'])) & (test_df['ISBN'].isin(train_df['ISBN']))]
    id_cols = ['userID', 'ISBN']
    trans_cat_train = dict()
    trans_cat_test = dict()
    for k in id_cols:
        cate_enc = preprocessing.LabelEncoder()
        trans_cat_train[k] = cate_enc.fit_transform(train_df[k].values)
        trans_cat_test[k] = cate_enc.transform(test_df[k].values)# --- Encode ratings:
    cate_enc = preprocessing.LabelEncoder()
    ratings = dict()
    ratings['train'] = cate_enc.fit_transform(train_df.bookRating)
    ratings['test'] = cate_enc.transform(test_df.bookRating)n_users = len(np.unique(trans_cat_train['userID']))
    n_items = len(np.unique(trans_cat_train['ISBN']))train = coo_matrix((ratings['train'], (trans_cat_train['userID'], \
                                                          trans_cat_train['ISBN'])) \
                                      , shape=(n_users, n_items))
    test = coo_matrix((ratings['test'], (trans_cat_test['userID'], \
                                                        trans_cat_test['ISBN'])) \
                                     , shape=(n_users, n_items))
    return train, test, train_df

函数 informed_train_test()返回训练集和测试集的 coo 矩阵以及原始训练数据帧,以便稍后对模型进行评估。让我们看看如何拟合我们的模型并评估其性能:

train, test, raw_train_df = informed_train_test(ratings_explicit, 0.8)start_time = time.time()
model=LightFM(no_components=110,learning_rate=0.027,loss='warp')
model.fit(train,epochs=12,num_threads=4)
# with open('saved_model','wb') as f:
#     saved_model={'model':model}
#     pickle.dump(saved_model, f)
auc_train = auc_score(model, train).mean()
auc_test = auc_score(model, test).mean()print("--- Run time:  {} mins ---".format((time.time() - start_time)/60))
print("Train AUC Score: {}".format(auc_train))
print("Test AUC Score: {}".format(auc_test))**--- Run time:  4.7663776795069377 mins ---
Train AUC Score: 0.9801499843597412
Test AUC Score: 0.853681743144989**

正如所料,训练集的 AUC 分数接近 1,我们在测试集中得到了 0.853 的 AUC 分数,不算太差。使用随机搜索来调整用于训练 LightFm 模型的参数。GridSearh 运行起来太昂贵了,所以我决定使用 scikit-optimize 包中的 forest_minimize()来调优参数。关于调整参数的函数的更多细节在本文的 github 页面中。

我知道我之前提到过,对于向没有与项目进行任何交互的新用户推荐项目来说,纯协作过滤预计表现不佳(冷启动问题)。在 LightFM 文档页面中展示的示例中,他们还表明,在使用 movielens 数据集向新客户推荐电影时,纯粹的协作方法无法获得令人满意的结果,但是,我很好奇自己是否会针对图书交叉数据集进行测试。令人惊讶的是,结果显示该数据集对冷启动问题反应良好,AUC 得分相对较高!!!为了在这种情况下训练模型,唯一的区别是我们将数据集随机分为训练集和测试集。这意味着在训练集和测试集中出现常见用户-项目交互的概率是完全随机的:

import scipy.sparse as spdef _shuffle(uids, iids, data, random_state):shuffle_indices = np.arange(len(uids))
    random_state.shuffle(shuffle_indices)return (uids[shuffle_indices],
            iids[shuffle_indices],
            data[shuffle_indices])**def random_train_test_split(interactions_df,
                            test_percentage=0.25,
                            random_state=None):**
    """
    Randomly split interactions between training and testing.This function takes an interaction set and splits it into
    two disjoint sets, a training set and a test set. Note that
    no effort is made to make sure that all items and users with
    interactions in the test set also have interactions in the
    training set; this may lead to a partial cold-start problem
    in the test set.Parameters
    ----------interactions: a scipy sparse matrix containing interactions
        The interactions to split.
    test_percentage: float, optional
        The fraction of interactions to place in the test set.
    random_state: np.random.RandomState, optional
        The random state used for the shuffle.Returns
    -------(train, test): (scipy.sparse.COOMatrix,
                    scipy.sparse.COOMatrix)
         A tuple of (train data, test data)
    """
    interactions = csr_matrix(interactions_df.values)
    if random_state is None:
        random_state = np.random.RandomState()interactions = interactions.tocoo()shape = interactions.shape
    uids, iids, data = (interactions.row,
                        interactions.col,
                        interactions.data)uids, iids, data = _shuffle(uids, iids, data, random_state)cutoff = int((1.0 - test_percentage) * len(uids))train_idx = slice(None, cutoff)
    test_idx = slice(cutoff, None)train = coo_matrix((data[train_idx],
                           (uids[train_idx],
                            iids[train_idx])),
                          shape=shape,
                          dtype=interactions.dtype)
    test = coo_matrix((data[test_idx],
                          (uids[test_idx],
                           iids[test_idx])),
                         shape=shape,
                         dtype=interactions.dtype)return train, test

现在让我们来看看 AUC 分数在随机训练测试分割中是如何不同的:

train, test = random_train_test_split(ratings_matrix)start_time = time.time()
model=LightFM(no_components=115,learning_rate=0.027,loss='warp')
model.fit(train,epochs=12,num_threads=4)
# with open('saved_model','wb') as f:
#     saved_model={'model':model}
#     pickle.dump(saved_model, f)
auc_train = auc_score(model, train).mean()
auc_test = auc_score(model, test).mean()print("--- Run time:  {} mins ---".format((time.time() - start_time)/60))
print("Train AUC Score: {}".format(auc_train))
print("Test AUC Score: {}".format(auc_test))**--- Run time:  8.281255984306336 mins ---
Train AUC Score: 0.9871253967285156
Test AUC Score: 0.6499683856964111**

随机分割数据预计会得到 0.5 左右的 AUC 分数,但我们可以看到,我们做得比扔硬币向新用户推荐商品或向当前用户推荐新商品好得多,因为我们的 AUC 分数为 0.649。我把对这种行为的进一步分析留给了本文的读者。

应用:

让我们假设数据集中的书籍是我们正在销售的商品,数据集中的用户实际上是目标客户。为了使案例更接近电子商务在线商店,我们可以改变评分值的一个方面是将值的范围从(1–10)减少到(7–10)。顾客的交互可以总结为: A-查看商品,B-点击商品,C-将商品添加到他们的购物车,以及 D-进行交易以购买商品。因此,在这种情况下,通过将评分值减少到前 4 名(7、8、9、10),我们可以更接近地模拟上述商品与顾客的互动。

photo credit: unsplash

在电子商务应用中,推荐系统主要有三种应用场景。我不打算包含为本文接下来的部分提供结果的函数的实际代码,但它们会在 github repo 的主 jupyter 笔记本中。

  • 最常见的场景是根据特定客户的互动(查看和点击商品)向其进行典型推荐:

User-Item interaction matrix

user_dikt, item_dikt = user_item_dikts(user_item_matrix, books)similar_recommendation(model, user_item_matrix, 254, user_dikt, item_dikt,threshold = 7)**Items that were liked (selected) by the User:**
1- The Devil You Know
2- Harlequin Valentine
3- Shout!: The Beatles in Their Generation
4- Sandman: The Dream Hunters
5- Dream Country (Sandman, Book 3)
6- Assata: An Autobiography (Lawrence Hill &amp; Co.)
7- The Golden Compass (His Dark Materials, Book 1)
8- The Fellowship of the Ring (The Lord of the Rings, Part 1)
9- The Hobbit: or There and Back Again
10- Harry Potter and the Sorcerer's Stone (Book 1)
11- Something Wicked This Way Comes
12- Martian Chronicles
13- Animal Farm
14- 1984
15- The Dark Half
16- Harry Potter and the Goblet of Fire (Book 4)
17- Harry Potter and the Prisoner of Azkaban (Book 3)
18- Harry Potter and the Prisoner of Azkaban (Book 3)
19- Harry Potter and the Chamber of Secrets (Book 2)
20- Harry Potter and the Chamber of Secrets (Book 2)
21- The Bonesetter's Daughter
22- The Wolves in the Walls
23- Stardust
24- Martian Chronicles
25- American Gods: A Novel

 **Recommended Items:**
1- The Lovely Bones: A Novel
2- Harry Potter and the Order of the Phoenix (Book 5)
3- The Catcher in the Rye
4- The Da Vinci Code
5- Harry Potter and the Sorcerer's Stone (Harry Potter (Paperback))
6- Red Dragon
7- Interview with the Vampire
8- Divine Secrets of the Ya-Ya Sisterhood: A Novel
9- Sphere
10- The Pelican Brief
11- Little Altars Everywhere: A Novel
12- To Kill a Mockingbird
13- Coraline
14- The Queen of the Damned (Vampire Chronicles (Paperback))
15- The Hours: A Novel

基于相似的用户-项目交互,我们向 ID#为 254 的用户推荐了 15 个项目(书籍)。

  • 第二种最常见的情况是,您计划告知客户有关追加销售(销售补充已购商品的额外商品)和交叉销售(销售客户可能感兴趣的其他独立类别的商品)的选项。明确的例子有:“经常一起购买”、“查看了该商品的顾客也查看了……”。对于这个任务,我必须将用户和图书评分的阈值从 20 增加到 200,这样我就可以得到一个更小的评分数据框架。查找相似的项目需要为数据集中的所有项目创建项目嵌入,这可能会占用大量内存(RAM)。我试着运行了几次,但我得到了低内存错误,所以如果您的机器上有足够的 RAM,您可以尝试使用较低的阈值:
item_embedings = item_emdedding_distance_matrix(model,user_item_matrix)
also_bought_recommendation(item_embedings,'B0000T6KHI' ,item_dikt)**Item of interest :Three Fates (ISBN:** B0000T6KHI**)**
**Items that are frequently bought together:**
1- Surrender to Love (Avon Historical Romance)
2- Landower Legacy
3- Ranch Wife
4- Sara's Song
  • 这种推荐系统的第三个应用可以帮助改善客户体验并增加销售额,当您拥有一家商店,并且您决定通过向更有可能购买该商品的特定用户推荐商品来开展促销活动时:
users_for_item(model, user_item_matrix, '0195153448', 10)**[98391, 5499, 136735, 156214, 96473, 83443, 67775, 28666, 115929, 42323]**

我们推荐了 10 个更有可能对 ISBN #为 0195153448 的物品(书)感兴趣的用户(id)。下一步可能是向这些用户发送促销电子邮件,看看他们是否对提到的商品感兴趣。

最终想法:

值得注意的是,一般来说,协同过滤方法需要足够的数据(用户-项目交互)才能获得好的结果。非常感谢您的提问和评论。

以下是该项目的 github repo 的链接:

[## nxs 5899/推荐系统-LightFM

使用 python-nxs 5899/Recommender-System-LightFM 中的 light FM 包的可扩展电子商务推荐系统

github.com](https://github.com/nxs5899/Recommender-System-LightFM)

参考资料:

https://github . com/aayushmnit/cookbook/blob/master/rec sys . py

https://towards data science . com/my-journey-to-building-book-recommendation-system-5ec 959 c 41847

https://towards data science . com/challenges-solutions-for-production-recommendation-systems-d 656024 bbd ca

如果你想增加枪支致死的风险,就不要管制枪支。哦,等等,那很糟糕…

原文:https://towardsdatascience.com/if-you-want-to-increase-risk-of-death-by-firearm-dont-regulate-guns-oh-wait-that-s-bad-p-9d9e0166b540?source=collection_archive---------7-----------------------

2015 年,如果你的孩子住在阿拉斯加,他们死于子弹的可能性是住在马萨诸塞州的 24 倍。就我个人而言,我不希望我的孩子去上图左上角的任何一个州处理他们的日常事务或参加电影或音乐会或大学课程,因为我希望他们健康长寿,为我生孙子,这样我就可以有孩子一起玩了。我跑题了。

为了制作这个图表,我按照美国各州和年份过滤了疾病预防控制中心的数据库中的死亡原因。根据以下死亡原因代码,任何火器造成的死亡都包括在内,无论是合法死亡还是意外死亡:

U01.4(涉及火器的恐怖主义)

W32(手枪发射)

W33(步枪、猎枪和大型火器发射)

W34(从其他和未指明的火器发射)

X72(手枪走火造成的故意自残)

X73(用步枪、猎枪和更大的火器发射故意自残)

X74(其他未具体说明的火器发射造成的故意自伤)

X93(手枪发射攻击)

X94(步枪、猎枪和大型火器攻击)

X95(用其他未具体说明的火器发射攻击)

Y22(手枪射击,未确定意图)

Y23(步枪、猎枪和大型火器发射,未确定意图)

Y24(其他和未指明的火器发射,未确定的意图)

Y35.0(涉及火器发射的法律干预)

我将这些数据与总部位于波士顿大学的州枪支法律项目的州级枪支限制法规数据结合起来(嘿,我儿子在波士顿大学读的研究生——耶!).我刚刚被指向 2013 年 J AMA 内科学的一篇文章,该文章使用类似的数据(CDC 枪支死亡数据+各州枪支法律数据)得出类似的结论。它在付费墙后面,但是你可以阅读摘要。

我没有在这个情节上花太多时间。这并不好看,不仅仅是因为这个话题。我故意省略了州名和红蓝标签,因为我想专注于两个指标:被子弹打死的可能性&买枪有多难。如果你对你所在州的法律感到关注或好奇,请查看页面,了解更多

用于数据操作和数据可视化的代码可以在我的 GitHub 中找到。

感谢您的阅读。

我欢迎反馈——您可以“鼓掌”表示赞同,或者如果您有具体的回应或问题,请在此给我发消息。我也有兴趣听听你想在未来的帖子中涉及哪些主题。

阅读更多关于我的作品jenny-listman.netlify.com。欢迎随时通过 Twitter@ jblistmanLinkedIn联系我。

注意事项:

  1. 枪支法律数据:美国各州从 1991 年到 2017 年的枪支法律可从https://www.kaggle.com/jboysen/state-firearms获得
  2. 疾控中心 1999 年至 2015 年火器致死原因数据:https://wonder.cdc.gov/ucd-icd10.html
  3. 使用 R 中的工具处理和绘制数据

如果你的文件只保存在你的笔记本电脑上,它们就像不存在一样!

原文:https://towardsdatascience.com/if-your-files-are-saved-only-on-your-laptop-they-might-as-well-not-exist-29f3503750d5?source=collection_archive---------2-----------------------

如何避免计算机灾难

上周,当我在做三个研究生课程项目中的一个时,我的笔记本电脑决定是时候放弃了。我花了 15 分钟徒劳地重置电池,并按住电源按钮试图得到回应,但无济于事:我的笔记本电脑永远完了。

一年前的这个时候,我会无法控制地哭泣,我的学期在最后一周结束了。然而,这一次,我放下我的笔记本电脑,走到学校图书馆,登录到一台电脑上,从 Google Drive 下载我的文件,这些文件一直同步到我的笔记本电脑变暗的那一分钟,并在 30 分钟内完成我的最终项目。总而言之,多亏了自动备份,我没有损失一整个学期,而是损失了一份报告的两行内容。

这个近乎悲剧的例子说明了任何在电脑上工作的人都必须记住的两点:

  1. 不久的某个时候,你的电脑会彻底失灵
  2. 这可能是致命的损失,也可能没什么大不了的,这取决于你的安全措施

亲眼目睹了电脑故障对同学们造成的破坏,几个月前,我终于安装了谷歌硬盘备份和同步。这是将在你的电脑后台运行的服务之一,将所有文件(或你选择的文件)保存到云端,你可以从世界上任何一台电脑上访问它们。

有一句话我很喜欢,叫做二的法则:“二等于一,一等于零。”(我第一次在 Cortex 播客上从 CGPGrey 那里听到这个。这意味着,如果你只有一件必需品,它还不如不存在,因为你可能会不可避免地失去它。说到文件存储,如果你的文件只存在你的笔记本电脑上,它们可能根本不会被保存,因为你是如此的脆弱。

注册备份服务往往是每个人都说他们会抽时间去做,但从来没有真正实施的事情之一(我在这个群体中呆了很长时间)。然而,在你开始做任何你不想失去的工作之前,有适当的备份应该是必要的!

在今天这个存储便宜得离谱的世界里,没有任何理由不在云中提供文件的多个副本。对于学生来说,你可能会通过 Google Drive 获得免费的无限存储空间,这意味着你可以存储任何你想要的东西(我没有测试过无限的限制,但有朋友节省了数 TB)。对于其他人来说, 100 GB 的存储空间在 Google Drive 上只需每月 2 美元,其他选项也同样合理。我知道当我的屏幕变成一片空白时,我会很乐意每年支付 100 美元来确保我的文件是安全的。

您选择的确切备份路径并不重要,但重要的是确保您的文件位于多个位置(u 盘总比没有好,但云备份是最佳选择)。我更喜欢自动同步,因为人类会犯错。有了自动同步文件的服务,你就没有什么风险会受到技术的阻碍!这是一个你应该满足于让计算机替你思考的领域。(同样,如果一个程序提供了自动保存文件的选项,一定要让它尽可能频繁地保存!)

每当我在笔记本电脑上看到 Google Drive sync 的小图标呼呼转动时,我都会花一点时间来欣赏自动文件备份的奇迹。下次我的笔记本电脑不可避免地出现故障时,我知道这只是一个小的、可恢复的不便。你能说同样的话吗?

我欢迎反馈和讨论,可以通过 Twitter @koehrsen_will 联系到我。

如果你不关注分析和归因,那么你就没有抓住重点

原文:https://towardsdatascience.com/if-youre-not-focusing-on-analytics-and-attribution-then-you-re-missing-the-point-e901444366ac?source=collection_archive---------7-----------------------

所有网站都有某种目标或一组目标。你想要一定数量的读者,或者一定数量的新闻订阅,或者(很常见)一定数量的销售额。但是当你试图实现这些目标时,除非你有某种盲目的运气,否则你需要一条通往那里的道路。如果你想一个月卖 50 个小部件,而你只卖了 20 个,你如何得到另外 30 个呢?

这很容易成为任何电子商务新手最常见的第一个问题。对于一个不具备所需各种技能的专业人士来说,尤其是在数字营销领域,提高转化率的途径很容易变得模糊不清。你需要尽你所能让它尽可能的清晰。怎么会?通过学习如何解读网络分析。

维基百科给出了定义:“分析是数据中有意义模式的发现、解释和交流。”

首先,你有责任对你正在吸引的流量类型、这些用户来自哪里以及他们在你的网站上做什么有一个非常坚实的概念。因为营销预算不是无限的,即使是很大的预算也必须有效利用,所以有必要(也很明显)吸引最有可能帮助你以经济高效的方式实现目标的流量。

我个人在过去看到过许多公司对整个问题采取极不科学的方法的例子——尤其是当忽视适当的分析设置时。然后,他们会想为什么他们的目标甚至没有接近实现,吸引流量或增加转化率的整个概念对他们来说就像是巫术。

当看着你的战略不断完善时,在你开始“建立更多”之前,通常更好地利用时间来完善你已经拥有的。你想知道网站的哪些部分已经吸引了最多的流量,用户在哪里停留的时间最长,最高价值的用户来自哪里,等等。

能够访问这么多数据的好处在于,你可以对网站上的所有流量和行为有一个非常细致的了解。这种数据供应是可以利用的。你需要收集尽可能多的数据,并学会热爱、生活和呼吸数据。需要从第一个访客那里收集。即使在一开始,当流量水平较低时,你仍然可以获得有价值的见解,这将使你受益,并在早期阶段给你动力。

例如,一个主要的数据是桌面和移动用户的细分。如今,随着越来越多的流量是移动的,这是一个需要考虑的非常重要的问题(许多网站的绝大多数流量细分都倾向于移动)。另一方面,许多设计师和开发人员倾向于以桌面优先的方式来考虑网站的设计和可用性——我认为这在很大程度上是因为桌面是一个更大的“画布”,当你有很多页面元素想要融入设计时,桌面会更加宽容。这种方法的结果并不理想。如果你看了你的分类,发现 90%的流量是移动的,那么你可能会重新考虑这种方法。

即使对那些没有预算的人来说, Google Analytics 也是一项非常强大的分析服务,被全球数百万网站所使用。对于那些害怕的人,谷歌甚至提供免费培训,所以没有借口。这是一个比你的网络主机可能提供的内置分析好得多的解决方案。

一旦你开始有一个更具体的想法,你的典型流量来自哪里,他们如何与你的网站互动,以及其余的基础知识,这是很重要的,看看到底是什么样的流量给你想要的结果,所以你可以专注于它们。你需要了解是什么样的流量在推动转化。这叫归因。

维基百科给出了定义:“营销归因提供了一种理解,即以何种特定顺序发生的事件的何种组合会影响个人从事所需的行为,通常被称为转化。”

一旦你有了一些转化数据,和大量的流量数据,你就可以看看是什么来源和平台给你带来了最好的结果。例如,通常你会看到移动电子商务的转换率(和其他数据,如会话时间)低于桌面电子商务。在这种情况下,你可能想增加桌面流量的广告支出,以提高你的整体转化率。此外,你可以根据页面速度优化优先处理移动网站,重新考虑用户结账流程,并测试不同的登录页面。

如果你发现你所有的转化率对搜索流量更有利(这是我见过的典型情况),那么你需要更多地关注 SEO 来吸引更多的这类流量。如果你发现来自 Instagram 的流量比来自脸书的流量表现更好,那么你可以重新考虑你的社交媒体策略。

你明白了。

然而,要当心“虚荣尺度”。这意味着这些数字实际上并不意味着什么。总会话数是一个虚荣心指标,关注者也是。你可以针对某个东南亚国家开展一场极其廉价的页面点击活动,让成千上万的用户点击你的网站,但我保证没有人(或很少人)会采取任何有意义的转化行动。就追随者而言,那些总是可以买到的。主要数字是转化率,是百分比。垃圾流量太多,这个比例就会下降。

一旦数字变得更加清晰,那么增加转化率的途径也会变得更加清晰。自然,理解这一切是一个学习的过程。无论如何,这是创建一个盈利网站或电子商务业务最重要的第一步。现在投入的时间会让你的生活更轻松,你的目标更接近,从长远来看,你的网站会更赚钱。祝你好运。

注册我的时事通讯,了解更多类似的故事和其他有趣的事情。

我是住在纽约市的数码战略家和偶尔的摄影师。在 Instagram 上的 @andreikorchagin 关注我,或者在 andreikorchagin.com拜访我

IGLOO:一种不使用递归神经网络处理序列的不同范例

原文:https://towardsdatascience.com/igloo-a-different-paradigm-for-processing-sequences-ec656da732cf?source=collection_archive---------9-----------------------

Photo by Celso on Unsplash

在 ReDNA labs,我们最近发表了一篇研究论文,虽然其中充满了技术细节、基准和实验,但我们希望对这种新的神经网络结构给出更直观的解释。原文在此

在本文中,我们介绍了一种新的神经网络架构,它是特别擅长处理长序列,并且与主要教条相反,没有利用任何形式的递归神经网络。虽然这不是第一次对序列进行卷积处理,但我们的结构 IGLOO 利用了输入片段之间的一些特殊关系。这种新颖的方法在各种常见的基准测试中产生了良好的结果;值得注意的是,我们表明,在一些常见的任务上,它可以处理多达 25000 个时间步,而历史递归神经网络则难以处理超过 1000 个时间步。该方法可应用于各种研究领域,本文特别将其应用于医学数据和情感分析。

使用神经网络处理序列

直到最近,一旦在机器学习任务中有了顺序的概念,神经网络一直是首选结构。众所周知,鉴于递归神经网络(RNN)的递归性质,存在消失梯度的问题。历史上,长短期记忆(LSTM)和门控循环单位(GRU)细胞是最常用的 RNN 结构,但最近出现了新的改进细胞,如独立循环神经网络(IndRNN)、准循环神经网络(QRNN)、循环加权平均(RWA)和其他一些细胞。它们在速度和对历史单元的收敛方面有所改进。

所有这些单元的主要思想是数据被顺序处理。

除此之外,一种称为时间卷积网络(TCN)的新结构可用于分析顺序数据。TCN 使用 1D 卷积和扩张卷积来寻找序列的表示。(Bai 等人,2018) [3]的论文-用于序列建模的一般卷积和递归网络的经验评估,给出了更多细节。

自从最初尝试使用卷积来处理序列,就为新方法的出现开辟了道路。

爱斯基摩人圆顶小屋

Basic IGLOO cell

我们知道,应用于序列的 1D 卷积返回特征图,指示序列如何对各种过滤器作出反应。给定核大小 K*,K 个滤波器,并使用因果 1D 卷积(以便在时间 T,只有直到时间 T 的数据是可用的),每个时间步长找到具有向量的表示。该向量中的每一项代表该时间步中每个过滤器的激活。完整特征图 F1 的大小为(T,K)。

然后,通常的卷积网络将另一个卷积应用于该初始卷积,并返回第二个更深(在某种意义上,它离输入更远)的特征图。该第二卷积可以被视为学习特征图的邻接片之间的关系。通常的 Convnets 继续以这种方式堆叠层。例如,时间卷积网络(TCN)结构使用扩展卷积来减少网络的总深度,同时旨在使较深层具有尽可能大的感受域,即,使较高层具有关于初始输入的尽可能全局的视野。由于更高层连接到所有的输入,然后由训练过程使信息向上流动。

冰屋结构的工作方式不同。在初始卷积之后,不是将第二卷积层应用于 F1,而是我们在第一轴上从可用的 T(p 的典型值为 4)中收集 p 个切片,然后我们将这些切片连接起来以获得大小为(p,K)的矩阵 H。这些 p 切片可以来自附近地区,也可以来自遥远的地区,因此汇集了来自特征地图不同部分的信息。因此,可以说冰屋在初始特征地图 F1 中利用了非本地关系。收集数量为 L 的这些大块以产生大小为(L,p,K)的矩阵。然后,该矩阵逐点乘以相同大小的可训练滤波器。看待这种操作的一种方式是,过滤器学习 F1 的非连续切片之间的关系。然后,我们将最后一个和倒数第二个轴上的逐点乘法产生的每个元素加在一起,以找到大小为 l 的向量 U。我们还将偏差添加到该输出。因此会有 L 偏差。应用诸如 ReLU 的非线性(该步骤不是必需的)。结果,我们获得了一个向量 U,它将代表序列,然后可以输入到一个密集层,用于分类或回归。总之,我们训练(L . k . p+1)个参数(不包括初始卷积 C1)。

一些评论:

U 的每个元素可以被视为特征图 F1 的 p 个不一定连续的随机选择的切片之间的关系的表示。这种关系的本质是由为该补丁训练的唯一过滤器给出的。

给定足够大的 L,U 具有完整的感受野,并且连接到输入向量的每个元素,因此它可以用作该序列的表示向量。这对于收敛不是绝对必要的,因为一些输入点可能对有效的表示没有贡献。CNN 架构并不总是具有这种特性。

传统的 CNN 依靠网络深度来汇集来自输入的遥远部分的信息,而 IGLOO 直接从输入的遥远部分采样补丁,因此它不需要深度。在某些情况下,一层就足够了。然而,由于 CNN 在每一层深度提供了不同的粒度级别,所以使用不同级别的补丁也是很有趣的,这是我们实现的。

虽然卷积网络都是以金字塔的方式利用本地信息,但 IGLOO 试图从整个输入空间收集信息。直观上,convnets 将连续的卷积层应用于输入序列或图像,并且每一层以不同的粒度水平表示信息,因为离输入数据越远的每一层具有越大的感受域。IGLOO 可以直接访问不同区域的输入数据,所以不需要完全依赖这种金字塔结构。本质上,它试图利用输入空间的不同部分之间的相似性来找到可用于回归或分类的表示。

思想实验

例如,让我们想象下面的思维实验。给定我们具有 100 个时间步长和 10 个特征的序列,即大小为(100,10)的矩阵。一些序列在前 50 个时间步长和后 50 个时间步长中包含大小为 10 的相同向量。其他一些序列没有任何重复的向量。该机器学习任务的目标是在大量的例子上进行训练(在训练集上),然后能够在给定测试集的情况下正确地识别那些具有重复元素的序列(类 1)和那些没有重复元素的序列(类 0)。如果随机选择,我们有 50%的几率是正确的。

RNN 将如何处理这项任务?RNN 有一个内部存储器,用于记录将误差降至最低所需的重要信息。因此,RNN 将一个接一个地处理序列中的每个元素,并跟踪是否存在重复。

冰屋将如何处理这项任务?想象在训练集中,对于第一个样本,在索引 1 和 51 处有相同的向量。然后,在收集随机补丁时,IGLOO 将处理向量(0,1,10,25),(20,40,60,80)或(1,51,10,3)(它可以设置为处理 1000 个这样的补丁)。在后一种情况下,应用于该小块的可训练滤波器将通过输出一个大的正数而做出强烈的反应,因此网络将了解到如果在第 1 个索引处的向量和在第 51 个索引处的向量是相同的,那么为该序列找到的表示应该是第 1 类。然后在测试时,如果索引 1 和 51 处的向量相同,网络现在知道它应该被分类为类别 1。

虽然这项任务相当简单,但研究文档中介绍了一些稍微复杂一些的任务。

使用复制记忆任务延长记忆时间

这项任务最初是在(Hochreiter 和 J. Schmidhuber,1997 年)[1]中介绍的。我们给定一个大小为 T+20 的向量,其中前 10 个元素 G=[G0,G1,..,G9]是 1 到 8 之间的随机整数,接下来的 T-1 个元素是 0,接下来的元素是 9(作为标记),接下来的 10 个元素又是 0。任务是生成一个序列,该序列除了最后 10 个项目之外在任何地方都是零,该序列应该能够再现 g。任务 A 可以被认为是一个分类问题,并且所使用的损失将是分类交叉熵(跨 8 个类别)。该模型将输出 8 个类别,这些类别将与实际类别进行比较。

实验表明,对于超过 1000 个时间步长,rnn 在这个任务上很难实现收敛,部分原因是梯度消失的问题。因为冰屋把一个序列看作一个整体,所以它没有同样的缺点。

复制记忆——冰屋模型。达到精度> 0.99 秒的时间。

t 大小(补丁数量)—时间—参数

T=100 (300) — 12s — 80K

T=1000 (500) — 21s — 145K

T=5000 (2500) — 52s — 370K

T=10000 (7000) — 61s — 1520K

T=20000 (10000) — 84s — 2180K

T=25000 (15000) — 325s — 3270K

对于超过 25000 个时间步的序列,IGLOO 似乎可以实现收敛。文献中没有 RNN 能够做到这一点。

虽然 NLP 任务通常使用少于 1000 步的序列,但在某些领域长序列是常见的。例如 EEG 数据和声波。这篇论文包括一个用脑电图数据做的实验。

更快地收敛语法任务

Grammar rules

紧随其后(Ostemeyer et al .,2017)[2],我们使用这个任务来确保 IGLOO 可以高效地表示序列,而不仅仅是集合。为了成功完成这项任务,任何神经网络都需要能够提取序列元素出现顺序的信息。基于人工语法生成器,我们生成训练集,该训练集包括遵循所有预定义语法规则并且被分类为正确的序列,并且我们生成具有错误的序列,该错误应该被识别为无效。作为语法生成器的结果,诸如 BPVVE、BTSSSXSE 和 BPTVPXVVE 的序列将被分类为有效,而诸如 BTSXXSE、TXXTTVVE 和 BTSSSE 的序列将被分类为无效。

在这种情况下,序列只有 50 倍步长,有 7 个特征。实验记录了在使用不同模型的测试集上达到 95%的准确率需要多长时间。

Results on the Grammar task from the original paper

在这个实验中,IGLOO 似乎比测试的其他 RNN 细胞更快,尤其是比 CuDNNGRU 细胞更快,CuDNNGRU 细胞是普通 GRU 的优化版本

结论

我们引入了一种新型的神经网络,通过利用非局部相似性来处理序列。从基准测试来看,它在处理非常长的序列时似乎比普通的 RNNs 更好,同时也更快。

虽然基准可以很好地确保一个想法在原则上是有意义的,但在野外尝试冰屋将有助于了解它在某些情况下是否可以作为替代方案。

提供了该结构的 Keras/tensorflow 代码,所以这实际上是将 RNN 细胞换成冰屋细胞的问题,看看是否会发生奇迹。我们鼓励读者报告他们的发现。

此处提供了一个 Keras 实现

我们确实帮助公司将机器学习添加到他们的业务流程中,也许我们也可以帮助你。取得联系!【ai@rednalabs.com 号

参考文献

1-S. Hochreiter 和 J. Schmidhuber。长短期记忆。神经计算,9(8):1735–1780,1997。

2-J .奥斯特迈耶和 l .科威尔。基于递归加权平均的序列数据机器学习。arXiv:1703.01253v5,2018。

3-S .白、j .济科-科尔特尔和 v .科尔通。用于序列建模的一般卷积和递归网络的经验评估。在 arXiv:1803.01271v2,2018。

原载于 2018 年 7 月 19 日www.rednalabs.com

用排列测试阐明我们的灯泡数据

原文:https://towardsdatascience.com/illuminating-our-light-bulb-data-with-the-permutation-test-e89dc50695e4?source=collection_archive---------18-----------------------

几乎每天我都会遇到一种新的“环境统计”(是的,现在有了一个新的名称)。卫生纸每天杀死 27000 棵树。三分之二的大堡礁正在消失。虽然我确信这些有趣的事实是相关的,但我经常发现它们不相关,不可思议,也不那么有趣。此外,随着我对统计的了解越来越多,我开始质疑这些数字背后隐藏的过程。所以我决定自己做一个关于伯克利学生和灯泡的环境统计。

Photo by Luis Tosta on Unsplash

这学期,我有机会在加州大学伯克利分校的能源和资源组领导一门课程的教学——ERG 98:为了更绿色的明天的可持续能源。在这个标题乐观的课堂上,我和我的同事伊丽莎白给 30 名学生讲授能源和环境的基础知识——从千瓦与千瓦时到气候变化的社会不公。然后,我们邀请来自可持续发展公司的演讲嘉宾,如特斯拉和 Volta Charging,以及学术界人士,如可持续交通行为的研究人员。

我们的一个固定的演讲嘉宾,克里斯托弗·琼斯,在加州大学伯克利分校运行凉爽气候网络。他创造了第一个综合碳足迹计算器,它询问用户的生活方式并输出他们估计的碳排放量。利用这些数据,Chris 绘制了美国各县的估计排放量。

Average Household Carbon Footprint — Eastern United States. Credit: CoolClimate Network

你看到了什么?

在看到这张图之前,我就在期待类似的图。随着我们接近更发达的地区,每户平均排放量通常会增加。但是一个奇怪的现象引起了我的注意——城市中心的那些绿色斑点。城市真的比周围的郊区更有效率吗?2010 年,Edward Glaeser 和 Matthew Kahn 在为城市经济学杂志撰写的题为 城市的绿色:二氧化碳排放和城市发展 的论文中讨论了这一趋势。 Glaeser 和 Kahn 观察了 48 个大都市的城市和郊区的交通、家庭取暖和电力使用的排放。在这项研究中,他们得出结论:

“如果城市人口居住在更靠近城市中心的高密度地区,这些地区的冬天更温暖,夏天更凉爽,电力公司使用更少的煤来发电,那么家庭温室气体排放量就会更低。”

从本质上讲,人口密度的增加通常意味着碳强度的降低,尤其是在煤炭不太受欢迎的地区。

看到这种趋势,我决定以 ERG 98 的学生为对象进行自己的统计测试。不幸的是,个人的总排放量很难计算,所以用一个不完美的替代物来代替:灯泡数。下课时,我顺手在考勤表上加了两个额外的问题。以下是我问他们的问题:

  1. 你会把你的家分为农村、郊区还是城市?
  2. 你家大约有多少个灯泡?

这些是我收到的分发内容:

Histograms of survey answers for number of lightbulbs, split by area type

很明显,城市和郊区的灯泡数量有所不同,大约有 11 个灯泡!这可能支持这样的观点,即大都市地区的能源使用通常在城市中心较低。但是在我做太多宽泛的陈述之前,我必须认识到我的假设。这绝不是对大都市居民的随机抽样。此外,这种手段上的差异可能完全是随机发生的。

让我们把重点放在后一种说法上。如果我的特定城市学生只是碰巧因为未知原因少了灯泡怎么办?见鬼,我住在伯克利市,但是我的室友(也住在这个城市)比我多了 3 个灯泡!在比较两种分布时,应该有一种方法来解释这种随机变化。

一种越来越流行的比较两种分布的方法是排列测试。置换检验的前提是假设两组数字来自相同的基础分布(科学家称此为零假设 ) 在这种假设下,我们通过改变“城市”和“郊区”标签来模拟新的学生调查。然后,经过多次模拟,我们可以确定我们观察的近似可能性——11 个灯泡的平均差异。

这个过程从随机地将标签“郊区”和“市区”重新分配给调查中给出的各种灯泡数量开始。我们有 13 名郊区学生和 14 名城市学生,所以我们打乱了数据表,将前 13 行分配给“郊区”,其余的分配给“城市”这给了我们两个新的分布来比较。

然后,我们计算两个随机生成的分布的平均值之间的新差异。称之为 D1。我们可以将 D1 解释为城市和郊区灯泡数量之间的一个可能差异,假设它们是从相同的基础分布中选择的。然后,我们重复这个过程很多次(我做了 10,000 次),每次都得到一个新的“随机”差异。

Two instances of shuffling the labels and calculating a new difference in means.

现在,假设城市和郊区学生的答案来自相同的分布,我们通过 10,000 来近似所有可能的均值差异来观察 D1。

正如我们从这个直方图中看到的,最有可能的差异在-10 到 10 个灯泡之间。右侧中突出显示的空间表示大于或等于 11 个差异灯泡的区域。因此,我们可以将这个区域中的蓝条视为满足该差异的所有“随机”时间。这相当于整个分布的 3.48%——意味着至少 11 个灯泡的差异有 3.48%的可能性是由于随机性造成的。

因此,我们可以有 96%的把握说,由于某种潜在的原因,我的城市学生比我的郊区学生拥有的灯泡少。正如研究表明的那样,人口密度和每户能源使用量之间似乎存在某种联系。Glaeser 和 Kahn 认为公共交通的便利和房子的大小是可能的原因。显然,城市化进程的加快是气候变化之谜的一部分。

要了解更多关于排列测试的知识,我推荐阅读托马斯·斯莫尔的概念性文章这里切斯特·伊茨的编程文章这里。你也可以在我的 github 上查看我的博客代码。

我希望你喜欢这个小小的社会和环境问题的统计之旅。如果您对此分析有任何问题或意见,请发表评论,我将确保做出回应。你也可以在johnleyden.com找到我的联系方式。

LSTM 和 GRU 的图解指南:一步一步的解释

原文:https://towardsdatascience.com/illustrated-guide-to-lstms-and-gru-s-a-step-by-step-explanation-44e9eb85bf21?source=collection_archive---------0-----------------------

嗨,欢迎来到长短期记忆(LSTM)和门控循环单位(GRU)的图解指南。我是迈克尔,我是人工智能语音助手领域的机器学习工程师。

在这篇文章中,我们将从 LSTM 和 GRU 背后的直觉开始。然后我会解释让 LSTM 和 GRU 表现如此出色的内部机制。如果你想了解这两个网络的内幕,那么这篇文章就是为你准备的。

如果你愿意,你也可以在 youtube 上观看这篇文章的视频版本。

问题是,短期记忆

递归神经网络存在短期记忆的问题。如果一个序列足够长,它们将很难将信息从较早的时间步骤传递到较晚的时间步骤。因此,如果你试图处理一段文字来做预测,RNN 氏症可能会从一开始就遗漏重要信息。

在反向传播期间,递归神经网络遭受消失梯度问题。梯度是用于更新神经网络权重的值。消失梯度问题是当梯度随着时间向后传播而收缩时。如果一个梯度值变得极小,它不会贡献太多的学习。

Gradient Update Rule

所以在递归神经网络中,获得小梯度更新的层停止学习。这些通常是早期的层。因此,因为这些层不学习,RNN 氏症可以忘记它在更长的序列中看到的东西,因此有短期记忆。如果你想知道更多关于递归神经网络的一般机制,你可以在这里阅读我以前的帖子。

[## 递归神经网络图解指南

嗨,欢迎来到循环神经网络图解指南。我是迈克尔,也被称为学习矢量。我是一个…

towardsdatascience.com](/illustrated-guide-to-recurrent-neural-networks-79e5eb8049c9)

LSTM 的和 GRU 的作为解决方案

LSTM 和 GRU 的发明是为了解决短期记忆问题。它们有称为“门”的内部机制,可以调节信息的流动。

这些门可以了解序列中哪些数据是重要的,应该保留或丢弃。通过这样做,它可以将相关信息传递到长长的序列链中进行预测。几乎所有基于递归神经网络的现有技术结果都是用这两个网络实现的。LSTM 和 GRU 氏症可以在语音识别、语音合成和文本生成中找到。你甚至可以用它们来为视频生成字幕。

好了,到这篇文章结束的时候,你应该对为什么 LSTM 和 GRU 擅长处理长序列有了一个坚实的理解。我将用直观的解释和插图来处理这个问题,并尽可能避免使用数学。

直觉

好了,先来一个思维实验。假设你正在网上看评论,以决定是否要买生活麦片(不要问我为什么)。你将首先阅读评论,然后决定是否有人认为它是好的还是坏的。

当你阅读评论时,你的大脑下意识地只记住重要的关键词。你会听到像“惊人的”和“完美平衡的早餐”这样的词。你不太在意“这个”、“给了”、“所有”、“应该”之类的词。如果一个朋友第二天问你这篇评论说了什么,你可能不会一字不差地记住它。你可能还记得要点,比如“肯定会再次购买”。如果你和我很像,其他的词会从记忆中消失。

这基本上就是 LSTM 或 GRU 所做的。它可以学习只保留相关信息来进行预测,而忘记不相关的数据。在这种情况下,你记住的单词让你判断它是好的。

递归神经网络综述

为了理解 LSTM 和 GRU 是如何做到这一点的,让我们回顾一下递归神经网络。一个 RNN 是这样工作的;第一个单词被转换成机器可读的向量。然后,RNN 逐一处理向量序列。

Processing sequence one by one

在处理时,它将前一个隐藏状态传递给序列的下一步。隐藏状态充当神经网络的记忆。它保存网络以前看到的以前数据的信息。

Passing hidden state to next time step

让我们看看 RNN 的一个单元,看看如何计算隐藏态。首先,将输入和先前的隐藏状态组合起来形成一个向量。该向量现在具有关于当前输入和先前输入的信息。向量经过 tanh 激活,输出是新的隐藏状态,或者网络的记忆。

RNN Cell

Tanh 激活

tanh 激活用于帮助调节流经网络的值。tanh 函数将值压缩为总是在-1 和 1 之间。

Tanh squishes values to be between -1 and 1

当向量流经神经网络时,由于各种数学运算,它会经历许多转换。所以想象一个值继续乘以比如说 3 。你可以看到一些价值如何爆炸,成为天文数字,导致其他价值似乎微不足道。

vector transformations without tanh

双曲正切函数确保值保持在-1 和 1 之间,从而调节神经网络的输出。您可以看到上面的相同值是如何保持在 tanh 函数允许的边界之间的。

vector transformations with tanh

这是 RNN 的作品。它的内部操作很少,但是在适当的情况下(比如短序列)可以很好地工作。RNN 算法使用的计算资源比它的变种 LSTM 算法和 GRU 算法少得多。

LSTM

LSTM 具有与递归神经网络相似的控制流。当信息向前传播时,它处理传递信息的数据。不同之处在于 LSTM 细胞内的操作。

LSTM Cell and It’s Operations

这些操作用于允许 LSTM 保存或忘记信息。现在,查看这些操作可能会有点让人不知所措,因此我们将一步一步地讲解。

核心概念

LSTM 的核心概念是细胞状态,以及它的各种门。细胞状态就像一条传输高速公路,沿着序列链一路传输相关信息。你可以把它想象成网络的“记忆”。理论上,细胞状态可以在整个序列处理过程中携带相关信息。因此,即使是来自较早时间步骤的信息也可以传递到较晚的时间步骤,从而减少短期记忆的影响。当细胞状态继续它的旅程时,信息通过门被添加到细胞状态或从细胞状态移除。这些门是不同的神经网络,决定细胞状态允许哪些信息。盖茨夫妇可以在训练中了解哪些信息是应该保留或忘记的。

乙状结肠的

门包含乙状结肠激活。乙状结肠活化类似于双曲结肠活化。它不是挤压-1 和 1 之间的值,而是挤压 0 和 1 之间的值。这有助于更新或忘记数据,因为任何乘以 0 的数字都是 0,导致值消失或被“忘记”任何数字乘以 1 都是相同的值,因此该值保持不变或“保持不变”网络可以了解哪些数据不重要,因此可以忘记,或者哪些数据重要,需要保留。

Sigmoid squishes values to be between 0 and 1

让我们更深入地了解一下各个门在做什么,好吗?所以我们有三个不同的门来调节 LSTM 细胞中的信息流动。遗忘门、输入门和输出门。

忘记大门

首先,我们有遗忘之门。这个门决定哪些信息应该被丢弃或保留。来自先前隐藏状态的信息和来自当前输入的信息通过 sigmoid 函数传递。值介于 0 和 1 之间。越接近 0 表示忘记,越接近 1 表示保留。

Forget gate operations

输入门

为了更新单元状态,我们有输入门。首先,我们将先前的隐藏状态和当前输入传递给一个 sigmoid 函数。它通过将值转换为 0 和 1 之间的值来决定哪些值将被更新。0 表示不重要,1 表示重要。您还可以将隐藏状态和当前输入传递给 tanh 函数,以挤压-1 和 1 之间的值,从而帮助调节网络。然后将双曲正切输出乘以 sigmoid 输出。sigmoid 输出将决定哪些信息对 tanh 输出很重要。

Input gate operations

细胞状态

现在我们应该有足够的信息来计算细胞状态。首先,单元格状态逐点乘以遗忘向量。如果乘以接近 0 的值,这有可能会丢失单元状态中的值。然后,我们从输入门获取输出,进行逐点加法,将细胞状态更新为神经网络认为相关的新值。这给了我们新的细胞状态。

Calculating cell state

输出门

最后,我们有输出门。输出门决定下一个隐藏状态应该是什么。请记住,隐藏状态包含以前输入的信息。隐藏状态也用于预测。首先,我们将先前的隐藏状态和当前输入传递给一个 sigmoid 函数。然后,我们将新修改的单元格状态传递给 tanh 函数。我们将双曲正切输出乘以 sigmoid 输出来决定隐藏状态应该携带什么信息。输出是隐藏状态。然后,新的单元状态和新的隐藏被带入下一个时间步骤。

output gate operations

回顾一下,“遗忘之门”决定了哪些内容与之前的步骤相关。输入门决定从当前步骤添加哪些相关信息。输出门决定下一个隐藏状态应该是什么。

代码演示

对于那些通过查看代码更好理解的人,这里有一个使用 python 伪代码的例子。

python pseudo code

1.首先,前一个隐藏状态和当前输入被连接起来。我们就叫它组合
2。合并把得到的输入到遗忘层。该层移除不相关的数据。
4。使用组合创建一个候选层。候选包含可能添加到单元格状态的值。
3。 Combine 也把 get 的馈入输入层。这一层决定来自候选的什么数据应该被添加到新的单元状态。
5。在计算了遗忘层、候选层和输入层之后,使用这些向量和先前的像元状态来计算像元状态。
6。然后计算输出。
7。逐点乘以输出和新的单元状态得到新的隐藏状态。

就是这样!LSTM 网络的控制流是一些张量运算和一个 for 循环。您可以使用隐藏状态进行预测。结合所有这些机制,LSTM 可以选择在序列处理过程中记住或忘记哪些相关信息。

苏军总参谋部情报总局

现在我们知道了 LSTM 是如何工作的,让我们简单看看 gru。GRU 是新一代的递归神经网络,与 LSTM 非常相似。GRU 摆脱了细胞状态,用隐藏状态来传递信息。它也只有两个门,一个复位门和更新门。

GRU cell and it’s gates

更新门

更新门的作用类似于 LSTM 的遗忘和输入门。它决定丢弃什么信息和添加什么新信息。

复位门

重置门是另一个用来决定忘记多少过去信息的门。

这是一个 gru。GRU 的张量运算较少;因此,他们比 LSTM 的训练速度要快一些。没有明显的赢家哪一个更好。研究人员和工程师通常尝试两者来确定哪一个更适合他们的用例。

原来如此

综上所述,RNN 氏综合症对于处理序列数据进行预测是很好的,但是会受到短期记忆的影响。LSTM 氏症和 GRU 氏症是作为一种利用被称为“门”的机制来减轻短期记忆的方法而产生的。门只是调节流经序列链的信息流的神经网络。LSTM 和 GRU 的被用于先进的深度学习应用,如语音识别、语音合成、自然语言理解等。

如果你有兴趣深入了解,这里有一些很棒的资源链接,可以让你从不同的角度理解 LSTM 和 GRU。这篇文章深受他们的启发。

http://www . wild ml . com/2015/10/recurrent-neural-network-tutorial-part-4-implementing-a-grul STM-rnn-with-python-and-the ano

http://colah.github.io/posts/2015-08-Understanding-LSTMs/

https://www.youtube.com/watch?v=WCUNPb-5EYI

我写这篇文章很开心,所以请在评论中告诉我这是否有帮助,或者你想在下一篇文章中看到什么。一如既往,感谢您的阅读!

查看michaelphi.com了解更多类似的内容。

✍🏽想要更多内容?查看我的博客https://www.michaelphi.com

📺喜欢看基于项目的视频?来看看我的 Youtube

🥇注册我的 电子邮件简讯 ,了解最新的文章和视频!

递归神经网络图解指南

原文:https://towardsdatascience.com/illustrated-guide-to-recurrent-neural-networks-79e5eb8049c9?source=collection_archive---------0-----------------------

理解直觉

嗨,欢迎来到循环神经网络图解指南。我是迈克尔,也被称为学习矢量。我是人工智能语音助手领域的机器学习工程师。如果你刚刚开始学习 ML,并且想获得递归神经网络背后的一些直觉,这篇文章是为你准备的。

如果你愿意,你也可以观看这篇文章的视频版本。

如果你想进入机器学习,递归神经网络是一种强大的技术,理解这一点很重要。如果你使用智能手机或经常上网,奇怪的是你已经使用了利用 RNN 的应用程序。递归神经网络用于语音识别、语言翻译、股票预测;它甚至被用于图像识别来描述图片中的内容。

所以我知道有很多关于循环神经网络的指南,但我想分享一些插图和解释,关于我是如何理解它的。我将避免所有的数学,而是专注于 RNNs 背后的直觉。在这篇文章结束时,你应该对 RNN 有了很好的理解,并希望有一个灯泡的时刻。

序列数据

好的,RNN 的神经网络擅长对序列数据建模。为了理解这意味着什么,让我们做一个思维实验。假设你拍了一张球随时间运动的静态快照。

假设你想预测球的运动方向。那么,只有你在屏幕上看到的信息,你会怎么做呢?好吧,你可以猜一猜,但是你能想到的任何答案都是,一个随机的猜测。如果不知道球去了哪里,你就没有足够的数据来预测它要去哪里。

如果你连续记录球的位置的许多快照,你将有足够的信息来做出更好的预测。

所以这是一个序列,一个事物跟随另一个事物的特殊顺序。有了这些信息,你现在可以看到球正在向右移动。

序列数据有多种形式。音频是一个自然的序列。你可以把一个音频声谱图分割成块,然后输入 RNN 的大脑。

Audio spectrogram chopped into chunks

文本是序列的另一种形式。您可以将文本分成一系列字符或一系列单词。

顺序记忆

好的,RNN 擅长处理序列数据进行预测。但是怎么做呢??

他们通过一个我称之为顺序记忆的概念做到了这一点。为了更好地理解顺序记忆的含义…

我想邀请你说出你脑中的字母表。

那很简单,对吧。如果你被教导这个特定的顺序,它应该很快就会出现在你面前。

现在试着倒着说字母表。

我打赌这要困难得多。除非你以前练习过这个特定的顺序,否则你可能会有一段艰难的时间。

这里有一个有趣的,从字母 f 开始。

起初,你会纠结于前几个字母,但当你的大脑掌握了这个模式后,剩下的就会自然而然了。

所以这很难做到是有逻辑原因的。你按顺序学习字母表。顺序记忆是一种让你的大脑更容易识别顺序模式的机制。

递归神经网络

好的,RNN 有顺序记忆的抽象概念,但是 RNN 是怎么复制这个概念的呢?让我们来看看传统的神经网络,也称为前馈神经网络。它有输入层、隐藏层和输出层。

Feed Forward Neural Network

我们如何让一个前馈神经网络能够利用以前的信息来影响以后的信息?如果我们在神经网络中添加一个可以向前传递先验信息的回路会怎么样?

Recurrent Neural Network

这就是递归神经网络的本质。RNN 有一个循环机制,充当高速公路,允许信息从一个步骤流向下一个步骤。

Passing Hidden State to next time step

这个信息是隐藏状态,它是先前输入的表示。让我们通过一个 RNN 用例来更好地理解它是如何工作的。

假设我们想要建立一个聊天机器人。它们现在很受欢迎。假设聊天机器人可以从用户输入的文本中对意图进行分类。

Classifying intents from users inputs

来解决这个问题。首先,我们将使用 RNN 对文本序列进行编码。然后,我们将把 RNN 的输出输入一个前馈神经网络,这个网络将对意图进行分类。

好的,那么一个用户输入… 现在是几点? 。首先,我们把句子分解成单个的单词。RNN 的作品是按顺序排列的,所以我们一次输入一个单词。

Breaking up a sentence into word sequences

第一步是将“什么”输入 RNN。RNN 对“什么”进行编码并产生输出。

对于下一步,我们输入单词“时间”和上一步的隐藏状态。RNN 现在有了关于“什么”和“时间”的信息

我们重复这个过程,直到最后一步。你可以看到,在最后一步,RNN 已经对前面步骤中所有单词的信息进行了编码。

因为最终输出是从序列的其余部分创建的,所以我们应该能够获得最终输出,并将其传递给前馈层以对意图进行分类。

对于那些喜欢看代码的人来说,这里有一些 python 展示了控制流。

Pseudo code for RNN control flow

首先,初始化网络层和初始隐藏状态。隐藏状态的形状和维度将取决于你的递归神经网络的形状和维度。然后循环输入,将单词和隐藏状态传递给 RNN。RNN 返回输出和修改后的隐藏状态。你继续循环,直到你没有词了。最后,将输出传递给前馈层,它会返回一个预测。就是这样!递归神经网络正向传递的控制流是 for 循环。

消失渐变

你可能已经注意到隐藏状态中奇怪的颜色分布。这说明了 RNN 所谓的短期记忆的问题。

Final hidden state of the RNN

短期记忆是由臭名昭著的消失梯度问题引起的,这在其他神经网络架构中也很普遍。随着 RNN 处理更多的步骤,它很难保留以前步骤的信息。如你所见,来自单词“什么”和“时间”的信息在最后的时间步几乎不存在。短期记忆和消失梯度是由于反向传播的性质;一种用于训练和优化神经网络的算法。为了理解这是为什么,让我们看看反向传播对深度前馈神经网络的影响。

训练神经网络有三个主要步骤。首先,它向前传递并进行预测。其次,它使用损失函数将预测与地面实况进行比较。损失函数输出一个误差值,该误差值是对网络性能有多差的估计。最后,它使用该误差值进行反向传播,计算网络中每个节点的梯度。

梯度是用于调整网络内部权重的值,允许网络学习。梯度越大,调整越大,反之亦然。这就是问题所在。当进行反向传播时,一个层中的每个节点计算它的梯度相对于它之前的层中的梯度的效果。因此,如果对之前图层的调整很小,那么对当前图层的调整会更小。

这导致梯度向下反向传播时呈指数级收缩。早期的层无法进行任何学习,因为内部权重由于极小的梯度而几乎没有被调整。这就是消失梯度问题。

Gradients shrink as it back-propagates down

让我们看看这是如何应用于递归神经网络的。您可以将递归神经网络中的每个时间步视为一层。为了训练一个递归神经网络,可以使用一种称为时间反向传播的反向传播应用程序。随着梯度值在每个时间步长中传播,梯度值将按指数规律收缩。

Gradients shrink as it back-propagates through time

再次,梯度用于调整神经网络的权重,从而允许它学习。小梯度意味着小调整。这导致早期层不学习。

由于渐变消失,RNN 不会学习跨时间步长的长程相关性。这意味着当试图预测用户的意图时,有可能不考虑单词“什么”和“时间”。然后,网络必须用“是吗?”做出最好的猜测。这相当模糊,即使对人类来说也很困难。所以不能学习更早的时间步骤会导致网络有短期记忆。

LSTM 和 GRU 的

好了,RNN 氏症患者患有短期记忆障碍,我们该如何克服呢?为了减轻短期记忆,创建了两个专门的递归神经网络。一种叫做长短期记忆,简称 LSTM 氏症。另一种是门控循环单元或 GRU 氏症。LSTM 和 GRU 的功能本质上和 RNN 的一样,但是他们能够使用被称为“门”的机制来学习长期的依赖性这些门是不同的张量运算,可以学习向隐藏状态添加或删除什么信息。因为这种能力,短期记忆对他们来说不是问题。如果你想了解更多关于 LSTM 和 GRU 的情况,你可以看看我关于他们的帖子。

[## LSTM 和 GRU 的图解指南:一步一步的解释

嗨,欢迎来到 LSTM 和 GRU 的图解指南。我是迈克尔,我是人工智能领域的机器学习工程师…

towardsdatascience.com](/illustrated-guide-to-lstms-and-gru-s-a-step-by-step-explanation-44e9eb85bf21)

那还不算太糟

综上所述,RNN 氏综合症对于处理序列数据进行预测是很好的,但是会受到短期记忆的影响。香草 RNN 氏症的短期记忆问题并不意味着完全跳过它们,使用更进化的版本,如 LSTM 或 GRU 氏症。RNN 的优势在于训练速度更快,使用的计算资源更少。这是因为需要计算的张量运算较少。当你期望对具有长期相关性的较长序列建模时,你应该使用 LSTM 或 GRU 的方法。

如果你有兴趣深入了解,这里有一些解释 RNN 氏症及其变体的链接。

[## 任何人都可以学习用 Python 编写 LSTM-RNN 代码(第 1 部分:RNN)——我是特拉斯克

机器学习技术博客。

iamtrask.github.io](https://iamtrask.github.io/2015/11/15/anyone-can-code-lstm/) [## 了解 LSTM 网络——colah 的博客

这些循环使得循环神经网络看起来有点神秘。然而,如果你想得更多一点,事实证明…

colah.github.io](https://colah.github.io/posts/2015-08-Understanding-LSTMs/)

我写这篇文章很开心,所以请在评论中告诉我这是否有帮助,或者你想在下一篇文章中看到什么。感谢阅读!

查看michaelphi.com了解更多类似的内容。

✍🏽想要更多内容?在 https://www.michaelphi.com 查看我的博客

📺喜欢看基于项目的视频?看看我的 Youtube

🥇注册我的 电子邮件简讯 ,了解最新文章和视频!

我是一名数据科学家,我为什么要使用云?

原文:https://towardsdatascience.com/im-a-data-scientist-why-should-i-use-the-cloud-b896ded55bb9?source=collection_archive---------1-----------------------

人们通常认为云只是一种租赁电脑的服务,由像 AWS (亚马逊网络服务)或 GCP (谷歌云平台)这样的公司提供。有人让我用他们的电脑,而不是我自己的?那又怎样!?!我的机器拥有我构建和开发机器学习算法所需的所有能力,我为什么要使用云呢?让我来解释一下云是如何让你的生活变得更加轻松的。

如果你想尝试一些新的、令人惊叹的开源技术(例如 Apache Spark ),但不知道在你的机器上设置它时从哪里开始,该怎么办?为什么不直接让云提供商给你一台已经预装了这个的机器(例如 AWS EMRGCP DataProc )?简单。

另一个场景可能是您有一个在本地运行的数据库(即不在云中)。您不断遇到升级问题(永远无法完成)、查询永远无法返回任何数据,以及存储空间耗尽的持续威胁。一种选择是继续打这场败仗,花掉你(和你的数据/软件工程师)所有的时间试图阻止数据库在任何时候冻结。为什么不直接让云提供商立即让你访问一个数据库(运行在完全由他们管理的机器上),这个数据库可以处理你扔给它的所有数据,而不会增加查询返回的时间(例如 AWS DynamoDBGCP BigQuery )?简单。

也许您想定期运行一个流程,比如每日报告。在本地,您需要在一台机器上安装一个应用程序,该应用程序将触发每个进程在正确的时间运行。您选择的机器现在是单点故障。它会崩溃,需要更新,会变旧,你会错误地运行一个耗尽所有计算资源的应用程序。为什么不直接让云提供商 100%保证地管理时间表呢?如果出现错误,他们甚至会重试单个流程(例如,如果您的每日报告流程在完成前崩溃),或者在重试 3 次后创建一个失败通知系统(例如, AWS 数据管道)。太美了。

你刚刚构建了一个惊人的数据科学算法。您已经将代码包装在一个 Docker 容器中,现在想要部署它。将它托管在单台机器上意味着您将会遇到上一段提到的单点故障噩梦。当需求增加时,您也无法轻松扩展。您的另一个选择是创建一些集群架构,将您的机器变成一个计算实体。如果一台机器停机,没问题,您的模型将自动移动到集群的不同部分。试图设置这将是一个非常痛苦和缓慢的练习。为什么不要求云提供商立即创建一个集群来托管你的模型(例如 AWS EC2 容器服务GCP 容器引擎)?太神奇了。

在云中工作的便利性是无与伦比的。它甚至真的很棒。云提供商现在提供一种叫做无服务器计算的服务(例如 AWS LambdaGCP 云功能)。它让您无需供应或管理任何服务器就可以运行代码。您只需提供要运行的代码,仅此而已。它仅在需要时执行您的代码,并自动伸缩。改变游戏规则。

所以云很神奇,一定很贵。事实恰恰相反。首先,AWS 和 GCP(举例来说)都提供广泛的自由层。越来越多的云提供商之间的竞争也保持了低价。但最重要的是,它是随用随付。您只需为您的云数据库中的数据量或您使用的计算能力付费。没有必要过度购买你可能一天只使用 8 小时的昂贵硬件。您可以在云中快速轻松地扩展,无需前期成本。你还能要求什么?

云让你的生活更轻松。作为一名数据科学家,您的目标是使用最先进的技术运行最佳算法,最可靠,所需维护最少,使用所有可用数据,尽可能缩短设置时间,只为您使用的数据付费,并且能够在需要时快速轻松地扩展。云让你到达那里,而本地工作却不能。结案了。

IMA 杂志时代

原文:https://towardsdatascience.com/ima-mag-age-7bc81399b0a6?source=collection_archive---------6-----------------------

吴恩达卷积神经网络课程回顾

通过这篇文章,我将尝试诚实地回顾我在 Coursera 上学习的最新课程:吴恩达的“卷积神经网络”。

我第一次跟随来自吴恩达的“机器学习课程是在 2014 年。我真的很喜欢他的授课速度,以及他积累知识让你跟上进度的方式。因此,当他关于深度学习的新纳米学位在今年 8 月发布时,我是第一批加入的人之一,我很快完成了三门课程。几周前,五门课程中的第四门课程发布了。我立即上了“卷积神经网络”课程,继续我的旅程。

正如预期的那样,该课程结构合理,进度恰当。内容分为四周。第一周建立卷积神经网络(CNN)的基础,并解释这些卷积是如何计算的,机制。它解释了它在计算机视觉中的基础,然后将详细说明与填充、步幅和池层(最大池、平均池)的卷积。

第二周着眼于几个“经典”的 CNN,并解释如何通过在已有概念的基础上添加新的概念来构建架构。然后,它继续解释 ResNets(这个概念可以应用于其他网络,而不仅仅是 CNN),然后建立盗梦空间网络(是的,盗梦空间就像电影中一样)

第三周介绍了两个新的实用概念,目标定位和目标检测。计算出一个物体在照片中的位置,其次,我们可以在照片中检测到多少个物体,以及它们各自的位置。它很好地展示了如何使用锚定框来预测和评估边界框。

最后,在第四周你会学到一些关于 CNN 最酷最有趣的事情:人脸识别和神经类型转移。这里介绍了一些重要的概念,如一次性学习(这也适用于 CNN 以外的其他网络)和连体网络。

总而言之,这是一门很好的课程。一路上有些小故障。一些视频没有尽可能地完美,即一些“漏洞”需要删除,幻灯片上有一些错误需要纠正,但非常轻微。我最大的不满是关于编程作业。首先,它们不是独立的。他们从一开始就提到了在纳米学位第二个课程的第三周对 Tensorflow 的介绍:“改进深度神经网络”。当你每天不使用 Tensorflow(通常我对 Keras 没问题)并且课程之间有 2-3 个月的间隔时,这就有点尴尬了…

第二,与纳米学位的其他课程相比,作业的指导性稍差,也就是说,你将需要花更多的时间来解决编程中的小问题,而这些问题不像以前的课程那样需要大量的手工处理。这与其说是一个问题,不如说是一个声明,然而,当它与有问题的 Coursera 作业提交引擎结合起来时,就成了一个问题(嗯,老实说,我不知道这是 Coursera 的错还是课程的错,但结果是一样的)。有时,它会拒绝正确地给你的作业评分,甚至不会给你错误的东西评分,或者会引入人为的界限,而不告诉你这些界限已经存在……我希望这些问题能尽快得到解决,因为它不会阻止像我这样的早期采用者,但很可能会阻止未来出现更多的人。

最后,网站上使用的 jupyter 内核很麻烦。服务器可用性有时似乎很粗略。即使保存了您的工作,也经常会丢失(您应该定期保存/导出到您的本地机器以缓解这些问题)。简而言之,距离 Kaggle 内核的处理还有很长的路要走。我的一个同事在参加另一个 Coursera 课程后也报告了同样的问题,所以这不是 CNN 课程独有的。此外,由于 Coursera 的访问现在是基于订阅的,如果您在课程结束后不续订,您将无法访问您的内核。因此,如果你不想丢失你的作品(因为它和课程视频一样具有参考价值),你必须将它们存储在你的本地机器或首选云存储中。

尽管如此,这是一门很好的课程,教会了我很多我以前不知道的东西,所以总共 4/5!但是要做好准备,尤其是在编程作业中。我特别喜欢一次性学习,我打算将它应用于我工作中的一个深层神经网络问题(与 CNN 无关)和神经类型转移。在最后一个编程练习中,您完成了一个神经类型转换算法代码。在我的好朋友 Marc-Olivier 的推动下,我更进一步,实现了一个多风格的传输算法。这些是我最小的孩子,他们从爱德华·蒙克巴勃罗·毕加索文森特·梵高乔治·布拉克都有不同程度的风格转变。

My youngest kids with style transferred left to right, top to bottom: Edvard Munch, Pablo Picasso, Vincent Van Gogh and Georges Braques.

本网站上的帖子是我个人的,不一定代表爱立信的立场、策略或观点。

自定义图像增强

原文:https://towardsdatascience.com/image-augmentation-14a0aafd0498?source=collection_archive---------4-----------------------

图象生成

图像增强

图像增强是一种技术,用于人为扩展数据集。当我们得到一个只有很少数据样本的数据集时,这是很有帮助的。在深度学习的情况下,这种情况很糟糕,因为当我们在有限数量的数据样本上训练它时,模型往往会过度拟合。

通常用于增加数据样本计数的图像增强参数是缩放、剪切、旋转、预处理 _ 函数等。这些参数的使用导致在深度学习模型的训练期间生成具有这些属性的图像。使用图像增强生成的图像样本通常会导致现有数据样本集增加近 3 到 4 倍。

在 Keras 中,我们借助一个名为 ImageDataGenerator 的函数来实现图像增强。函数定义的基本概要如下:

Function to Initialize Data Augmentation Parameters

自定义图像增强

自定义图像增强我们可能希望在 Keras 中为 ImageDataGenerator 定义我们自己的预处理参数,以便使它成为一个更强大的图像生成 API。我们可以通过更改 Keras image.py 文件来实现这一点。

为了便于理解,最好创建 image.py 的副本,并在副本中进行更改。这是在运行于 Anaconda 环境的 Windows 机器上通过以下步骤实现的:

Steps to Create Custom Image Augmentation File — image_dev.py

现在,按照以下步骤添加您希望在 ImageDataGenerator 中看到的自定义参数:

实验结果

Augmented Images Obtained Using - datagen_1

Augmented Images Obtained Using — datagen_2

源代码

[## shree 6791/深度学习

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

github.com](https://github.com/shree6791/Deep-Learning/tree/master/CNN/Cats and Dogs/keras/src)

Python 中的图像增强示例

原文:https://towardsdatascience.com/image-augmentation-examples-in-python-d552c26f2873?source=collection_archive---------4-----------------------

我目前正在进行一项研究,审查图像数据增强的深度和有效性。这项研究的目标是了解如何增加我们的数据集大小,以训练具有有限或少量数据的稳健卷积网络模型。

这项研究需要列出我们能想到的所有图像增强,并列举所有这些组合,以尝试和提高图像分类模型的性能。想到的一些最简单的增强是翻转、平移、旋转、缩放、隔离单独的 r、g、b 颜色通道和添加噪声。更令人兴奋的扩展集中在使用生成对抗网络模型,有时用遗传算法交换生成网络。还提出了一些创造性的方法,例如对图像应用 Instagram 风格的照明过滤器,应用随机区域锐化过滤器,以及基于聚类技术添加平均图像。本文将向您展示如何使用 NumPy 对图像进行放大。

以下是一些增强技术的列表和说明,如果您能想到任何其他方法来增强图像,以提高图像分类器的质量,请留下评论。

Original Image, (Pre-Augmentation)

增加

所有的扩充都是在没有 OpenCV 库的情况下使用 Numpy 完成的

# Image Loading Code used for these examples
from PIL import Image
import numpy as np
import matplotlib.pyplot as pltimg = Image.open('./NIKE.png')
img = np.array(img)
plt.imshow(img)
plt.show()

轻弹

翻转图像是最流行的图像数据增强方法之一。这主要是由于翻转代码的简单性,以及对于大多数问题来说,翻转图像将为模型增加价值是多么直观。下面的模型可以被认为是看到了一只左脚的鞋子而不是右脚的鞋子,因此,随着数据的增加,该模型对于看到鞋子的潜在变化变得更加稳健。

# Flipping images with Numpy
flipped_img = np.fliplr(img)
plt.imshow(flipped_img)
plt.show()

翻译

很容易想象以检测为目的的分类器的翻译增强的价值。好像这个分类模型试图检测鞋子何时在图像中,何时不在图像中。这些平移将帮助它拾取鞋子,而不用在框架中看到整个鞋子。

# Shifting Left
for i in range(HEIGHT, 1, -1):
  for j in range(WIDTH):
     if (i < HEIGHT-20):
       img[j][i] = img[j][i-20]
     elif (i < HEIGHT-1):
       img[j][i] = 0plt.imshow(img)
plt.show()

# Shifting Right
for j in range(WIDTH):
  for i in range(HEIGHT):
    if (i < HEIGHT-20):
      img[j][i] = img[j][i+20]plt.imshow(img)
plt.show()

# Shifting Up
for j in range(WIDTH):
  for i in range(HEIGHT):
    if (j < WIDTH - 20 and j > 20):
      img[j][i] = img[j+20][i]
    else:
      img[j][i] = 0plt.imshow(img)
plt.show()

#Shifting Down
for j in range(WIDTH, 1, -1):
  for i in range(278):
    if (j < 144 and j > 20):
      img[j][i] = img[j-20][i]plt.imshow(img)
plt.show()

噪音

噪声是一种有趣的增强技术,我开始越来越熟悉它。我看过很多关于对抗性训练的有趣论文,在这些论文中,你可以向一幅图像中加入一些噪声,结果模型将无法对其进行正确分类。我仍然在寻找产生比下图更好的噪音的方法。添加噪波可能有助于消除光照失真,并使模型总体上更加健壮。

# ADDING NOISE
noise = np.random.randint(5, size = (164, 278, 4), dtype = 'uint8')

for i in range(WIDTH):
    for j in range(HEIGHT):
        for k in range(DEPTH):
            if (img[i][j][k] != 255):
                img[i][j][k] += noise[i][j][k]
plt.imshow(img)
plt.show()

甘斯:

我对使用生成性对抗网络进行数据增强的研究产生了浓厚的兴趣,下面是我使用 MNIST 数据集制作的一些图像。

从上面的图像中我们可以看出,它们看起来确实像 3、7 和 9。我目前在扩展网络架构以支持运动鞋的 300x300x3 尺寸输出(相比于 28x28x1 MNIST 数字)时遇到了一些问题。然而,我对这项研究感到非常兴奋,并期待着继续下去!

感谢您阅读本文,希望您现在知道如何实现基本的数据扩充来改进您的分类模型!

用于深度学习的图像增强

原文:https://towardsdatascience.com/image-augmentation-for-deep-learning-histogram-equalization-a71387f609b2?source=collection_archive---------2-----------------------

深度网络需要大量的训练数据来实现良好的性能。为了使用非常少的训练数据建立强大的图像分类器,通常需要图像增强来提高深度网络的性能。图像增强通过不同的处理方式或多种处理方式的组合,如随机旋转、平移、剪切、翻转等,人工创建训练图像。

图像数据发生器

使用 Keras 中的 ImageDataGenerator API 可以轻松创建一个增强图像生成器。ImageDataGenerator通过实时数据增强生成批量图像数据。创建和配置ImageDataGenerator以及用增强图像训练深度神经网络的最基本代码如下。

datagen = ImageDataGenerator()
datagen.fit(train)
X_batch, y_batch = datagen.flow(X_train, y_train, batch_size=batch_size)
model.fit_generator(datagen, samples_per_epoch=len(train), epochs=epochs)

我们可以用下面的代码来创建具有所需属性的增强图像。在我们的例子中,下面的数据生成器生成一批 9 个增强图像,旋转 30 度,水平移动 0.5。

datagen = ImageDataGenerator(rotation_range=30, horizontal_flip=0.5)
datagen.fit(img)i=0
for img_batch in datagen.flow(img, batch_size=9):
    for img in img_batch:
        plt.subplot(330 + 1 + i)
        plt.imshow(img)
        i=i+1    
    if i >= batch_size:
        break

Original Image and Augmented Images

直方图均衡

除了 Keras 中的ImageDataGenerator类提供的标准数据扩充技术,我们还可以使用自定义函数来生成扩充图像。例如,您可能想要使用对比度拉伸来调整图像的对比度。对比度拉伸是一种简单的图像处理技术,通过将图像的亮度值范围重新缩放(“拉伸”)到所需的值范围来增强对比度。

直方图均衡是另一种图像处理技术,使用图像强度直方图增加图像的整体对比度。均衡图像具有线性累积分布函数。这种方法不需要参数,但有时会产生看起来不自然的图像。

另一种方法是自适应直方图均衡化 (AHE),它通过计算对应于图像不同部分的几个直方图来提高图像的局部对比度(不同于仅使用一个直方图来调整全局对比度的普通直方图均衡化),并将它们用于局部对比度调整。然而,AHE 倾向于过度放大图像中相对均匀区域的噪声。

对比度受限的自适应直方图均衡 (CLAHE)是为了防止 AHE 导致的噪声过度放大而开发的。简言之,它通过在计算累积分布函数之前将直方图限幅在预定值来限制 AHE 的对比度增强。

为了在 Keras 中实现用于增强的定制预处理函数,我们首先定义我们的定制函数,并将其作为参数传递给ImageDataGenerator。例如,我们可以使用下面的代码实现 AHE。

def AHE(img):
    img_adapteq = exposure.equalize_adapthist(img, clip_limit=0.03)
    return img_adapteqdatagen = ImageDataGenerator(rotation_range=30, horizontal_flip=0.5, preprocessing_function=AHE)

Augmented Images using Contrast Stretching (left), Histogram Equalization (middle) and Adaptive Histogram Equalization (right)

源代码

参考

基于 Keras 和直方图均衡的深度学习图像增强

原文:https://towardsdatascience.com/image-augmentation-for-deep-learning-using-keras-and-histogram-equalization-9329f6ae5085?source=collection_archive---------0-----------------------

在本帖中,我们将回顾:

  • 图像增强:它是什么?为什么重要?
  • Keras:如何使用它进行基本的图像增强。
  • 直方图均衡化:它是什么?怎么有用?
  • 实现直方图均衡化技术:修改 keras .预处理 image.py 文件的一种方法。

图像增强:它是什么?为什么重要?

深度神经网络,尤其是卷积神经网络(CNN),尤其擅长图像分类任务。最先进的 CNN 甚至被证明在图像识别方面超过了人类的表现。

https://www.eff.org/ai/metrics

然而,正如我们从杨健先生在热门电视节目【硅谷】(该应用程序现已在 app store 上提供)中的“热狗,不是热狗”食物识别应用中了解到的那样,收集图像作为训练数据既昂贵又耗时。

如果你不熟悉电视节目《硅谷》,请注意以下视频中的语言是 NSFW 语:

为了对抗收集成千上万训练图像的高费用,已经开发了图像增强,以便从现有数据集生成训练数据。图像增强是获取已经在训练数据集中的图像并操纵它们以创建同一图像的许多改变版本的过程。这不仅提供了更多的图像进行训练,而且还可以帮助我们的分类器暴露在更广泛的光照和颜色情况下,从而使我们的分类器更加鲁棒。下面是一些来自 imgaug 库的不同扩充的例子。

https://github.com/aleju/imgaug

使用 Keras 进行基本图像增强

有许多方法可以对图像进行预处理。在这篇文章中,我们将回顾一些最常见的开箱即用的方法,这些方法是 keras 深度学习库为增强图像提供的,然后我们将展示如何改变keras . preprocessing image . py文件,以便启用直方图均衡化方法。我们将使用 keras 附带的 cifar10 数据集。然而,我们将只使用来自数据集中的猫和狗的图像,以便保持任务足够小,可以在 CPU 上执行——如果您想继续的话。你可以从这篇文章中查看 IPython 笔记本的源代码。

加载和格式化数据

我们要做的第一件事是加载 cifar10 数据集并格式化图像,以便为 CNN 做准备。我们还将浏览一些图片,以确保数据已经正确加载。

cifar10 图像只有 32 x 32 像素,因此在这里放大时看起来有颗粒,但 CNN 不知道它有颗粒,它看到的只是数据。

从 ImageDataGenerator()创建图像生成器

用 keras 增加我们的图像数据非常简单。杰森·布朗利在这方面提供了很棒的教程。首先,我们需要通过调用ImageDataGenerator()函数创建一个图像生成器,并向它传递一个参数列表,描述我们希望它对图像执行的更改。然后,我们将调用图像生成器上的fit()函数,它将把更改一批一批地应用到图像上。默认情况下,修改将被随机应用,所以不是每个图像每次都会改变。您还可以使用keras.preprocessing将增强的图像文件导出到一个文件夹中,以便建立一个巨大的修改图像数据集。

我们将在这里看一些视觉上更有趣的增强。所有可能的ImageDataGenerator()参数的描述以及keras.preprocessing中可用的其他方法列表可在 keras 文档中找到。

随机旋转图像

垂直翻转图像

水平翻转图像也是为分类器生成更多数据的经典方法之一。这很容易做到,并且可能对这个数据集更有意义,但是,我已经省略了代码和图像,因为在没有看到原始图像的情况下,没有办法知道狗或猫的图像是否被水平翻转。

将图像垂直或水平移动 20%

直方图均衡技术

直方图均衡化是采用低对比度图像并增加图像相对高点和低点之间的对比度的过程,以便带出阴影中的细微差异并创建更高对比度的图像。结果可能是惊人的,尤其是对于灰度图像。以下是一些例子:

https://www.bruzed.com/2009/10/contrast-stretching-and-histogram-equalization/

http://www-classes.usc.edu/engr/ee-s/569/qa2/Histogram%20Equalization.htm

https://studentathome.wordpress.com/2013/03/27/local-histogram-equalization/

在本帖中,我们将探讨三种提高图像对比度的图像增强技术。这些方法有时也被称为“直方图拉伸”,因为它们采用像素强度的分布,并拉伸该分布以适应更大范围的值,从而增加图像最亮和最暗部分之间的对比度。

直方图均衡

直方图均衡化通过检测图像中像素密度的分布并将这些像素密度绘制在直方图上来增加图像的对比度。然后分析该直方图的分布,如果存在当前未被利用的像素亮度范围,则直方图被“拉伸”以覆盖这些范围,然后被“反向投影到图像上以增加图像的整体对比度。

对比度扩展

对比度拉伸采用的方法是分析图像中像素密度的分布,然后“重新缩放图像,以包含第二和第 98 个百分点内的所有强度。”

自适应均衡

自适应均衡不同于常规直方图均衡,因为计算了几个不同的直方图,每个直方图对应于图像的不同部分;然而,它有在其他不感兴趣的部分过度放大噪声的趋势。

以下代码来自于 sci-kit image library 的 docs,并已被修改以在我们的 cifar10 数据集的第一个图像上执行上述三个增强。首先,我们将从 sci-kit image (skimage)库中导入必要的模块,然后修改来自 sci-kit image 文档的代码,以查看数据集的第一个图像的增强。

以下是来自 cifar10 数据集的低对比度猫的修改图像。如您所见,结果不如低对比度灰度图像那样引人注目,但仍有助于提高图像质量。

修改 keras .预处理以启用直方图均衡化技术。

既然我们已经成功地修改了来自 cifar10 数据集的一幅图像,我们将演示如何修改 keras.preprocessing image.py 文件,以便执行这些不同的直方图修改技术,就像我们使用ImageDataGenerator()对现成的 keras 增强所做的那样。为了实现这一功能,我们将遵循以下一般步骤:

概观

  • 在您自己的机器上找到 keras.preprocessing image.py 文件。
  • 将 image.py 文件复制到您的文件或笔记本中。
  • 将每个均衡技术的一个属性添加到 DataImageGenerator() init 函数中。
  • 将 IF 语句子句添加到 random_transform 方法中,以便在我们调用datagen.fit()时实现扩充。

对 keras.preprocessing 的image.py文件进行修改的最简单的方法之一就是简单地将其内容复制并粘贴到我们的代码中。这将消除导入它的需要。你可以在这里查看 github image.py文件的内容。然而,为了确保你抓取的文件版本与你之前导入的文件版本相同,最好抓取你机器上已经存在的image.py文件。运行print(keras.__file__)将打印出机器上 keras 库的路径。该路径(对于 mac 用户)可能类似于:

/usr/local/lib/python3.5/dist-packages/keras/__init__.pyc

这为我们提供了本地机器上 keras 的路径。继续导航到那里,然后进入preprocessing文件夹。在preprocessing里面你会看到image.py文件。然后,您可以将其内容复制到您的代码中。这个文件很长,但是对于初学者来说,这可能是对它进行修改的最简单的方法之一。

编辑image.py

在 image.py 的顶部,你可以注释掉这一行:from ..import backend as K,如果你已经在上面包含了它。

此时,还要仔细检查以确保您导入了必要的 scikit-image 模块,以便复制的image.py可以看到它们。

from skimage import data, img_as_float
from skimage import exposure

我们现在需要在 ImageDataGenerator 类的__init__ 方法中添加六行代码,这样它就有三个属性来表示我们将要添加的增强类型。下面的代码是从我当前的 image.py 复制过来的,旁边有#####的那几行是我添加的。

random_transform()函数(如下)响应我们传递给ImageDataGenerator()函数的参数。如果我们已经将contrast_stretchingadaptive_equalizationhistogram_equalization参数设置为True,当我们调用ImageDataGenerator()(就像我们对其他图像增强所做的那样)random_transform()将应用所需的图像增强。

现在我们已经有了所有必要的代码,可以调用 ImageDataGenerator()来执行直方图修改技术。如果我们将这三个值都设置为True,下面是一些图像的样子。

对于任何给定的数据集,我不建议将它们中的一个以上设置为True。请确保使用您的特定数据集进行实验,以了解哪些内容有助于提高分类器的准确性。对于彩色图像,我发现对比度拉伸通常比直方图修改或自适应均衡获得更好的结果。

训练和验证你的 Keras CNN

最后一步是训练我们的 CNN,并使用model.fit_generator()验证模型,以便在增强图像上训练和验证我们的神经网络。

深度学习中的图像字幕

原文:https://towardsdatascience.com/image-captioning-in-deep-learning-9cd23fb4d8d2?source=collection_archive---------2-----------------------

什么是图像字幕?

图像字幕是生成图像文字描述的过程。它同时使用了自然语言处理计算机视觉来生成字幕。

Image Captioning

数据集将采用[ 图像标题的形式。数据集由输入图像及其相应的输出标题组成。

网络拓扑

编码器

卷积神经网络(CNN)可以被认为是一个编码器。输入图像交给 CNN 提取特征。CNN 的最后一个隐藏状态连接到解码器。

解码器

解码器是一个递归神经网络(RNN ),它在单词级别进行语言建模。第一时间步接收编码器的编码输出和矢量。

培训

CNN(编码器)最后一个隐藏状态的输出被提供给解码器的第一个时间步长。我们设置 x1 = <开始> 向量和期望的标号 y1 = 序列中的第一个字。类似地,我们设置第一个单词的 x2 = 单词向量,并期望网络预测第二个单词。最后,在最后一步, xT = 最后一个字,目标标签yT=token。****

在训练过程中,即使解码器之前出错,也会在每个时间步向解码器提供正确的输入。

测试

****图像表示被提供给解码器的第一时间步。设置 x1 = <开始> 向量,计算第一个字 y1 的分布。我们从分布中抽取一个单词(或者挑选 argmax),将其嵌入向量设为 x2 ,重复这个过程,直到生成 < END > token。

在测试期间,解码器在时间 t 的输出被反馈,并成为解码器在时间 t+1 的输入

数据集

使用 Keras 的图像字幕

原文:https://towardsdatascience.com/image-captioning-with-keras-teaching-computers-to-describe-pictures-c88a46a311b8?source=collection_archive---------0-----------------------

教计算机描述图片

目录:

  1. 介绍
  2. 动机
  3. 先决条件
  4. 数据收集
  5. 理解数据
  6. 数据清理
  7. 加载训练集
  8. 数据预处理—图像
  9. 数据预处理—标题
  10. 使用生成器功能准备数据
  11. 单词嵌入
  12. 模型架构
  13. 推理
  14. 估价
  15. 结论和未来工作
  16. 参考

1。简介

在下图中你看到了什么?

Can you write a caption?

有些人可能会说“草地上的白狗”,有些人可能会说“带褐色斑点的白狗”,还有一些人可能会说“草地上的狗和一些粉红色的花”。

毫无疑问,所有这些说明都与这张图片相关,可能还有其他一些说明。但是我想说的是。对我们人类来说,只是看一眼图片,然后用合适的语言描述它是如此容易。即使是一个 5 岁的孩子也能轻而易举地做到。

但是,你能编写一个将图像作为输入并产生相关标题作为输出的计算机程序吗?

The Problem

就在深度神经网络最近发展之前,这个问题甚至是计算机视觉领域最先进的研究人员都无法想象的。但是随着深度学习的出现,如果我们有了所需的数据集,这个问题就可以很容易地解决。

Andrej Karapathy 在斯坦福大学[1]的博士论文中很好地研究了这个问题,他现在也是特斯拉的 AI 总监。

这篇博客文章的目的是解释(用尽可能简单的话)如何使用深度学习来解决为给定图像生成字幕的问题,因此得名图像字幕。

为了更好地了解这个问题,我强烈建议使用这个由微软创建的最先进的系统,名为 字幕机器人 。只需转到此链接,尝试上传您想要的任何图片;这个系统会为它生成一个标题。

2.动机

我们必须首先理解这个问题对现实世界的场景有多重要。让我们看看这个问题的解决方案非常有用的几个应用。

  • 自动驾驶汽车——自动驾驶是最大的挑战之一,如果我们能够适当地描述汽车周围的场景,它可以促进自动驾驶系统的发展。
  • 帮助盲人——我们可以为盲人创造一种产品,引导他们在没有他人帮助的情况下上路。我们可以先将场景转换成文本,然后将文本转换成声音。两者现在都是深度学习的著名应用。参考这个 链接 ,它展示了 Nvidia research 如何试图创造这样一个产品。
  • 今天,闭路电视摄像头无处不在,但随着观看世界,如果我们也可以生成相关的字幕,那么我们就可以在某个地方发生恶意活动时发出警报。这可能有助于减少一些犯罪和/或事故。
  • 自动字幕可以帮助,使谷歌图片搜索像谷歌搜索一样好,因为然后每个图像可以首先转换成标题,然后可以根据标题进行搜索。

3。先决条件

这篇文章假设读者熟悉基本的深度学习概念,如多层感知器、卷积神经网络、递归神经网络、迁移学习、梯度下降、反向传播、过拟合、概率、文本处理、Python 语法和数据结构、Keras 库等。

4.数据收集

这个问题有很多开源数据集可用,像 Flickr 8k(包含 8k 张图片)、Flickr 30k(包含 30k 张图片)、MS COCO(包含 180k 张图片)等。

但是出于这个案例研究的目的,我使用了 Flickr 8k 数据集,您可以通过填写伊利诺伊大学香槟分校提供的这个 表格 来下载该数据集。此外,用大量图像训练模型在不是非常高端的 PC/膝上型电脑的系统上可能是不可行的。

这个数据集包含 8000 个图像,每个图像有 5 个标题(正如我们在简介部分已经看到的,一个图像可以有多个标题,所有标题同时相关)。

这些图像分为以下两部分:

  • 训练集— 6000 幅图像
  • 开发集— 1000 个图像
  • 测试集— 1000 幅图像

5.理解数据

如果您已经从我提供的链接下载了数据,那么,除了图像之外,您还将获得一些与图像相关的文本文件。其中一个文件是“Flickr8k.token.txt ”,它包含每张图片的名称及其 5 个标题。我们可以这样阅读这个文件:

# Below is the path for the file "Flickr8k.token.txt" on your disk
filename = "/dataset/TextFiles/Flickr8k.token.txt"
file = open(filename, 'r')
doc = file.read()

该文本文件如下所示:

Sample Text File

因此每行包含 #i ,其中 0≤i≤4

即图像的名称、标题号(0 到 4)和实际标题。

现在,我们创建一个名为“descriptions”的字典,它包含图像的名称(没有。jpg 扩展名)作为键,对应图像的 5 个标题的列表作为值。

例如,参考上面的屏幕截图,字典将如下所示:

descriptions['101654506_8eb26cfb60'] = ['A brown and white dog is running through the snow .', 'A dog is running in the snow', 'A dog running through snow .', 'a white and brown dog is running through a snow covered field .', 'The white and brown dog is running over the surface of the snow .']

6.数据清理

当我们处理文本时,我们通常会执行一些基本的清理,如将所有单词小写(否则“hello”和“Hello”将被视为两个独立的单词),删除特殊标记(如“%”、“$”、“#”等)。),删除包含数字的单词(如“hey199”等)。).

以下代码执行这些基本的清理步骤:

Code to perform Data Cleaning

创建在数据集中所有 8000*5(即 40000)个图像标题(语料库)中出现的所有唯一单词的词汇表;

vocabulary = set()
for key in descriptions.keys():
    [vocabulary.update(d.split()) for d in descriptions[key]]
print('Original Vocabulary Size: %d' % len(vocabulary))
Original Vocabulary Size: 8763

这意味着在所有 40000 个图片说明中,我们有 8763 个独特的单词。我们将所有这些说明连同它们的图像名称一起写入一个新文件,即“descriptions . txt”,并将其保存在磁盘上。

然而,如果我们仔细想想,这些词中有许多会出现很少次,比如说 1 次、2 次或 3 次。由于我们正在创建一个预测模型,我们不希望所有的单词都出现在我们的词汇表中,而是更有可能出现或更常见的单词。这有助于模型变得对异常值更加稳健,并减少错误。

因此,我们只考虑那些在整个语料库中至少出现 10 次的单词。这方面的代码如下:

Code to retain only those words which occur at least 10 times in the corpus

所以现在我们的词汇中只有 1651 个独特的单词。然而,我们将附加 0(零填充将在后面解释),因此总字数= 1651+1 =1652(0 的一个索引)。

7.加载训练集

文本文件“Flickr_8k.trainImages.txt”包含属于训练集的图像的名称。所以我们把这些名字加载到一个列表“train”中。

filename = 'dataset/TextFiles/Flickr_8k.trainImages.txt'
doc = load_doc(filename)
train = list()
for line in doc.split('\n'):
    identifier = line.split('.')[0]
    train.append(identifier)
print('Dataset: %d' % len(train))
Dataset: 6000

因此,我们在名为“train”的列表中分离了 6000 个训练图像。

现在,我们从 Python 字典“train_descriptions”中的“descriptions.txt”(保存在硬盘上)加载这些图像的描述。

然而,当我们加载它们时,我们将在每个标题中添加两个标记,如下所示(重要性稍后解释):

startseq ' - >这是一个开始序列标记,将被添加到每个字幕的开头。

endseq ' - >这是一个结束序列标记,将被添加到每个标题的末尾。

8.数据预处理—图像

图像只是我们模型的输入(X)。您可能已经知道,模型的任何输入都必须以向量的形式给出。

我们需要将每张图像转换成固定大小的向量,然后将其作为神经网络的输入。为此,我们通过使用 Google Research 创建的 InceptionV3 模型(卷积神经网络)选择了迁移学习

该模型在 Imagenet 数据集上进行训练,以对 1000 个不同类别的图像执行图像分类。然而,我们在这里的目的不是对图像进行分类,而是获得每幅图像的固定长度的信息向量。这个过程被称为自动特征工程。

因此,我们只是从模型中移除最后一个 softmax 层,并为每个图像提取 2048 长度向量(瓶颈特征),如下所示:

Feature Vector Extraction (Feature Engineering) from InceptionV3

这方面的代码如下:

# Get the InceptionV3 model trained on imagenet data
model = InceptionV3(weights='imagenet')
# Remove the last layer (output softmax layer) from the inception v3
model_new = Model(model.input, model.layers[-2].output)

现在,我们将每个图像传递给该模型,以获得相应的 2048 长度的特征向量,如下所示:

# Convert all the images to size 299x299 as expected by the
# inception v3 model
img = image.load_img(image_path, target_size=(299, 299))
# Convert PIL image to numpy array of 3-dimensions
x = image.img_to_array(img)
# Add one more dimension
x = np.expand_dims(x, axis=0)
# preprocess images using preprocess_input() from inception module
x = preprocess_input(x)
# reshape from (1, 2048) to (2048, )
x = np.reshape(x, x.shape[1])

我们将所有的瓶颈训练特征保存在一个 Python 字典中,并使用 Pickle 文件保存在磁盘上,即“ encoded_train_images.pkl ”,其关键字是图像名,值是对应的 2048 长度特征向量。

注意:如果您没有高端 PC/笔记本电脑,这个过程可能需要一两个小时。

类似地,我们对所有的测试图像进行编码,并将它们保存在文件“ encoded_test_images.pkl ”中。

9.数据预处理—标题

我们必须注意,字幕是我们想要预测的东西。因此在训练期间,字幕将是模型正在学习预测的目标变量(Y)。

但是对给定图像的整个字幕的预测不会立即发生。我们将逐字预测字幕。因此,我们需要将每个单词编码成一个固定大小的向量。然而,这一部分将在我们稍后查看模型设计时看到,但现在我们将创建两个 Python 字典,即“wordtoix”(发音—单词到索引)和“ixtoword”(发音—单词到索引)。

简单地说,我们将用一个整数(索引)来表示词汇表中的每个唯一的单词。如上所述,我们在语料库中有 1652 个唯一的单词,因此每个单词将由 1 到 1652 之间的整数索引来表示。

这两个 Python 字典的用法如下:

wordtoix[' abc ']-->返回单词' ABC '的索引

ixtoword[k] ->返回索引为“k”的单词

使用的代码如下:

ixtoword = {}
wordtoix = {}ix = 1
for w in vocab:
    wordtoix[w] = ix
    ixtoword[ix] = w
    ix += 1

我们还需要计算一个参数,即字幕的最大长度,我们的计算如下:

# convert a dictionary of clean descriptions to a list of descriptions
def to_lines(descriptions):
 all_desc = list()
 for key in descriptions.keys():
  [all_desc.append(d) for d in descriptions[key]]
 return all_desc# calculate the length of the description with the most words
def max_length(descriptions):
 lines = to_lines(descriptions)
 return max(len(d.split()) for d in lines)# determine the maximum sequence length
max_length = max_length(train_descriptions)
print('Max Description Length: %d' % max_length)
Max Description Length: 34

所以任何标题的最大长度是 34。

****10。使用生成器功能准备数据

这是本案例研究中最重要的步骤之一。在这里,我们将了解如何以一种方便的方式准备数据,以作为深度学习模型的输入。

在下文中,我将尝试通过以下示例来解释剩余的步骤:

假设我们有 3 张图片和 3 个相应的标题,如下所示:

(Train image 1) Caption -> The black cat sat on grass

(Train image 2) Caption -> The white cat is walking on road

(Test image) Caption -> The black cat is walking on grass

现在,假设我们使用前两幅图像和它们的标题来训练模型,使用第三幅图像测试我们的模型。

现在将要回答的问题是:我们如何将这一问题框定为监督学习问题?,数据矩阵是什么样子的?我们有多少数据点?等。

首先,我们需要将两个图像转换成它们相应的 2048 长度的特征向量,如上所述。设“图像 _1** ”和“图像 _2 ”分别为前两幅图像的特征向量**

其次,让我们为前两个(train)标题构建词汇表,在这两个标题中添加两个标记“startseq”和“endseq”:(假设我们已经执行了基本的清理步骤)

caption _ 1--> "黑猫坐在草地上"

caption _ 2--> " start seq 白猫走在路上 endseq "

vocab = {black,cat,endseq,grass,is,on,road,sat,startseq,the,walking,white}

让我们给词汇表中的每个单词编个索引:

黑色-1,猫-2,结束序列-3,草-4,是-5,on -6,道路-7,sat -8,开始序列-9,the -10,步行-11,白色-12

现在让我们试着把它框定为一个监督学习问题其中我们有一组数据点 D = {Xi,易},其中 Xi 是数据点‘我’的特征向量,易是相应的目标变量。

让我们取第一个图像向量 Image_1 和它对应的标题“ startseq the 黑猫坐在草地上 endseq ”。回想一下,图像向量是输入,标题是我们需要预测的。但是我们预测标题的方式如下:

第一次,我们提供图像向量和第一个单词作为输入,并尝试预测第二个单词,即:

input = Image _ 1+' start seq ';Output = 'the '

然后,我们提供图像向量和前两个单词作为输入,并尝试预测第三个单词,即:

input = Image _ 1+' start seq the ';输出= '猫'

诸如此类…

因此,我们可以将一幅图像的数据矩阵及其相应的标题总结如下:

Data points corresponding to one image and its caption

必须注意,一个图像+字幕不是单个数据点,而是取决于字幕长度的多个数据点。

类似地,如果我们考虑图像及其标题,我们的数据矩阵将如下所示:

Data Matrix for both the images and captions

我们现在必须明白,在每一个数据点中,不仅仅是图像作为系统的输入,还有部分标题帮助预测序列中的下一个单词。****

由于我们正在处理序列,我们将使用递归神经网络来读取这些部分字幕(稍后将详细介绍)。

然而,我们已经讨论过,我们不会传递标题的实际英文文本,而是传递索引序列,其中每个索引代表一个唯一的单词。

因为我们已经为每个单词创建了一个索引,现在让我们用它们的索引来替换单词,并理解数据矩阵将会是什么样子:

Data matrix after replacing the words by their indices

由于我们将进行批处理(稍后解释),我们需要确保每个序列的长度相等。因此,我们需要在每个序列的末尾添加 0 的(零填充)。但是我们应该在每个序列中添加多少个零呢?

这就是我们计算标题最大长度的原因,它是 34(如果你记得的话)。因此,我们将添加这些数量的零,这将导致每个序列的长度为 34。

数据矩阵将如下所示:

Appending zeros to each sequence to make them all of same length 34

需要数据生成器:

我希望这能给你一个好的感觉,关于我们如何为这个问题准备数据集。然而,这里面有一个很大的陷阱。

在上面的例子中,我只考虑了导致 15 个数据点的 2 个图像和标题。

然而,在我们实际的训练数据集中,我们有 6000 张图片,每张图片有 5 个标题。这使得总共有 30000 张图片和说明文字。

即使我们假设每个字幕平均只有 7 个单词长,也将导致总共 30000*7,即 210000 个数据点。

计算数据矩阵的大小:

Data Matrix

数据矩阵的大小= n*m

其中 n->数据点的数量(假设为 210000)

和 m->每个数据点的长度

显然 m=图像向量的长度(2048) +部分字幕的长度(x)。

m = 2048 + x

但是 x 的值是多少呢?

你可能认为是 34,但是不对,等等,这是错的。

每个单词(或索引)将通过一种单词嵌入技术被映射(嵌入)到更高维度的空间。

稍后,在模型构建阶段,我们将看到使用预训练的手套单词嵌入模型将每个单词/索引映射到 200 长的向量。

现在每个序列包含 34 个索引,其中每个索引是长度为 200 的向量。因此 x = 34*200 = 6800

因此,m = 2048 + 6800 = 8848。

最后,数据矩阵的大小= 210000 * 8848= 1858080000 块。

现在,即使我们假设一个块占用 2 个字节,那么,为了存储这个数据矩阵,我们将需要超过 3 GB 的主存储器。

这是一个相当大的需求,即使我们能够将这么多数据加载到 RAM 中,也会使系统非常慢。

由于这个原因,我们在深度学习中大量使用数据生成器。数据生成器是一种在 Python 中本地实现的功能。Keras API 提供的 ImageDataGenerator 类只不过是 Python 中生成器函数的一个实现。

那么使用生成器函数如何解决这个问题呢?

如果你知道深度学习的基础,那么你必须知道,为了在特定的数据集上训练模型,我们使用一些版本的随机梯度下降(SGD),如 Adam,Rmsprop,Adagrad 等。

使用 SGD ,我们不用计算整个数据集的损失来更新梯度。相反,在每次迭代中,我们计算一批数据点(通常是 64、128、256 等)的损失。)来更新梯度。****

这意味着我们不需要一次将整个数据集存储在内存中。即使我们在内存中有当前的一批点,它也足以满足我们的目的。

Python 中的生成器函数正好用于此目的。它就像一个迭代器,从上次被调用的地方恢复功能。

想了解更多关于发电机的知识,请在这里阅读。****

数据生成器的代码如下:

Code to load data in batches

11。单词嵌入

如上所述,我们将把每个单词(索引)映射到 200 长的向量,为此,我们将使用预先训练的手套模型:

**# Load Glove vectors
glove_dir = 'dataset/glove'
embeddings_index = {} # empty dictionary
f = open(os.path.join(glove_dir, 'glove.6B.200d.txt'), encoding="utf-8")for line in f:
    values = line.split()
    word = values[0]
    coefs = np.asarray(values[1:], dtype='float32')
    embeddings_index[word] = coefs
f.close()**

现在,对于我们词汇表中的所有 1652 个唯一单词,我们创建一个嵌入矩阵,该矩阵将在训练之前加载到模型中。

**embedding_dim = 200# Get 200-dim dense vector for each of the 10000 words in out vocabulary
embedding_matrix = np.zeros((vocab_size, embedding_dim))for word, i in wordtoix.items():
    #if i < max_words:
    embedding_vector = embeddings_index.get(word)
    if embedding_vector is not None:
        # Words not found in the embedding index will be all zeros
        embedding_matrix[i] = embedding_vector**

要了解更多关于单词嵌入的信息,请参考此 链接

12.模型架构

由于输入由两部分组成,一个图像向量和一个部分标题,我们不能使用 Keras 库提供的顺序 API。出于这个原因,我们使用函数式 API 来创建合并模型。

首先,让我们看看包含高级子模块的简要架构:

High level architecture

我们将模型定义如下:

Code to define the Model

让我们来看看模型总结:

Summary of the parameters in the model

下图有助于形象化网络结构,并更好地理解两个输入流:

Flowchart of the architecture

右侧的红色文本是为您提供的注释,用于将您对数据准备的理解映射到模型架构。

LSTM(长短期记忆)层只不过是一个专门的递归神经网络来处理序列输入(在我们的例子中是部分字幕)。要了解更多关于 LSTM 的信息,点击 这里

如果您已经阅读了前面的部分,我认为阅读这些评论应该有助于您以一种直接的方式理解模型架构。

回想一下,我们已经从预训练的手套模型中创建了一个嵌入矩阵,我们需要在开始训练之前将它包含在模型中:

**model.layers[2].set_weights([embedding_matrix])
model.layers[2].trainable = False**

请注意,由于我们使用的是预训练的嵌入层,所以在训练模型之前,我们需要冻结它(可训练=假),这样它就不会在反向传播过程中更新。

最后,我们使用 adam 优化器编译模型

**model.compile(loss=’categorical_crossentropy’, optimizer=’adam’)**

最后,通过反向传播算法更新模型的权重,并且给定图像特征向量和部分字幕,模型将学习输出单词。总而言之,我们有:

Input_1 ->部分字幕

Input_2 ->图像特征向量

Output ->一个适当的单词,在 input_1 中提供的部分字幕序列中的下一个(或者用概率术语我们说以图像向量和部分字幕为条件)

训练期间的高参数:

然后用 0.001 的初始学习率和每批 3 张图片(批量大小)训练该模型 30 个时期。然而,在 20 个时期之后,学习率降低到 0.0001,并且每批在 6 张图片上训练模型。

这通常是有意义的,因为在训练的后期阶段,由于模型正在走向收敛,我们必须降低学习率,以便我们朝着最小值迈出更小的步伐。此外,随着时间的推移增加批量大小有助于您的渐变更新更加强大。

耗时:我在www.paperspace.com上使用了 GPU+ Gradient 笔记本,因此我花了大约一个小时来训练模型。然而,如果你在没有 GPU 的 PC 上训练它,它可能需要 8 到 16 个小时,这取决于你的系统配置。

13.推理

到目前为止,我们已经了解了如何准备数据和构建模型。在本系列的最后一步,我们将了解如何通过传入新图像来测试(推断)我们的模型,也就是说,我们如何为新的测试图像生成标题。

回想一下,在我们看到如何准备数据的例子中,我们只使用了前两个图像及其标题。现在,让我们使用第三个图像,并尝试理解我们希望标题如何生成。

第三个图像向量和标题如下:

Test image

描述->黑猫在草地上行走

示例中的词汇还有:

vocab = {black,cat,endseq,grass,is,on,road,sat,startseq,the,walking,white}

我们将迭代生成标题,一次一个单词,如下所示:

迭代 1:

输入:图像向量+“startseq”(作为部分字幕)

预期输出字:“the”

(现在您应该理解标记“startseq”的重要性,它在推断过程中用作任何图像的初始部分标题)。

但是等等,模型生成了一个 12 长的向量(在示例中是 1652 长的向量,而在原始示例中是 1652 长的向量),这是词汇表中所有单词的概率分布。由于这个原因,我们贪婪地选择具有最大概率的单词,给定特征向量和部分标题。

如果模型训练良好,我们必须期望单词“the”的概率最大:

Iteration 1

这被称为最大似然估计(MLE) ,即我们根据给定输入的模型选择最有可能的单词。有时这种方法也被称为贪婪搜索,因为我们贪婪地选择具有最大概率的单词。

迭代 2:

输入:图像向量+ "startseq the "

预期输出字:“黑色”

Iteration 2

迭代 3:

输入:图像向量+ "startseq the black "

预期输出字:“猫”

Iteration 3

迭代 4:

输入:图像向量+ "startseq the black cat "

预期的输出字:“是”

Iteration 4

迭代 5:

输入:图像向量+ "startseq 黑猫是"

预期输出字:“行走”

Iteration 5

迭代 6:

输入:图像向量+ "startseq 黑猫在走"

预期输出字:“开”

Iteration 6

迭代 7:

输入:图像向量+“黑猫正在行走的起始序列”

预期输出字:“草”

Iteration 7

迭代 8:

输入:图像向量+“startseq 黑猫在草地上走”

预期输出字:“endseq”

Iteration 8

这是我们停止迭代的地方。

因此,当满足以下两个条件之一时,我们停止:

  • 我们遇到了一个“ endseq ”标记,这意味着模型认为这是标题的结尾。(您现在应该明白' endseq '标记的重要性了)
  • 我们达到由模型生成的单词数量的最大阈值

如果满足以上任何一个条件,我们就中断循环,并将生成的标题报告为给定图像的模型输出。用于推理的代码如下:

Inference with greedy search

14.估价

为了了解模型有多好,让我们尝试在测试数据集的图像上生成标题(即模型在训练期间没有看到的图像)。

Output — 1

注意:我们必须理解模型是如何精确地识别颜色的。

Output — 2

Output — 3

Output — 4

Output — 5

当然,如果我只给你看适当的说明,我是在欺骗你。世界上没有一个模型是完美的,这个模型也会犯错误。让我们来看一些例子,这些例子中的标题不是很相关,有时甚至是不相关的。

Output — 6

可能衬衫的颜色和背景色混在一起了

Output — 7

为什么模型把著名的拉菲尔·纳达尔归为女性:-)?大概是因为长发的缘故吧。

Output — 7

这次模型得到的语法不正确

Output — 9

很明显,这个模型尽了最大努力去理解这个场景,但是标题仍然不太好。

Output — 10

这又是一个模型失败,标题不相关的例子。

所以总而言之,我必须说,我天真的第一次切割模型,没有任何严格的超参数调整,在生成图像字幕方面做得很好。

重点:

我们必须理解,用于测试的图像必须与用于训练模型的图像在语义上相关。例如,如果我们在猫、狗等的图像上训练我们的模型。我们不能在飞机、瀑布等图像上测试它。这是一个训练集和测试集的分布将非常不同的例子,在这种情况下,世界上没有机器学习模型会提供良好的性能。

15.结论和未来工作

如果你已经到达这里,非常感谢。这是我第一次尝试写博客,所以我希望读者能慷慨一点,忽略我可能犯的小错误。

请参考我的 GitHub 链接 这里 访问 Jupyter 笔记本上写的完整代码。

请注意,由于模型的随机性,您生成的标题(如果您试图复制代码)可能与我的案例中生成的标题不完全相似。

当然,这只是一个初步的解决方案,可以进行许多修改来改进该解决方案,例如:

  • 使用一个更大的数据集。
  • 改变模型架构,例如包括注意模块。
  • 做更多超参数调整(学习率、批量大小、层数、单位数、辍学率、批量标准化等。).
  • 使用交叉验证集了解过拟合
  • 推断时使用波束搜索代替贪婪搜索。
  • 使用 BLEU Score 评估和测量模型的性能。
  • 以适当的面向对象的方式编写代码,以便其他人更容易复制:-)

16.参考

  1. https://cs.stanford.edu/people/karpathy/cvpr2015.pdf
  2. https://arxiv.org/abs/1411.4555
  3. https://arxiv.org/abs/1703.09137
  4. https://arxiv.org/abs/1708.02043
  5. https://machine learning mastery . com/develop-a-deep-learning-caption-generation-model-in-python/
  6. https://www.youtube.com/watch?v=yk6XDFm3J2c
  7. https://www.appliedaicourse.com/

PS: 如果你认为他们可以改进这个博客,请随时提供意见/批评,我一定会努力做出必要的修改。

图像分类挑战,使用迁移学习和深度学习工作室

原文:https://towardsdatascience.com/image-classification-challenge-using-transfer-learning-and-deep-learning-studio-2e89c3189fcf?source=collection_archive---------6-----------------------

Photo by Taylor Swayze on Unsplash.

图像分类的任务是识别图像上的对象或模式,并基于给定的类别/种类池来分配类别以对图像进行分类。有许多不同的子领域,如识别单个图像上的多个对象,甚至定位图像中的对象。

在这篇文章中,我想与你分享我参加第一次图像分类挑战赛以及使用深度学习工作室(DLS)平台的经历。DLS 在一个高抽象层次上提供了一个图形界面,以建立和训练基于后端的深度神经网络,如 keras / tensorflow / theano 等,免费用于桌面或云应用程序。

如果你从未听过或用过 DLS,去看看 这篇文章 Rajat 或在deep cognition . ai试用一下。

挑战

这项挑战被命名为汽水瓶识别挑战,由 DeepCognition.ai 直接主办,作为他们的第一场比赛,目标是在图像上识别不同种类的汽水瓶。
与其他竞赛类似,例如 Kaggle 上的竞赛,您会收到一个或多或少准备好的带有标签的图像数据集,以及一套关于如何评估结果的规则和信息,还有一个提交结果的流程。在这种情况下,由于需要使用深度学习工作室服务,数据集和提交过程是根据 DLS 的工作方式定制的,这使得获得 startet 和提交第一个模型变得非常容易。

在下面的帖子中,我试图描述我采取的步骤,我获得的经验和我犯的错误,我的最终模型得分为 93.75%,在比赛中获得了第 10 名。

数据集

提供的数据集由 6615 张图像组成,或多或少均匀地分成 8 类不同的汽水瓶。

Soda Bottle Dataset preview from DeepCognition.ai

正如你所看到的,图像已经基本上以类似的白色背景为中心,所以我决定我真的不需要任何更大的图像预处理步骤。人们应该注意到,并不是所有的图片都像这个数据集预览中显示的那样完美。通过手动滚动一些图像,您会注意到有许多不同角度的瓶子,以及瓶子躺着或被物体部分遮盖的图像。

Differently positioned bottles

原始图像大小为 640*480 像素,这不一定是一个巨大的图像处理,但肯定比大多数网络工作。因此,调整图像大小似乎是一个合理的决定,以查看哪些大小会产生最好的结果。

天真的第一种方法

我的第一个方法是简单地训练一个模型,用 DLS AutoML 特性生成,它将根据你的输入/输出设置为你生成一个完整的模型。

AutoML model for the Soda Bottle Challenge

正如你所看到的,生成的模型非常庞大,对于一个 6k 图像和 8 个类别的图像分类问题来说,可能是完全多余的,但我仍然继续尝试训练它。很快我就注意到,将图像保持在 640*480 像素的原始大小会立即填满我笔记本的 16GB RAM,并使训练过程崩溃。即使将尺寸缩小到原始图像的 1/4,这个 AutoML 模型对我的笔记本来说似乎还是太大了。

当然,DeepCognition 的云应用程序可以让你用相对较少的钱使用不同类型的 GPU,但我假设在这些条件下训练模型,将需要至少 4 个 GPU,这超出了我对这个项目的预算。

看起来简单的“魔棒”方法并没有让我走得更远,所以我考虑了其他可能的、资源更友好的解决方案。

迁移学习

迁移学习描述了一个相对宽泛的概念,即使用通过解决一组问题获得的知识来解决你当前问题的过程。

在我们的例子中,我们将使用一个已经成功训练的模型来识别图像上的某些对象,以识别不同的汽水瓶。乍一看,这可能没有意义。一个训练有素的模型如何区分猫和狗,能够告诉我们这个图像是包含露水还是胡椒博士瓶?

为了了解这可能是如何工作的,让我们非常简短地离题到图像分类模型是如何工作的。

特征抽出

几乎所有的图像分类模型都使用堆叠卷积层从图像中提取特征。这些特征在它们的第一层包含非常一般的信息,如边界或基本形状。使用预先训练的模型,我们可以利用模型的较低层的这些特征,因为它们将适用于几乎所有类型的图像数据。然后,我们只需要重新训练模型的最后几层,就可以学会识别我们的汽水瓶。

你可能想在这里 阅读关于卷积神经网络 的更深入的解释。

在讨论不同的模型选择之前,我们先来看看如何使用 DLS 实现预训练模型。

VGG16 as a pre-trained model

上面你可以看到一个非常基本的使用 DLS 图形编辑器的预训练 VGG16 模型的实现。有几件事需要考虑:

输入尺寸

我们的图像的输入尺寸显示在模型的第一个节点上(3,224,224),这意味着我们已经将图像的尺寸调整为 224*224 像素,这是 VGG16 模型的原始图像尺寸。

这可以在 DLS 的数据选项卡中轻松完成。

Resizing the input images

预训练模型

我们模型中的一个节点称为 VGG16,它实际上代表了压缩在单个节点中的整个 VGG16 模型架构。从预训练模型选项卡,DLS 提供了几个模型供选择。节点本身有一些关于如何加载预训练权重以及模型的哪个部分应该是可训练的选项。

VGG16 settings

正如你在右手边看到的,我们不包括 VGG16 模型的顶层,因为这些是一旦我们建立自己来分类 8 个汽水瓶类,而不是 1000 个类别的 imagenet 数据集,原始的 VGG16 模型被训练。

另一个重要参数是可训练值,它是我们希望在反向传播过程中包含的 VGG16 模型的百分比。由于前几层提取了相当一般化的特征,我们不想重新训练它们,而是保持它们原来的样子。实际上,在我的方法中,只重新训练 VGG16 模型的最后一个卷积块就足够了,它大约是模型的 25%。

通过这种设置,与 AutoML 模型相比,该模型需要的资源少得多,甚至可以在我配有 CPU 和 16GB RAM 的笔记本电脑上进行训练。然而,我只达到了大约 1 个样本/秒的处理速度,这将导致训练时间大约为。只有一个纪元的 76 分钟。这似乎是不可接受的,因为我想测试几种不同的方法,看看哪种模型表现最好。此外,整个比赛持续时间只有大约 3 周。

切换到云版本并使用 Telsa K80 以大约 1 美元/小时的速度运行,导致培训时间大约为。VGG16 型号每周期 74 秒,我尝试的一些其他型号甚至更快。

VGG16 / VGG19 / ResNet50

为了比较不同种类的预训练模型,我做了一个 10 个时期的小测试,每个时期都有与 VGG16 模型相同的设置。

VGG16

VGG16 training process

VGG16 模型在前 2 个时期后在验证集上仅实现了约 14%的准确度,并且似乎在最后 8 个时期都不被认可。在 8 类分类问题上 14%的准确率仅略高于随机猜测概率,后者约为 12.5%。这个结果对于迁移学习的前景来说并不是很鼓舞人心,但是让我们看看其他模型的得分如何。

VGG19

VGG19 training prcoess

VGG19 模型的架构与他的前任 VGG16 相似,但更深入,已经表现得更好,几乎达到 30%的精度。然而,训练曲线并没有给出通过进一步训练来提高准确度的希望。

ResNet50

ResNet50 training process

差别真大!这是我所希望的结果。如你所见,该模型在 3 个时期后几乎达到了 80%的准确率,并在整个训练过程中不断提高。除了在三款测试车型中表现最佳之外,它还拥有最快的训练速度。

估价

有几种方法可以评估模型的性能。首先,对您的数据进行适当的训练/测试分割对于创建一个对未来数据表现良好的模型是必不可少的。DLS 自动对您的数据执行训练/验证/测试分割,同时让您选择不同的分割比率。

DLS Dataset settup

在训练过程中,然后在每个时期之后使用验证集来计算验证损失和准确度,这与训练损失/准确度一起显示在训练图中。

在训练过程的最后,您可以对数据的测试分割进行推理。在我们的例子中,这意味着我们将使用我们训练过的模型来预测测试集的图像上显示的是哪一类汽水瓶。

DLS Dataset Inference

用我们训练过的模型在我们的测试分割上运行预测,可以让我们知道我们的模型能够多好地识别它以前没有见过的图像上的汽水瓶类别。

当然,这很大程度上取决于数据集内部的方差。在我们的案例中,提供的所有图像都是以非常相似的方式拍摄的,只有角度或旋转上的微小差异。因此,推理的表现和预期的一样好,这并不一定意味着它能够识别不同的图像。许多参赛者在提交他们的第一个模型进行评估后可能会注意到一个事实。

提交流程

在我们的私人数据集上创建了一个准确率约为 80%的模型后,我觉得自己已经准备好第一次提交参赛作品了。

本次比赛的提交过程相当简单。DLS 提供了一个以 zip 文件形式下载您的训练模型的功能,该文件包含您的. h5 模型文件以及一个配置文件和一个 test.py 脚本,可用于在测试映像上运行您的模型。这个压缩文件只需上传到比赛网站。

提交我的第一个模型,最终得分约为 40%。

相当令人失望,当我们预期分数约为 80%时。那么这种差异从何而来呢?

按照竞赛规则的规定,对参赛作品的评估是在个人的私有数据集上进行的,参赛者无法访问这些数据集。我们训练过的模型从未见过这些图像,因此 40%的准确率意味着该模型没有足够的泛化能力来识别它没有见过的图像上的汽水瓶。

数据扩充

提高模型性能的一种方法是数据扩充。数据扩充描述了仅使用来自我们的训练数据的信息来增加训练数据量的过程。对于我们的图像数据集,这意味着我们根据现有的图像创建更多具有不同特征的图像。例如,我们可以左右移动图像、旋转图像、上下翻转图像或执行剪切变换。

如果你有兴趣阅读更多关于数据增强的内容,请查看 瑞安·奥尔雷德 帖子

使用这些“新”图像,我们基本上在更大的数据集上训练我们的模型,并由此增加其鲁棒性,因为它不仅从原始图像中学习。因此,我们应该看到对私有评估数据集的预测也有所改善。

Data Augmentation in DLS

在 DLS,数据扩充可以像调整大小选项一样直接在输入图像的数据选项卡下使用。

使用如上所示的数据增强图像训练我们的 ResNet50 模型,得到了非常相似的训练曲线,在 10 个时期后峰值约为 90%。

ResNet50 training process with data augmentation

将这个模型提交给比赛给了我 57%的分数,这表明数据增强有助于提高模型的整体稳健性,正如我们预期的那样。

与我们在训练期间达到的 91%相比,57%看起来不是很好,但是不要忘记我们只训练了 10 个时期的模型。我认为有改进的余地。

超参数

机器学习中的超参数,描述我们的模型中在学习过程开始之前设置的那些参数。最常见的是你谈论的参数,如批量大小、时期数、优化器和损失函数。

阅读更多关于超参数的文章 本文 作者 丹尼尔·夏皮罗博士

这些也是 DLS 在超参数选项卡下为您提供的超参数。

据我所知,DLS 默认提供这些设置,基于 keras 中实现的默认值。因为这些是你最常用的设置,我继续使用 DLS 的默认设置。我只是调整了批量大小,以提高训练速度。

作为一个优化器,我们使用了 Adadelta,它有一个自适应的学习率,所以我们甚至不用费心去寻找正确的学习率。这对于快速获得好的结果是很棒的,但是也会导致一个小问题,我将在后面讨论。

如果你想深入了解不同的优化器,我建议你阅读本文Rinat Maksutov

决赛成绩

为了提高分数,我尝试了很多不同的方法。最后,帕维尔·奥斯特亚科夫和阿列克谢·哈尔拉莫夫在他们的谈话中表达了一个想法,这个想法让我最终得出了大约 93%的准确率。

他们参加了一场图像分类挑战,这有点类似于汽水瓶识别挑战,但数据集要大得多。他们在训练中的方法是只在原始图像上开始训练,没有任何数据增强。然后,在训练收敛后,他们停下来,保存模型,并继续进行少量增强训练。他们多次重复这些步骤,一直训练到损失收敛,每次都增加数据增加量。

起初,在 DLS 建立这种行为是相当容易的,因为在开始训练过程时,有一个选项来加载上次跑步的重量。

DLS loading weights of previous runs

当我试图模仿上面提到的程序时,我的最终得分高达 80%,但在我看来,这主要是因为该模型的整体训练时间较长。

学习率

如前所述,我选择了具有自适应学习率的 Adadelta 优化器。它以较高的学习率开始,并在训练过程中逐渐降低。

由于我们已经多次开始和停止训练过程来调整数据扩充,所以学习率的调整并不真正有效,因为我在 DLS 找不到任何选项来保存或加载先前运行的学习率。

这就是为什么我决定尝试 Adam 优化器,它也有一个学习率衰减的参数,但从一个固定的学习率开始。因此,我在第一次运行时以 0.01 的标准学习率开始,然后在每次新的训练开始后手动调整学习率。

用这种新方法,我最终达到了 93.75%的最终分数,请注意,这是提交期的最后一天。

由于选择正确的学习速率是超参数调优中最棘手也是最重要的部分之一,我将推荐阅读 文章 作者Pavel Surmenok**

结论

总的来说,由于这是我第一次参加比赛,我对自己的成绩非常满意。DeepCognitions 竞赛极大地激励了人们去尝试不同的架构和方法,并在这样做的同时学到了很多东西,所有这些都不需要编写一行代码。

比赛的前两个位置实际上达到了完美的 100 分,所以对我来说肯定有改进的空间。

我希望你喜欢阅读我关于如何应对这一挑战的想法,甚至可能带走一些想法。请随时留下任何提示或建议,告诉我你会如何解决这个问题,以及我可以如何改进。

我总是很高兴认识新朋友并分享想法,所以如果你喜欢这篇文章,可以考虑在 LinkedIn 上加我。

使用 MNIST 数据集在 10 分钟内完成图像分类

原文:https://towardsdatascience.com/image-classification-in-10-minutes-with-mnist-dataset-54c35b77a38d?source=collection_archive---------0-----------------------

深度学习案例研究

利用 TensorFlow 和 Keras |监督深度学习使用卷积神经网络来分类手写数字

如果你正在阅读这篇文章,我确信我们有着相似的兴趣,并且正在/将要从事相似的行业。所以还是通过 Linkedin 联系吧!请不要犹豫发送联系请求!Orhan g . yaln-Linkedin

MNIST Dataset and Number Classification by Katakoda

在开始这篇文章之前,我只想让你知道,如果你对深度学习感兴趣,我相信你也应该看看我的其他文章,比如:

1 — 使用深度卷积自动编码器在 10 分钟内降低图像噪声我们学习了如何构建用于图像去噪的自动编码器;

2 — 用递归神经网络预测明天的比特币(BTC)价格 我们用 RNN 预测 BTC 价格,因为它使用 API,所以结果总是最新的。

当你开始学习不同神经网络架构的深度学习时,你会意识到最强大的监督深度学习技术之一是卷积神经网络(缩写为“CNN”)。CNN 的最终结构实际上非常类似于常规神经网络(RegularNets ),其中存在具有权重和偏差的神经元。此外,就像在 RegularNets 中一样,我们在 CNNs [ CS231 ]中使用一个损失函数(例如 crossentropy 或 softmax)和一个优化器(例如 adam optimizer)。此外,在 CNN 中,还有卷积层、汇集层和平坦层。CNN 主要用于图像分类,尽管您可能会发现其他应用领域,如自然语言处理。

为什么选择卷积神经网络

正则网络的主要结构特征是所有的神经元都是相互连接的。例如,当我们有灰度为 28×28 像素的图像时,我们最终会在一个似乎易于管理的层中有 784(28×28×1)个神经元。然而,大多数图像有更多的像素,他们不是灰度。因此,假设我们有一组 4K 超高清彩色图像,我们将有 26,542,080 (4096 x 2160 x 3)个不同的神经元在第一层相互连接,这实际上是不可管理的。因此,我们可以说正则网对于图像分类是不可伸缩的。然而,特别是当涉及到图像时,两个单独的像素之间似乎几乎没有相关性或关系,除非它们彼此靠近。这就引出了卷积层和池层的概念。

CNN 中的层

我们能够在卷积神经网络中使用许多不同的层。但是,卷积、池化和全连接层是最重要的。因此,我将在实现它们之前快速介绍这些层。

卷积层

卷积层是我们从数据集中的图像中提取特征的第一层。由于像素仅与相邻和接近的像素相关,卷积允许我们保留图像不同部分之间的关系。卷积基本上是用较小的像素过滤器过滤图像,以减小图像的大小,而不丢失像素之间的关系。当我们通过使用具有 1x1 步幅(每步移动 1 个像素)的 3×3 滤波器将卷积应用于 5×5 图像时。我们最终将得到 3×3 的输出(复杂度降低了 64%)。

Figure 1: Convolution of 5 x 5 pixel image with 3 x 3 pixel filter (stride = 1 x 1 pixel)

汇集层

当构造 CNN 时,通常在每个卷积层之后插入汇集层,以减小表示的空间大小,从而减少参数计数,这降低了计算复杂度。此外,合并层也有助于解决过度拟合问题。基本上,我们通过选择这些像素内的最大值、平均值或和值来选择池大小以减少参数的数量。最大池化是最常见的池化技术之一,可演示如下:

Max Pooling by 2 x 2

一组完全连接的层

完全连接的网络是我们的规则网络,其中每个参数相互链接,以确定标签上每个参数的真实关系和效果。由于卷积和合并层大大降低了我们的时空复杂度,我们最终可以构建一个完全连通的网络来分类我们的图像。一组完全连接的层如下所示:

A fully connected layer with two hidden layers

既然您对我们将使用的各个层有了一些了解,我认为是时候分享一个完整的卷积神经网络的概览了。

A Convolutional Neural Network Example by Mathworks

现在你有了一个关于如何建立一个卷积神经网络的想法,你可以建立一个图像分类,我们可以得到最陈词滥调的分类数据集:MNIST 数据集,代表修改后的国家标准和技术研究所数据库。这是一个手写数字的大型数据库,通常用于训练各种图像处理系统。

下载 MNIST 数据集

MNIST 数据集是用于影像分类的最常用数据集之一,可从许多不同的来源访问。事实上,甚至 Tensorflow 和 Keras 也允许我们直接从它们的 API 导入和下载 MNIST 数据集。因此,我将从下面两行开始,在 Keras API 下导入 TensorFlow 和 MNIST 数据集。

MNIST 数据库包含 60,000 张训练图像和 10,000 张测试图像,取自美国人口普查局员工和美国高中生[ 维基百科 ]。因此,在第二行中,我将这两个组分为训练组和测试组,还将标签和图像分开。x_train 和 x_test 部分包含灰度 RGB 代码(从 0 到 255 ),而 y_train 和 y_test 部分包含从 0 到 9 的标签,表示它们实际上是哪个数字。为了可视化这些数字,我们可以从 matplotlib 获得帮助。

当我们运行上面的代码时,我们将得到 RGB 代码的灰度可视化,如下所示。

A visualization of the sample image at index 7777

我们还需要知道数据集的形状,以便将其导入卷积神经网络。因此,我将使用 NumPy 数组的“shape”属性,代码如下:

你会得到(60000,28,28)。您可能已经猜到,60000 表示训练数据集中的图像数量,而(28,28)表示图像的大小:28 x 28 像素。

重塑和标准化图像

为了能够在 Keras API 中使用数据集,我们需要 4 维 NumPy 数组。然而,正如我们在上面看到的,我们的数组是三维的。此外,我们必须规范化我们的数据,因为它在神经网络模型中总是需要的。我们可以通过将 RGB 代码分为 255(最大 RGB 代码减去最小 RGB 代码)来实现这一点。这可以通过下面的代码来完成:

构建卷积神经网络

我们将通过使用高级 Keras API 来构建我们的模型,该 API 在后端使用 TensorFlow 或 Theano。我想提一下,有几个高级 TensorFlow APIs,如 Layers、Keras 和 Estimators,可以帮助我们创建具有高级知识的神经网络。然而,这可能会导致混乱,因为它们的实现结构各不相同。所以,如果你看到同一个神经网络虽然都用 TensorFlow,但是代码完全不同,这就是为什么。我将使用最简单的 API,即 Keras。因此,我将从 Keras 导入顺序模型,并添加 Conv2D、MaxPooling、Flatten、Dropout 和 Dense 层。我已经谈到了 Conv2D、Maxpooling 和密集层。此外,丢弃层通过在训练时忽略一些神经元来对抗过度拟合,而展平层在构建完全连接的层之前将 2D 阵列展平为 1D 阵列。

对于第一致密层,我们可以用任何数目进行实验;然而,最终的密集层必须有 10 个神经元,因为我们有 10 个数字类(0,1,2,…,9)。你可以尝试内核大小、池大小、激活函数、退出率和第一密集层中的神经元数量,以获得更好的结果。

编译和拟合模型

使用上面的代码,我们创建了一个非优化的空 CNN。现在是时候为优化器设置一个使用度量标准的给定损失函数了。然后,我们可以通过使用我们的训练数据来拟合模型。对于这些任务,我们将使用以下代码:

您可以试验优化器、损失函数、指标和时期。然而,我可以说,亚当优化器通常是优于其他优化器。我不确定你是否真的可以改变多类分类的损失函数。请在下面随意试验和评论。纪元编号可能看起来有点小。然而,您将达到 98–99%的测试准确度。由于 MNIST 数据集不需要强大的计算能力,您也可以轻松地试验纪元编号。

评估模型

最后,您可以使用一行代码通过 x_test 和 y_test 来评估定型模型:

对于 10 个时期和这样一个简单的模型来说,结果相当不错。

Evaluation shows 98.5% accuracy on test set!

我们用这样一个基本模型达到了 98.5%的准确率。坦率地说,在许多图像分类情况下(例如,对于自动驾驶汽车),我们甚至不能容忍 0.1%的误差,因为作为类比,它将在 1000 个情况中导致 1 个事故。然而,对于我们的第一个模型,我会说结果还是不错的。我们还可以使用以下代码进行单独的预测:

我们的模型将图像分类为“9 ”,以下是图像的视觉效果:

Our model correctly classifies this image as a 9 (Nine)

虽然这不是一个很好的数字 9 的笔迹,但我们的模型能够将其归类为 9。

恭喜你!

你已经用 Tensorflow 的 Keras API 成功构建了一个卷积神经网络来对手写数字进行分类。你已经达到了超过 98%的准确率,现在你甚至可以保存这个模型&创建一个数字分类器应用程序!如果你对保存你的模型感兴趣,我会指引你去查看 Keras 文档。毕竟,为了能够有效地使用 API,必须学习如何阅读和使用文档。

订阅邮件列表获取完整代码

如果你想在 Google Colab 上获得完整的代码,并获得我的最新内容,请订阅邮件列表:✉️

现在就订阅

喜欢这篇文章

如果你喜欢这篇文章,可以考虑看看我的其他类似文章:

[## 使用卷积自动编码器在 10 分钟内降低图像噪声

在时尚 MNIST 的帮助下,使用深度卷积自动编码器清洁(或去噪)有噪声的图像

towardsdatascience.com](/image-noise-reduction-in-10-minutes-with-convolutional-autoencoders-d16219d2956a) [## 利用生成性对抗网络在 10 分钟内生成图像

使用无监督深度学习生成手写数字与深度卷积甘斯使用张量流和…

towardsdatascience.com](/image-generation-in-10-minutes-with-generative-adversarial-networks-c2afc56bfa3b) [## 使用递归神经网络预测比特币(BTC)价格

如果你能以某种方式预测明天的比特币(BTC)价格,这不是很棒吗?加密货币市场有…

towardsdatascience.com](/using-recurrent-neural-networks-to-predict-bitcoin-btc-prices-c4ff70f9f3e4) [## TensorFlow Hub & Magenta 在 5 分钟内实现快速神经风格转换

利用 Magenta 的任意图像风格化网络和深度学习,将梵高的独特风格转移到照片中

towardsdatascience.com](/fast-neural-style-transfer-in-5-minutes-with-tensorflow-hub-magenta-110b60431dcc)

图片分类 Keras 教程:Kaggle 犬种挑战赛

原文:https://towardsdatascience.com/image-classification-python-keras-tutorial-kaggle-challenge-45a6332a58b8?source=collection_archive---------1-----------------------

Golden Retriever image taken from unsplash.com

识别狗的品种是一个有趣的计算机视觉问题,因为细微的差异在视觉上将狗的品种彼此分开。本文旨在为那些刚刚开始使用卷积神经网络进行图像分类并希望了解如何试验网络架构、超参数、数据扩充以及如何处理加载自定义数据以进行测试和训练的人提供一个教程。

所有代码都用 Python 和 Keras 编写,托管在 Github 上:https://Github . com/CShorten/KaggleDogBreedChallenge/blob/master/dog breed _ binary classification . ipynb

我们使用的数据集来自 Kaggle.com 的狗品种鉴定挑战赛。Kaggle 竞赛是提升你的机器学习技能的一个很好的方式,本教程将帮助你熟悉网站上图像数据的格式。

Kaggle 上列出的这项挑战有 1286 个不同的团队参加。最大的挑战是在 120 个不同的种类中识别狗的品种。

120 个类是一个非常大的多输出分类问题,伴随着各种各样的挑战,例如如何对类标签进行编码。例如,对标签进行一次热编码将需要每个类别非常稀疏的向量,例如:[0,0,…,0,1,0,0,…,0]。

本教程随机选择了两个类,金毛寻回犬和设得兰牧羊犬,并侧重于二元分类的任务。

编程和数据科学新手可能会遇到的另一个挑战是 Kaggle 的数据格式。Kaggle 提供了一个由“id”而不是“Golden-Retriever-1”标记的图像的训练目录,以及一个带有 id →狗品种映射的 CSV 文件。我发现了 python 字符串函数。split('delimiter ')是我解析这些 CSV 文件的最好朋友,我将在教程中向您展示这是如何工作的。

本教程的第一部分将向您展示如何解析这些数据并将其格式化以输入到 Keras 模型中。然后我们将关注问题的一个部分,金毛寻回犬与设得兰牧羊犬,(任意选择)。

本教程的第二部分将向您展示如何将自定义数据加载到 Keras 中,并构建一个卷积神经网络来对它们进行分类。

本教程的第三部分将讨论偏差-方差权衡,并研究不同的架构、漏失层和数据扩充,以在测试集上获得更好的分数。

第 1 部分:格式化定制图像数据以输入到 Keras 模型

from PIL import Image # used for loading images
import numpy as np
import os # used for navigating to image path
import imageio # used for writing imagesnaimg_dict = {} # id: breed
f = open("labels.csv", "r")
fileContents = f.read()
fileContents = fileContents.split('\n')
for i in range(len(fileContents)-1):
  fileContents[i] = fileContents[i].split(',')
  naming_dict[fileContents[i][0]] = fileContents[i][1]

现在我们有了一个 python 字典 naming_dict,它包含了从 id 到 breed 的映射。现在,我们需要为每个品种建立一个计数字典,以便为图像分配标签,如“Golden_Retriever-1”、“Golden_Retriever-2”、“Golden_Retriever-67”。

breeds = naming_dict.values()
breed_set = set(breeds)
counting_dict = {}
for i in breed_set:
  counting_dict[i] = 0

I .我们循环浏览当前命名为“id.jpg”的图像

二。剥去。来自他们的 jpg

三。将它们与命名词典中的品种相匹配。

四。然后我们会根据我们已经统计的数量给它们命名

动词 (verb 的缩写)最后,用这个新实例增加计数。

for img in os.listdir('./raw_data'):
  imgName = img.split('.')[0] # converts '0913209.jpg' --> '0913209'
  label = naming_dict[str(imgName)]
  counting_dict[label] += 1
  path = os.path.join('./raw_data', img)
  saveName = './labeled_train/' + label + '-' + str(counting_dict[label]) + '.jpg'
  image_data = np.array(Image.open(path))
  imageio.imwrite(saveName, image_data)

现在,训练目录中的所有图像都被格式化为‘Breed-#’。jpg。非常有用的加载到 CNN 和分配一个热点矢量类标签使用图像命名。

将数据加载到 Keras 模型

关于训练-测试分割的说明:在本教程中,我决定使用训练集和测试集来代替交叉验证。这是因为我在我的 CPU 上运行这些 CNN,因此它们需要大约 10-15 分钟来训练,因此 5 重交叉验证将需要大约一个小时。我希望这项研究的重点是如何用不同的方法来改变你的模型结构,以达到更好的结果,因此快速迭代是很重要的。此外,我进行了大约 2/3–1/3 的训练/测试分割,这比通常的测试实例多一点,但是,这不是一个非常大的数据集。

def label_img(name):
  word_label = name.split('-')[0]
  if word_label == 'golden_retriever' : return np.array([1, 0])
  elif word_label == 'shetland_sheepdog' : return np.array([0, 1])

这被称为一键矢量编码,它比用“0”或“1”编码每个标签产生更好的结果。就神经网络结构而言,这意味着输出层中有 2 个神经元,而不是 1 个,您将在下面 CNN 代码的最后一行中看到这一点:

更新(4/22/19): 这仅在多标签分类的情况下成立,而不是二进制分类。在二进制分类中,输出被视为 0 或 1,并且只有一个输出神经元,keras 将在编译期间纠正这一错误。

model.add(Dense(2, activation = 'softmax'))

调整图像大小

当我们格式化要输入到 Keras 模型的图像时,我们必须指定输入尺寸。许多学术数据集,如 CIFAR-10 或 MNIST,都有相同的大小(分别为 32x32x3 和 28x28x1)。然而,在 ImageNet 数据集和这个狗品种挑战数据集中,我们有许多不同大小的图像。首先,我们将编写一些代码来循环遍历这些图像,并收集一些关于狗图像的最大、平均和最小高度和宽度的描述性统计数据。

def get_size_statistics(DIR):
  heights = []
  widths = []
  for img in os.listdir(DIR): 
    path = os.path.join(DIR, img)
    data = np.array(Image.open(path)) #PIL Image library
    heights.append(data.shape[0])
    widths.append(data.shape[1])
  avg_height = sum(heights) / len(heights)
  avg_width = sum(widths) / len(widths) print("Average Height: " + str(avg_height))
  print("Max Height: " + str(max(heights)))
  print("Min Height: " + str(min(heights)))
  print('\n')
  print("Average Width: " + str(avg_width))
  print("Max Width: " + str(max(widths)))
  print("Min Width: " + str(min(widths)))

结果:平均身高= 388.34,最大身高=914,最小身高= 150

平均宽度= 459.12,最大宽度= 800,最小宽度= 200

加载图像

IMG_SIZE = 300def load_training_data():
  train_data = []
  for img in os.listdir(DIR)
    label = label_img(img)
    path = os.path.join(DIR, img)
    img = Image.open(path)
    img = img.convert('L')
    img = img.resize((IMG_SIZE, IMG_SIZE), Image.ANTIALIAS)
    train_data.append([np.array(img), label]) # Basic Data Augmentation - Horizontal Flipping
    flip_img = Image.open(path)
    flip_img = flip_img.convert('L')
    flip_img = flip_img.resize((IMG_SIZE, IMG_SIZE), Image.ANTIALIAS)
    flip_img = np.array(flip_img)
    flip_img = np.fliplr(flip_img)
    train_data.append([flip_img, label]) shuffle(train_data)
  return train_data

测试图像加载以确保其正常工作

train_data = load_training_data()
plt.imshow(train_data[43][0], cmap = 'gist_gray')

第 2 部分:简单的 CNN

model = Sequential()
model.add(Conv2D(32, kernel_size = (3, 3), activation='relu', input_shape=(IMG_SIZE, IMG_SIZE, 1)))
model.add(MaxPooling2D(pool_size=(2,2)))
model.add(BatchNormalization())model.add(Conv2D(64, kernel_size=(3,3), activation='relu'))
model.add(MaxPooling2D(pool_size=(2,2)))
model.add(BatchNormalization())model.add(Conv2D(64, kernel_size=(3,3), activation='relu'))
model.add(MaxPooling2D(pool_size=(2,2)))
model.add(BatchNormalization())model.add(Conv2D(96, kernel_size=(3,3), activation='relu'))
model.add(MaxPooling2D(pool_size=(2,2)))
model.add(BatchNormalization())model.add(Conv2D(32, kernel_size=(3,3), activation='relu'))
model.add(MaxPooling2D(pool_size=(2,2)))
model.add(BatchNormalization())
model.add(Dropout(0.2))model.add(Flatten())
model.add(Dense(128, activation='relu'))
#model.add(Dropout(0.3))
model.add(Dense(2, activation = 'softmax'))

此模型的培训日志:

评估模型时使用:

loss, acc = model.evaluate(testImages, testLabels, verbose = 0)
print(acc * 100)

初始模型= 72.09%的准确度

第 3 部分:改进模型

我认为有 5 种策略可以最有效地提高测试准确度:

I .增加更多辍学层

正如我们从训练报告中看到的,该模型在训练集上达到了 100%的准确率。从训练中的 100%到测试中的 72%表明了过度拟合的明显问题。过拟合可以通过增加漏失层或简化网络架构来解决(la 偏差-方差权衡)。然而,这与其说是一门科学,不如说是一门艺术,如果没有反复试验,很难准确计算出如何减少过拟合。

二。卷积网络参数

我们可以尝试删除或添加卷积层,改变滤波器大小,甚至改变激活函数。

三。改变网络末端的多层前馈神经网络

卷积网络的工作原理是对图像进行卷积,创建一个新的表示,然后将该表示压缩成一个向量,该向量被输入到一个经典的多层前馈神经网络中。我们可以尝试添加更多的隐藏层,或者改变每个隐藏层中神经元的数量。

四。数据扩充

在本教程中,我们只是用水平翻转来增强图像。但是您可以尝试其他方法,如随机裁剪、翻译、色阶转换等等。如果你雄心勃勃,你也可以尝试神经类型转移或生成对抗网络来增强数据。

动词 (verb 的缩写)狗对象检测裁剪

当我浏览这个数据集时,很明显,这些图像中有许多噪声,可能会混淆卷积神经网络。因此,改善这个网络的一个很好的策略是训练一个对象识别模型来检测狗的图片,并裁剪掉图像的其余部分,这样你就只对狗本身进行分类,而不是对狗和背景中的其他一切进行分类。

如果您对改进图像识别模型的更多细节感兴趣,请查看这篇文章:

[## 入侵你的图像识别模型

建立模型后提高图像识别准确性的后续步骤。

towardsdatascience.com](/hacking-your-image-recognition-model-909ad4176247)

结论

希望本文能帮助您加载数据,熟悉 Kaggle 图像数据的格式,并了解更多关于图像分类和卷积神经网络的知识。这是我第一次尝试做一个完整的编程教程,请在评论中留下你的任何建议或问题。另外,如果这篇文章对你有帮助,请留下你的掌声,谢谢你的阅读!

CShorten

Connor Shorten 是佛罗里达大西洋大学计算机科学专业的学生。对深度学习和软件工程感兴趣。

基于 MNIST 数据集的卷积神经网络图像分类。

原文:https://towardsdatascience.com/image-classification-using-convolutional-neural-networks-on-mnist-data-set-406db0c265ed?source=collection_archive---------7-----------------------

这篇文章是为那些对机器学习感兴趣并且正在寻找一个不太复杂的来源的人准备的。

我是犹他大学的一名研究生,在我短暂的课程工作中,我对机器学习和人工智能产生了兴趣。我喜欢研究不同的数据集,并做笔记,然后发布到网上,这样那些觉得难以理解深度研究论文的人就可以从更简单、更容易理解的角度来看待人工智能和人工智能。

如果我必须向一个五年级学生解释什么是机器学习,我会说,你迈出的每一小步都会产生一个结果,让你知道什么是有利的,什么是不利的。这是机器学习的基础。类似地,当我们在大型数据集上训练计算机系统时,我们在给它们提供什么是有利的,什么是不利的信息。例如,当狗和猫的图片被提供给系统时,系统根据该信息训练自己,并且基于该信息,系统现在能够识别什么是猫,什么是狗。如何训练一个计算机系统来完成这样的魔法,我们将在本文的后面部分找到答案。

MNIST 手写的图像:

这是一个数据集,由从 0 到 9 的手写数字图像组成。每个图像都是单色的,28 * 28 像素。请参见下面的示例:

Source: https://www.tensorflow.org/tutorials/layers

目标:

训练计算机系统首先理解什么是数字的手写图像,然后测试该系统以正确预测新的手写图像。我们将向我们的系统提供 MNIST 数据集,并用随机图像对其进行测试,以检查其预测的准确性。

先决条件:

  1. python 脚本基础知识,Python 3.6。
  2. 关于什么是机器学习和张量流的概念。
  3. 学习新事物的活力。

如何做:

导入张量流和 MNIST 数据:

import tensorflow as tffrom tensorflow.examples.tutorials.mnist import input_data
mnist = input_data.read_data_sets("MNIST_data/", one_hot=True)

占位符:

占位符不同于变量。它们是为保存训练数据而创建的参数,在这种情况下,它们是训练图像。MNIST 图像的形状为(28*28)。这些将被展平成(None *784)形状张量。“无”表示它可以是任何大小。

x = tf.placeholder(tf.float32, [None, 784])

权重和偏差:

权重和偏差的初始值被设置为零,因为当计算发生时它将被改变。因此,初始值是什么并不重要。因为存在 784 个特征和 10 个输出,所以 w’是(784 * 10)形状。“b”的形状是 10,因为从 0 到 9(数字)有 10 个输出。

w = tf.Variable(tf.zeros([784,10]))
b = tf.Variable(tf.zeros([10]))

预测模型:

x 和 w 是相乘并加到偏差上的矩阵。softmax 函数接受值并使总和为 1。这样,它可以用作概率值,使得判断哪个数字(0 -9)被预测的机会更高变得一致。

y = tf.nn.softmax(tf.matmul(x,w) + b)
#training our model
y_ = tf.placeholder(tf.float32, [None,10])

交叉熵函数:

交叉熵函数是成本或损失函数。它将真实值与预测值进行比较。目标是使损失最小化。

cross_entropy = tf.reduce_mean(-tf.reduce_sum(y_ * tf.log(y), reduction_indices=[1]))

梯度下降优化器:

当使用交叉熵函数形成模型图时,我们希望找到损失最小的点。这是使用梯度下降优化器完成的。它向图中值较小的部分移动。可以手动设置步数或学习率。如果设定一个非常小的学习率,如 0.001,系统将永远需要达到损失最小的点,但它将更加精确。如果学习率设置得很高,则系统可能会产生快速但错误的结果。

train_step = tf.train.GradientDescentOptimizer(0.5).minimize(cross_entropy)

训练模式:

在这里,我们正在训练我们的模型,以 100 个为一批来学习 MNIST 数据。

y_ = tf.placeholder(tf.float32, [None,10])cross_entropy = tf.reduce_mean(-tf.reduce_sum(y_ * tf.log(y), reduction_indices=[1]))train_step = tf.train.GradientDescentOptimizer(0.5).minimize(cross_entropy)

评估和测试模型:

在这里,模型以 0.8916 的精度被评估和测试。tf.argmax 给出一个轴中的最高值。所以,y_ 是正确值,y 是预测值。tf.equal 用于判断它们是否相等。

prediction = tf.equal(tf.argmax(y,1), tf.argmax(y_,1))

多卷积层:

在这里,我们使用更多的层、权重和偏差来改进我们的模型并提高准确性。

我们的第一个卷积层对于每个 5*5 的面片有 32 个特征。它的权重张量将是[5,5,1,32]的形状。前两个维度是面片大小,接下来是输入通道,最后一个数字是输出通道。

为了应用卷积层,x 被整形为 4D 张量。28*28 是图像的宽度和高度,最后一个维度是颜色通道的数量。

然后应用 ReLU 函数使负值为 0,并保持正值不变。最大池将图像大小缩小到 14*14。

第二卷积层对于每个 5*5 的面片具有 64 个特征。

现在,图像大小已经减少到 7*7,我们添加一个具有 1024 个神经元的全连接层。

漏失和读出层:

为了减少过度拟合,我们会随机丢弃一些数据。因此,下降层有助于提高预测的准确性。下一层用于读取数据。

最终精度:

0.9919

完整的 Python 代码:

[## 拉吉特尼哈尔/MNIST

在 GitHub 上创建一个帐户,为 rajitnikhare/MNIST 的发展做出贡献。

github.com](https://github.com/rajitnikhare/MNIST/blob/master/MNIST_Softmax.py)

参考文献:

  1. https://www . tensor flow . org/versions/r 1.0/get _ started/Mn ist/pros
  2. https://code labs . developers . Google . com/code labs/cloud-tensor flow-mnist/# 2

图像分类:完整的工作流程

原文:https://towardsdatascience.com/image-classifier-complete-workflow-a9e0003c80ba?source=collection_archive---------13-----------------------

I .定义问题并获取数据

机器学习模型一般分为两类,分类和回归模型。然而,分类模型之间还有一些额外的变化。例如,您可以预测一个二进制输出,如猫对狗,或许多输出,如 CIFAR-10 数据集,还有许多其他方法来映射分类器的输出,这将反映在网络的最终层。

一旦你定义了你的问题,你就应该开始考虑如何获得你的数据。最流行的方法之一是开发一种网络抓取算法,从网站上的标签中抓取图像。你也可以使用机械土耳其人外包你的数据收集需求。我通常只是通过简单地在网上截图并改变截图的默认存储位置来开始项目,以便通过这种方式收集数据。这个过程显然是非常艰巨的,但是,我发现它可以很好地获得项目的快速原型。

此外,一旦您收集了大量数据,您将需要考虑替代的数据存储方法,如云。

二。卷积架构,目标是增加复杂性

一旦你收集了足够的数据开始,你将建立你的卷积网络。这对于 TFlearn、Keras 或 PyTorch APIs 来说非常容易。下面的文章将为您提供入门代码,您可以轻松地将其复制并粘贴到您的项目中,从而创建一个非常简单的 CNN 架构。

[## Python:如何构建卷积网络分类器:耐克 vs 阿迪达斯鞋子

我为#100DaysOfMLCode 做的一个实验是建立一个图像分类器来区分 Nike…

towardsdatascience.com](/how-to-build-a-convolutional-network-classifier-81eef880715e)

渐进复杂性:当你在试验你的卷积网络时,最好从一个简单的结构开始,比如 1-4 个卷积层。当您添加更多数据时,或者如果您的初始结果不令人满意,您可能希望添加更多图层。当您试验您的网络架构时,为测试模型保留一个数据集是很重要的。通过这种方式,您可以使用这种性能作为控制来试验您的模型复杂性。

三。数据扩充

提高模型性能和稳健性的最简单方法之一是向数据集添加合成数据。添加更多数据的最简单方法是简单地水平翻转你的图像(如果与你的问题相关,也可以垂直翻转)。另一种流行的方法是随机生成与图像大小相同的噪声,然后将这种噪声添加到图像中。最后,如果你喜欢冒险,有很多关于使用生成对抗网络(GANs)来添加有意义的数据的研究。

四。解释结果,混淆矩阵

这是最重要的步骤之一,尽管经常被忽视。这一步被忽略的原因主要是因为数据昂贵且难以获得。因此,将一部分数据单独放在一边进行测试似乎是愚蠢的。然而,这对于建立您的绩效基准非常重要。

然而,除了要优化的相关性能变量之外,您还可以使用混淆矩阵可视化来深入了解您的数据。通过可视化错误分类的实例,您可以深入了解在描述整体类时哪些类型的图像未被充分代表。

动词 (verb 的缩写)数据采集和自动化改进

一旦您的模型被部署到某种应用程序中。您通常可以找到收集更多数据的方法,从而提高模型的性能和概化能力。

[## 自动数据收集

提高图像识别模型性能的最佳方法之一是添加更多数据进行训练!一些最…

towardsdatascience.com](/automatic-data-collection-to-improve-image-classifiers-232c2f0b2070)

结论

我相信这个工作流程是构建图像分类模型的一系列步骤。如果您想获得关于改进图像识别模型的更多提示,请点击此处。感谢您的阅读!

CShorten

Connor Shorten 是佛罗里达大西洋大学计算机科学专业的学生。对计算机视觉、深度学习和软件工程感兴趣。

人工智能的图像数据集

原文:https://towardsdatascience.com/image-datasets-for-artificial-intelligence-bbb12615edd7?source=collection_archive---------3-----------------------

在人工智能领域,数据就是力量。

人工智能算法以及它们如何相互融合是一门艺术,通过大学课程、在线培训以及观看 YouTube 视频的人逐渐了解这门艺术。人工智能是开源的,应该是。为了保护你的公司免受竞争,你可以做的是建立专有数据集。

有大量的数据集向公众开放。例如, Kaggle ,以及其他企业学术数据集,以及众多联邦市级数据源。我们在很多项目中使用这些,但是其他人也可以。你要的是造一些我没有的“特别”。例如,你不能在搜索方面打败谷歌,因为他们知道人们搜索什么,而你不知道。优势在于其数据集的规模和深度,而不仅仅是市场份额。

我们经常遇到构建人工智能解决方案的需求,在这种情况下,客户需要一个图像数据集来继续前进。客户端通常没有图像数据集来开始。他们不能简单地使用现成的解决方案或 API,因为现成卷积网络中典型的 1000 个对象并不像人们希望的那样广泛,而且区分两个类的分类器可能比有 1000 个的分类器更强大。当“输出类”(系统可以看到的事物类型)的数量很小时,做出错误预测的机会就很少,因此这些专门的模型往往工作得很好。

今天我想向大家介绍的是我们构建这些自定义图像数据集的一种方法。先说只有 2 类的情况:染病叶片健康叶片。这个想法是用人工智能来区分某处田地里健康和病态的叶子。

首先,我们安装了 images-scraper 和 nodejs,我们将抓取的图像限制为非 https URLs。我们确保网址有。jpg '结尾,这通常是格式良好的。我们接下来需要的是一组关键字,所以我们使用下面的关键字列表开始:

keywordList = ['healthy', 'thriving', 'growing', 'living', 'beautiful','nourishing','tasty','green']baseKeyword = 'leaf'

从这里,我们生成关键字列表和基本关键字的组合。例如:

('healthy leaf', 'thriving leaf', 'growing leaf', 'living leaf', 'beautiful leaf')

接下来,我们将每个组合传递到一个单独的 nodejs 线程中。scraper 将抓取的图像收集到一个基本目录中,每个关键字组合都有子文件夹。然后,我们运行脚本来删除重复和空的文件。

这是一个完整的例子,我们如何刮图像感染的叶子。

keywordList = ['sick', 'damaged', 'infected', 'dying', 'bacteria','virus','sickly','wilting']
baseKeyword = 'leaf'import lemayScraper as lsls.scrapeImages(keywordList, baseKeyword)

在这一点上,我们有 2 个文件夹,一个包含数千张健康叶子的图片(和许多垃圾图片),另一个包含数千张感染叶子的图片(和更多垃圾图片)。接下来的任务是手动浏览图像,并删除与树叶无关的图像(一个拿着雨伞的婴儿),然后再次浏览图像,并删除类型错误的图像(树叶的绘图、树叶的 3D 渲染等)。最后,人类操作员梳理图像,并添加他们认为第一遍所需的尽可能多的努力。在后期阶段,我们可能会选择裁剪图像,或做其他图像清理。在这个阶段,目标只是确保坏数据不会过滤到训练数据中。

Collected image data for healthy leaves (left) and infected leaves (right).

此时,训练人工智能进行图像识别的项目可以开始了。我们已经看到了收集图像数据的许多其他要求,因此您的项目的解决方案可能会有所不同。有时,我们会寻找在感知哈希方面相似的图像,如下例所示:

3 images from a scrape

上面的图片都是醒目的红色。也许它们来自于对单词“红色”和“停止”的刮擦。我们可以通过下面的代码看到它们是多么相似:

结果如下:

ffe2c38f8983073d c3991c6e763899c3 ffe3c3c0c0c1c0ec
False
s1-s2 47
s1-s3 20

在结果的第一行,我们看到每个图像都有一个唯一的散列。英语停止标志(s3.jpg)和禁止标志(s3.jpg)之间的差异大于英语和法语停止标志(s3.jpg 和 s3.jpg)之间的差异。这太酷了!用数学它明白了停止标志是相似的!

因此,我们能够对刮下的图像进行后处理,在没有人工干预的情况下,将与其他东西相似的东西收集成堆(子类)。我们有很多其他的脚本来帮助清理 scraper 输出。一旦我们在分类器训练过程中看到一个好的分类结果(混淆矩阵),我们就停止胡闹。在这篇文章中讨论了这个图像刮刀的起源,以及一些关于如何使用它的疯狂想法。

至于使用来自 web 抓取的数据所需的许可,以及其他知识产权问题,那已经超出了本文的范围。

因此,总之,抓取图像形成一个数据集是完全可行的。我们都在关注快节奏的开发和尽早展示价值,抓取图像是构建定制图像识别解决方案的重要组成部分。

如果你喜欢这篇关于构建图像数据集的文章,可以看看我过去读过最多的文章,比如“如何为人工智能项目定价”和“如何聘请人工智能顾问”除了与业务相关的文章,我还准备了一些关于寻求采用深度机器学习的公司所面临的其他问题的文章,如“没有云和 API 的机器学习

编码快乐!

-丹尼尔
丹尼尔@lemay.ai ←打个招呼。
LEMAY . AI
1(855)LEMAY-AI

您可能喜欢的其他文章:

keras 中从零开始的图像分类。初学者友好,中级刺激和专家刷新。

原文:https://towardsdatascience.com/image-detection-from-scratch-in-keras-f314872006c9?source=collection_archive---------0-----------------------

source: pixabay.com

上周末我在大声思考。

如果我有一个非常非常小的图像数据集,我自己捕获的,并想教计算机识别或区分一些特定的类别。

假设我有几千张图像,我想训练一个模型来自动检测一个类和另一个类。既然我只有这么少的数据,我能训练一个深度神经网络来成功地对这些图像进行分类吗?

嗯,在做了一些研究后,我发现必须用很少的数据训练深度神经网络是人们在计算机视觉领域遇到的常见情况。

Image source: pixabay.com

好吧,让我们面对现实吧,并不是每个人都可以像谷歌或人脸那样访问大数据,而且有些数据很难获得。

但是我也发现这个问题的解决方法很简单。所以今天我将带你训练一个卷积神经网络使用这一点点图像数据,你必须得到一个真正好的分类器,其准确率约为 81%。

在这篇的文章中,我介绍了一种叫做迁移学习的非常强大的技术,它帮助我们将准确率提高到大约 95%。

Image source: pixabay.com

好了,你可以出去开始收集数据了。

我将使用 K aggle 平台上现有的猫狗数据集。——是的,我很懒。我拿不到自己的数据。

kaggle.com

Kaggle 是全球数据科学和机器学习从业者的家园。他们举办了一些最大的数据科学竞赛,这是一个获得开源数据以及向获奖专家学习的好地方。

Yes i’m a Zindian. source: zindi.africa

我觉得我应该这么说。如果你来自非洲,我们有一个名为 Zindi 的新平台,它类似于 Kaggle ,但对非洲社会进行了微调。它包含从非洲企业和组织收集的数据集。这是防止 AI 偏见的一大步, Zindi 就是一个很棒的平台。

所以小心那些津迪亚人,我们来了。

好了,回到获取数据。我们前往 Kaggle 上的这个页面。这里我们有两个选择,我们可以下载数据并在我们的笔记本电脑上本地训练我们的模型,或者我们可以使用 Kaggle 内核,它为我们提供了更多的计算能力,访问 GPU,以及几乎所有预安装的用于机器学习和深度学习的库。

我不知道你怎么想,但我宁愿用 Kaggle 内核,除非我有 GPU。

source: pcmag.com

如果你买得起 GPU,或者你是一个游戏玩家,我完全虚构了这个词,并且已经有了一个 GPU,并且你想在你的 PC 上训练你的模型,因为你太喜欢你的 PC 了,那么你可以按照这个 教程 或者这个**one建立你自己的深度学习工作站。**********

对于其余懒惰或目前负担不起的 GP-us,让我们前往 K 阿格尔并启动这个引擎。

点击链接,我们传送到这里。

cats vs dogs kernel on kaggle

注意:当你访问一个 Kaggle 竞赛页面时,阅读数据描述通常是一个好主意。

接下来,点击内核,然后点击右上角的蓝色新内核按钮,这将要求您选择内核类型。选择笔记本,这样我们可以做一些交互式编程。

如果你不知道什么是笔记本或者需要刷新你的 notebooking 技能,这里的和这里的都是很棒的关于 Jupyter 笔记本的教程网站。****

点击 Notebook 为你创建一个新的私有内核,并自动将 dogs vs cats 数据集添加到你的文件路径——云中的当然还有****

给你的内核取个名字,并使用你的超级能力( GPU )来加快计算速度。

Your Notebook opens like this

现在我们的内核已经准备好了,让我们导入一些将要使用的库。键入下面的代码并按下 shift 回车 来运行单元格。

Import the following libraries

  1. cv2 cv2也叫**OpenCV,是 Python 等多种高级编程语言中可用的图像和视频处理库。它用于各种图像和视频分析,如面部识别和检测、车牌读取、照片编辑、高级机器人视觉、光学字符识别等。在本教程中,我们将使用它来读取和调整我们的图像。**
  2. NumPy 是 Python 中最流行的数学库。它使大型多维数组和矩阵的工作和计算变得非常容易和快速。它有大量的高级数学函数来处理这些数组。
  3. PandasPandas 是一个为 Python 编程语言编写的用于数据操作和分析的软件库。特别是,它提供了数据结构和操作来操作数字表和时间序列。****
  4. Matplotlib是 Python 的一个绘图库。它可以用来绘制线,条形图,图表,直方图,甚至显示图像。
  5. %matplotlib inline 是一个让我们的图出现在笔记本中的命令。
  6. 操作系统是一个内置的 python 包,用于访问你的计算机和文件系统。它可以用来显示目录中的内容,创建新的文件夹,甚至删除文件夹。
  7. random 将帮助我们创建随机数,这些随机数将在我们分割或打乱数据集时使用。
  8. gc 垃圾收集器的简称,是手动清理和删除不必要变量的重要工具。我们将在 Kaggle 内核上积极使用它,因为由于我们正在处理图像数据集,分配给我们的空闲内存可能会变满。

导入必要的库后,我们将图像读入内存。数据以 Zip 文件的形式存储在我们的内核中。

Our data

我们可以看到三个文件:

  1. sample submission.csv
    这是一个 csv(逗号分隔值)文件,用于在训练您的模型并在给您的测试文件上进行测试后进行提交。由于本次比赛已经结束,我们不能提交,所以我们将忽略此文件。
  2. test.zip
    该文件包含我们将在训练后测试我们的模型的图像,以了解我们的模型是否已经学会区分狗和猫。
  3. 这是我们模特的食物。它包含了我们将要用来教我们的模型一只狗或一只猫长什么样的数据。

现在,为了访问我们的训练图像,我们将使用我们之前导入的操作系统包。****

注意:kaggle 上的所有数据文件路径都以根目录 开始../输入。例如,这个内核中训练数据的文件路径将是../输入/训练

import our Images

  1. 在这里,我们为我们的训练和测试数据创建一个文件路径
  2. **这里我们创建两个变量 train_dogstrain_cats 。一个用于所有的狗图像,另一个用于猫图像。我们编写一个列表理解,使用命令 os.listdir() 获取列车数据 zip 文件中的所有图像,并检索名称中带有的所有图像。
    我们对猫的图像也是如此。
  3. 我们也得到我们的测试图像。
  4. 训练数据集总共包含 25,000 幅图像,但由于我们正在试验使用一个小数据集,并且我们显然只能使用很少的计算能力,因此我们将从两个类中仅提取 2000 幅图像。
    ** 2000 张狗图像和 2000 张猫图像,制作 4000 张图像的训练数据集。
    所以我们从 train_dogstrain_cats 中抓取前 2000 个图像,然后将它们连接成一个名为 train_imgs 的训练集。
  5. 非常重要!
    我们随机洗牌 train_imgs。
  6. 在这里,我们做一些清洁。你可能已经注意到了,我们现在有 train_imgs 意为 train_dogstrain_cats 变量是无用的,并且占用了不必要的空间。如果我们不删除它们,当我们开始训练我们的模型时,我们可能会耗尽内存。

好的,让我们来看看 train_imgs 中的一些图片。

lets view some cute dogs

  1. 从 matplotlib 导入图像绘图模块
  2. 运行 for 循环来绘制 train_imgs 中的前三幅图像

请记住这是一个随机列表,但幸运的是,当我运行代码时,前三个图像是由两只狗和一只猫组成的,请注意它们有不同的尺寸。

The last two images of plot

在下一个代码块中,我们将使用 cv2 模块来调整图像的大小。
首先让我们声明我们想要使用的新维度。在这里,我使用 150 乘 150 的高度和宽度和 3 个通道。

declare some important variables

彩色图像由 3 个通道组成,即红色、绿色和蓝色像素值的 3 个阵列。我们可以使用 1 个通道来读取灰度格式(黑白)的图像。

现在,让我们写一个小函数,它也有助于阅读,然后调整我们的图像到上面提到的高度和宽度。

helper function

  1. 创建一个新变量 X ,它将保存新的训练集,而 y 将保存我们的训练标签。(如果图像是狗,则为 1;如果图像是猫,则为 0)
  2. 我们一个接一个地读取我们的图像,并用 cv2 命令调整它们的大小。
  3. 如果图像是一只狗,我们将 1 添加到 y 中,如果图像是一只猫,我们将 0 添加到图像中。

现在,让我们调用我们的函数并处理图像。

*****X, y = read_and_process_image(train_imgs)*****

x 现在是图像像素值的数组,y 是标签的列表。我们来预览一下 x 中的第一张图片。

Yea, that’s what your computer calls a dog

我的朋友是一只狗。或者我们可以说我们的电脑称之为狗。等等!我怎么知道它是一只狗?好吧,让我们看看标签列表 y 中的对应值。

remember 1 for dog and 0 for cat

嗯,记得我们说过让 1 和 0 分别代表狗和猫。

还是不相信我。然后,让我们绘制 X 的前 5 个数组。我们不能用上面的matplotlib . imagempimg 模块绘制 X 中的图像,因为这些现在是像素数组,而不是原始的 jpg 文件。所以我们应该使用 imshow ()命令。****

plot the first five images

现在,我们确信我们的训练集包含了适当的狗和猫的图像,让我们看看我们的标签。记住我们总共有 4000 张图片(2000 只狗和 2000 只猫),因此我们的标签列表 y 应该包含 2000 张 1 和 2000 张 0。让我们画出这个并确认。

  1. 我们导入了 seaborn 包,这是另一个构建在 matplotlib 之上的绘图包,它给出了非常漂亮的绘图。
  2. 记住,我们是爱整洁的人,我们不会等着清洁工来为我们打扫卫生。所以我们删除了 train_imgs ,因为它已经被转换为一个数组并保存在 X.
  3. x 和 y 目前是 list 类型(python 数组的列表),我们将把它们转换成 numpy 数组,这样我们就可以把它输入到我们的模型中。
  4. 绘制一个彩色图表来确认我们的 y 标签变量中的类的数量

bar count of labels

太好了!我们有 2000 个狗和猫的班级。我们继续吧。

接下来让我们检查数据的形状。总是检查和确认你的数据的形状,这是非常重要的。

shape of our data

我们可以看到,我们的图像是一个秩为 4 的张量,或者我们可以说是一个 4 维数组,其尺寸为 4000 x 150 x 150 x 3,分别对应于批次大小、高度、宽度和通道。

我们的图像数组的形状对于我们将要构建的 keras 模型非常重要。该模型将(高度、宽度、通道)的数组作为输入

现在我们的数据已经准备好了(X,y ),我们可以开始训练,但是首先我们必须做一些非常重要的事情,那就是将我们的数据分成训练集和验证集。这是开始训练模型之前要做的最重要的事情之一。

对于拆分,我们将使用 python 中一个流行的机器学习包中的一个方便的函数,名为 sklearn

  1. sklearn 导入 train_test_split
  2. 我们告诉函数,我们希望将 20%的数据分配给验证集,而将另外 80%的数据分配给训练集。
  3. 这里我们打印了新的训练和验证集的形状

接下来,我们将声明在训练我们的模型时将使用的一些重要变量。

  1. 是的,我们还在打扫。
  2. 获取训练集和验证集的长度。

wheeeeew…现在是时候创建我们的模型了。

我们将使用卷积神经网络(convnet)来训练我们的模型。当涉及到计算机视觉问题时,Convets 是当前的标准。在任何图像问题上,它们总是胜过其他类型的神经网络。

刚接触 convnets?在这篇文章的最后,有一些很好的网站链接,你可以在那里了解它们。

在创建我们的模型时,我们将使用 KERAS

根据维基百科…

Keras 是用 Python 编写的开源神经网络库。它能够在 TensorFlow、微软认知工具包或 Theano 上运行。旨在实现深度神经网络的快速实验,它专注于用户友好、模块化和可扩展。

首先,让我们导入将要使用的必要的 keras 模块

  1. *****这里我们导入 keras 图层 模块 其中包含深度学习中使用的不同类型的图层,例如:
    **卷积层(主要用于计算机视觉)
    **池层(也用于计算机视觉)
    **递归层(主要用于序列和时间序列建模)
    *嵌入层(主要用于自然语言处理)
    规范化层
    等等
  2. *****这里我们导入 keras 模型 ,它包含两种类型:
    • *我们将在本教程中使用的顺序模型和
    • 带有函数式 API 的模型****
  3. 这里我们导入 kerasoptimizer,一个模块* 包含不同类型的反向传播算法用于训练我们的模型。这些优化器包括:
    **sgd(随机梯度下降)
    **rmsprop(均方根传播)
      • Adams
      • Adagrad
      • Adadelta*****
  4. 这里我们导入一个最重要的函数( ImageDataGenerator ),在处理小数据集时使用。以下是更多相关信息。

现在让我们创建我们的网络架构。我们将遵循一个流行、有效和简单的架构,叫做 VGGnet

slide from Elsever

网络架构只是我们排列卷积层的方式

我们将使用一个小的 vggnet,但你可以在下面看到,我们的过滤器大小随着我们向下分层而增加。

32 → 64 →128 →512 —最后一层是 1

  1. 这里我们创建一个序列模型。这告诉 keras 按顺序堆叠所有层。
  2. 这里我们通过调用来创建第一层。在我们创建的模型上添加()函数,并传递我们想要的图层类型——一个 Conv2D 图层。这第一层被称为输入层,有一些我们需要设置的重要参数。
    ****** 滤波器大小 [ 32 ]:这是输出维度的大小(即卷积中输出滤波器的数量)
    *** kernel _ size[3,3]: 这指定了 2D 卷积窗口的高度和宽度。
    激活 [' relu ']:我们选择一个激活函数,也称为非线性,供我们的神经网络使用。R eLU (整流线性单位)是当今最常用的激活函数,其他变体还有R
    eLU
    和 eLU 输入形状[150,150,3]: 还记得我们调整图像的尺寸吗?150 乘 150 对吗?我们在这里通过,包括通道 3。
    我们不传递第一个维度 4000,因为这是批量维度。
    ***
  3. 这里我们添加一个maxpool 2d图层。它的功能是减少输入特征的空间大小,因此有助于减少网络中的参数和计算的数量,从而有助于减少过拟合。

过拟合发生在我们的模型记忆训练数据的时候。该模型在训练时表现出色,但在测试时会失败。

  1. 这里我们添加一个展平层。conv2D 图层提取并学习空间要素,然后在展平后将其传递给密集图层。这是展平层的工作。****
  2. 这里我们添加一个值为 0.5 的下降层。Dropout 随机丢弃神经网络中的一些层,然后使用简化的网络进行学习。通过这种方式,网络学会在单个层上独立而不可靠。底线是,它有助于过度拟合。
    0.5 表示随机掉一半的图层。
  3. 最后一层的输出大小为 1,激活函数称为 sigmoid。 这是因为我们试图检测一张图片是狗还是猫。也就是说,我们希望模型输出图像是狗而不是猫的概率,这意味着我们需要一个概率分数,其中较高的值意味着分类器认为图像是狗,较低的值意味着它是猫。
    sigmoid 非常适合这种情况,因为它接受一组数字,并返回 0 到 1 范围内的概率分布。

我们可以通过调用 Keras 函数来预览我们的 convnet 的排列和参数大小。模型对象上的 summary()****

我们可以看到我们想要训练的参数的数量(300 多万)和不同层的一般排列。

下一步是编译我们的模型。

我们向 model.compile()命令传递三个参数

  1. lOSS[' binary _ cross entropy ']:我们指定一个损失函数,我们的优化器将最小化它。在这种情况下,因为我们正在处理两类问题,所以我们使用 二进制交叉熵损失****
  2. 还记得我们之前定义的 优化器 吗?我们将使用其中一个名为 rmsprop 的。这不是一个固定的选择,这是一个叫做 超参数调整 的过程的一部分,这可能就是世界级模型和幼稚模型的区别。
  3. 在这里,我们指定在训练后测量模型性能时要使用的指标。我们想知道我们的模型做得好不好。
    既然我们在做分类问题,那么精度指标 (acc) 是个不错的选择。
    注:您用来衡量模型性能的指标将取决于您正在处理的问题的类型。

最后,在我们开始训练我们的模型之前,我们需要执行一些规范化。即缩放我们的图像像素值,使其具有单位标准偏差和平均值 0。

我们将使用 Keras 中一个名为imagedata generator的重要模块,当我们在训练期间将图像输入模型时,它会执行一些重要的功能。******

但是……但是什么是图像数据生成器呢?

根据 Keras 的创建者 Fran ois Chollet的说法,Keras ImageDataGenerator()让我们可以快速设置 python 生成器,自动将图像文件转换为预处理张量,可以在训练期间直接输入到模型中。它很容易为我们执行以下功能:
1 .将 JPEG 内容解码为像素的 RGB 网格。
2。把这些转换成浮点张量。
3。将像素值(在 0 和 255 之间)重新缩放到[0,1]区间(神经网络在规格化数据时表现更好)。
4。它帮助我们轻松地增强图像。(这是我们将使用的一个重要特性,因为我们是在一个小数据集上进行训练的)。

好了,让我们创建我们的 ImageDataGenerator 对象。我们将创建两个生成器,一个用于训练集,另一个用于验证集。

  1. 我们将 rescale 选项传递给 ImageDataGenerator 对象。 重新标度=1。/255选项是一个非常重要的参数。它将图像像素值标准化为平均值为零,标准偏差为 1。它有助于您的模型有效地学习和更新其参数。****
  2. 第二组选项是图像增强。他们告诉 ImageDataGenerator 对图像随机应用一些变换。这将有助于扩大我们的数据集,提高泛化能力。
  3. 这里我们还为我们的验证集创建了一个 ImageDataGenerator 对象。注意:我们这里不做数据扩充。我们只执行 重新调整

既然我们有了 ImageDataGenerator 对象,让我们通过传递我们的训练和验证集从它们创建 python 生成器。

  1. 我们称之为 。我们在上面创建的数据生成器上的 flow( ) 方法传递数据和标签集。
    X_trainy_train 用于训练,然后 X_valy_val 用于验证。
    批次大小告诉数据生成器一次仅获取指定批次(在我们的例子中为 32)的图像。
  2. 现在我们通过调用来训练我们的网络。在模型上拟合()方法并传递一些参数。第一个参数是训练集imagedata generatorobject[train _ generator**]。****
  3. 这里我们指定每个时期 的 步数。这告诉我们的模型,在对我们的损失函数进行梯度更新之前,我们想要处理多少图像。
    总共 3200 张图像除以 32 的批量大小将得到 100 个步骤。这意味着我们将在整个训练集中一次对我们的模型进行总共 100 次梯度更新。
  4. 一个历元是整个训练集的一个完整周期或一遍。在我们的例子中,当我们按照我们的 steps_per_epoch 参数的指定进行 100 次梯度更新时,就达到了一个 epoch。
    E pochs = 64 ,意味着我们要检查我们的训练数据 64 次,每次我们将进行 100 次梯度更新。
  5. 我们传递我们的验证数据生成器。
  6. 我们也在这里设置步长。我将使用与上述相同的步长。

运行细胞开始训练…这需要一段时间。去推特上打扰某人吧…

仅仅过了 64 个时期,我就获得了大约 80%的准确率。

screenshot of model training

对于一个我们用很少的数据从零开始训练的模型来说,这已经不错了。

也许增加历元的数量和使用一些超参数,如批量大小和优化器,将有助于提高这个分数。

我将把那留给你去探索。

接下来,我们保存我们的模型,使用下面显示的简单的 Keras 函数,这样我们可以随时重用它,而不是在重新运行我们的笔记本时再次训练。

****#Save the modelmodel.save_weights('model_wieghts.h5')
model.save('model_keras.h5')****

我们将绘制一些训练集和验证集中的准确性和损失的图表,看看我们是否可以获得一些见解。

  1. 在训练一个 Keras 模型之后,它总是计算并保存我们在一个名为 history 的变量中编译我们的模型时指定的指标。我们可以提取这些值并绘制出来。
    :历史对象包含训练过程中发生的所有更新。
  2. 这里我们简单的从' acc' 列表中的数值个数得到我们 epoch 的大小。
  3. 这里我们绘制了精度与历元大小的关系。
  4. 这里我们绘制了损失与历元大小的关系。

Plot of accuracy against epochs

那么我们能从这个情节中学到什么呢?

  1. 首先要注意的是,我们没有过度拟合,因为训练和验证准确性非常接近,并且相互跟随。
  2. 我们还可以注意到,精度随着历元的增加而不断增加,这给我们一种直觉,即增加历元大小可能会给我们带来更高的精度。

Plot of loss against epochs

我们仍然没有过度拟合,因为训练和验证损失都呈下降趋势,就像上面的准确度图一样,如果我们增加历元大小,损失可能会更低..

所以,你已经有了一些直觉。现在尝试增加历元大小,并使用一些超参数。

在我结束本教程之前,我们将在测试集中的一些图像上测试我们的模型。

code to pre-process the test Images

我们在训练和验证集上执行相同的预处理。

  1. 我们读取测试集中的前 10 幅图像,并将其转换为数组列表。
    注: y_test 将为空,因为测试集没有标签。
  2. 我们将数组列表转换成一个大的 numpy 数组。
  3. 我们创建了一个测试 ImageDataGenerator ,并且只执行标准化。
    注意:我们不扩充测试集。

现在我们将创建一个简单的 for 循环,它遍历来自生成器的图像来进行预测。然后我们将绘制结果。

  1. 创建一个列表来保存我们将要生成的标签。
  2. 我们设置将要绘制的图像的图形大小。
  3. 这里我们通过调用ImageDataGenerator 提供的特定图像进行预测。predict( ) 方法在我们训练好的模型上。
  4. pred 变量是模型确定当前图像是狗的概率。
    因为我们给狗的标签是 1,所以高概率——至少大于平均 0.5——意味着我们的模型非常确信图像是狗,否则就是猫。
    因此,我们简单地创建一个 if -else 语句,如果概率大于 0.5,该语句将字符串“ Dog ”追加到 text_label。我们这样做是为了在绘图时给图像添加一个标题。
  5. 这里我们添加了一个支线剧情,这样我们就可以绘制多个图像。
  6. 这里,我们将预测的类作为标题添加到图像绘图中。
  7. 我们最终绘制出图像。

让我们看看我们的模型在以前看不到的图像上表现如何。

嗯…我们的模型从五幅图像中得到一个错误。我没说它处于最佳状态…至少现在还没有。

wheeew…这是一个很长的帖子,但我想这是值得的。在这个 下一个教程中,我们通过使用一个 预训练的网络,改进了我们的模型,达到了大约 95%的准确率。 一个过程叫做 转移学习。

source: pixabay.com

好了,再见了,祝你编码愉快。

**在 Github 上链接到这个笔记本**

CNN 和 Keras 上一些惊人的帖子和文章。

欢迎提问、评论和投稿。

推特 上跟我连线。

insta gram上跟我连线。****

图像处理类别(EGBE443) #1.2 —数字图像

原文:https://towardsdatascience.com/image-processing-class-0-2-digital-image-7509403b4c86?source=collection_archive---------10-----------------------

这篇文章是为了总结我在医学图像处理课上(EGBE443)学到的经验。如果我犯了什么错误,请纠正我。谢谢你。

上一篇文章是关于构建图像的最简单的方法。在这篇文章中,我将谈论什么是数字图像和每种文件格式的区别。

如果您还没有阅读上一篇文章,您可以点击下面的链接轻松找到它。😃

[## 图像处理类(EGBE443) #0.1 —图像采集

大家好!我叫皮查亚·西普克汉姆。我是玛希隆生物医学工程系四年级学生…

towardsdatascience.com](/image-processing-class-egbe443-0-1-image-aquisition-7e80cc89de84)

什么是数字图像?

D 数字图像是以计算机可以存储的形式(即以数字的形式)呈现的图像。这种形式易于操作,适用于图像处理。

制作“数码快照”的方法有以下几个必要步骤:

  1. 空间采样:将连续信号转化为离散表示。这一步被称为图像的“空间采样”,它取决于传感器和采集设备的几何形状。
  2. 时间采样:该过程通过定期测量入射到每个单独传感器元件上的光量来执行。
  3. 像素值的量化:所有的像素值都被转换成一个范围内的整数值,例如 8 位= 256 或 12 位= 4096。但是在某些情况下,使用浮点值。(例如,医学图像处理)

数字图像的坐标系统

尺寸为 M x N(列 x 行)的图像表示为图像矩阵 I。每个像素由它们所在的行和列表示,原点坐标在图像的左上角(u = 0,v =0)。所以最大列和最大行分别是 M-1 和 N-1。

在现实世界中,每次测量的像素数量;例如,每英寸点数或每英寸线条数被称为图像的''

每个像素的值取决于数据类型,该数据类型总是长度为 k (k 为 2 的幂)的二进制值,因此像素值可以是该范围内的任何值。k 值被称为图像的“比特深度”。

图像处理中你应该知道的另一个重要话题是‘图像文件格式’。**

图像文件格式

任何图像都存储在内存中,光栅图像包含按规则矩阵排列的像素值。相反,矢量图像使用连续坐标表示几何对象。如果放大光栅图像,图像的分辨率将会丢失,但在矢量图像中不会发生这种情况。

Raster image and Vector image

  1. 标记图像文件格式(TIFF)

TIFF 旨在满足不同领域的专业需求。这种格式支持各种类型的图像,也支持灰度和真彩色图像。TIFF 提供了多种不同的压缩方法(LZW、ZIP、CCITT 和 JPEG ),它可以在单个 TIFF 文件中存储多种不同大小和表现形式的图像。

典型 TIFF 文件的结构由标题和图像对象的链接列表组成。每个图像对象都由一个“标签”列表组成,其对应的条目后跟一个指向实际图像数据的指针。

The structure of a typical TIFF file for three image object.

2。图形交换格式(GIF)

GIF 格式支持多位深度索引颜色,并可以通过在单个文件中存储大量图像并按顺序显示它们来编码简单的动画。这种格式设计用于灰度和彩色图像,最大深度为 8 位,不支持真彩色。

3。便携式网络图形(PNG)

PNG 是作为 GIF 格式的替代而开发的。PNG 支持三种不同类型的图像:

  • 真彩色(3 x 16 位/像素)
  • 灰度(16 位/像素)
  • 索引(256 色)

PNG 为透明度提供了最大深度为 16 位的 alpha 通道。该通道只有一位深,并且该格式仅支持在一个文件中具有 2 行的最大 30 次方和 2 列的最大 30 次方的单个图像。

3。Windows 位图(BMP)

BMP 只是在 Windows 下使用,它支持灰度、真彩色和索引图像以及二进制图像,但每个像素都用一个完整的字节存储。

4。可移植位图格式(PBM)

PBM 格式将图像存储在人类可读的文本中,可以使用文本编辑器进行阅读和编辑。

Example of BPM file format read from text editor program.

5。JPEG

JPEG 是一种广泛使用的文件格式。JPEG 标准压缩方法取决于应用。在 RGB 图像的情况下,有三个主要步骤:

  • 颜色转换和下采样:将颜色转换到 YCbCr 空间。y 和 C 分别是亮度分量和颜色分量。
  • 频率空间中的余弦变换和量化:图像被分成 8 个块的网格,对于每个块,使用离散余弦变换来计算频谱。然后,将每个块的 64 个频谱系数量化到量化表中。
  • 无损压缩:用无损方法压缩数据。

The process of JPEG compression method in RGB image.

实际上,JPEG 不是一种文件格式,而是一种压缩方法。Eric Hamilton 和 IJG 开发了一种关于 JPEG 压缩方法的文件格式,称为“JPEG 文件交换格式”或 JFIF。此外,还有一种称为可交换图像文件格式(EXIF)的文件格式,它是 JPEG(JFIF)的变体,也可以将图像存储在数码相机上。

希望你对数字世界中的图像有更清楚的了解。课程的下一个主题是关于应用和修改数字图像。你可以通过点击下面的链接很容易地找到下一篇文章。

* [## 图像处理类(EGBE443) #2

这篇文章是为了总结我在医学图像处理课上(EGBE443)学到的经验。

medium.com](https://medium.com/@ptchaya.p/image-processing-class-egbe443-2-6beb2a8349e6)*

图像处理 1.1 级—图像采集

原文:https://towardsdatascience.com/image-processing-class-egbe443-0-1-image-aquisition-7e80cc89de84?source=collection_archive---------15-----------------------

大家好!我叫皮查亚。我是玛希隆大学生物医学工程系的四年级学生。

我写这篇文章的目的是总结我在医学图像处理课程或 EGBE443 中学到的经验。如果我犯了什么错误,请纠正我。谢谢你。

先说第一个题目, 图像采集

Image from NOPO Pinhole Camera

什么是图像采集过程?

图像采集是构建图像的过程。有一个执行这个过程的简单模型叫做 【针丨孔丨摄像机模型】

针丨孔丨摄像机型号

室内摄像机是生成图像的最简单的工具。它很容易制作,因为它的组件只是由一个漆黑的房间,一个叫做“针丨孔丨”的小洞和一个场景组成。为了形成图像,光线穿过针丨孔丨,入射到场景中。这会使图像变小并反转。

针丨孔丨摄像机的几何属性非常简单,如下图所示。

Geometric properties of the image from pinhole camera

从图中可以看出,物体位于离
针丨孔丨水平距离 Z 处,离光轴垂直距离 Y 处。f 是针丨孔丨和场景之间的距离。我们通过相似三角形原理找到了物体坐标 X,Y,Z 和图像坐标 X,Y,焦距 f 之间的关系。

The relationship between object coordinate and image coordinate.

然而,针丨孔丨照相机并不像预期的那样实用。较小的孔产生更清晰的图像,并且伴随着更长的曝光时间。所以使用 光学镜头型号 就是因为这些原因。为了使用,我们需要用薄透镜代替针丨孔丨。我们假设它无限薄。所以图像的几何形状类似于针丨孔丨摄像机的图像。薄透镜模型的几何特性如图所示。

The geometric properties of thin lens model

这个视频将向您展示如何制作针丨孔丨摄像机以及图像采集过程的结果。

我和我组里的朋友制作了一个针丨孔丨相机,并在不同的距离和快门速度下测试了第一个原型。这些是每个标准的结果。

  • 与物体的距离= 1 米。速度快门= 5 秒

  • 距离物体 1 米,快门速度 10 秒

  • 距离物体 2 米,速度快门 5 秒

  • 距离物体 2 米,快门 10 秒

如你所见,很容易制作!让我们开始吧,享受你的相机!😃

无论如何,可调整的图像必须是数字图像。所以在下一章,我会解释这个话题。它让你明白它是如何适合这种形式的修改。

下面是下一篇文章。请点击它前往:)

[## 图像处理类别#0.2 —数字图像

这篇文章是为了总结我在医学图像处理课上(EGBE443)学到的经验。

medium.com](https://medium.com/@ptchaya.p/image-processing-class-0-2-digital-image-7509403b4c86)

图像处理类别# 2-直方图

原文:https://towardsdatascience.com/image-processing-class-egbe443-2-6beb2a8349e6?source=collection_archive---------8-----------------------

这篇文章是为了总结我在医学图像处理课上(EGBE443)学到的经验。

这篇文章是关于基本的图像处理。如果你是这个领域的新手,你可以点击下面的链接阅读我的第一篇文章。😃

[## 图像处理类(EGBE443) #0.1 —图像采集

大家好!我叫皮查亚·西普克汉姆。我是玛希隆生物医学工程系四年级学生…

towardsdatascience.com](/image-processing-class-egbe443-0-1-image-aquisition-7e80cc89de84)

在之前的帖子中,我已经谈到了数字图像。在这篇文章中,你会了解到 直方图 ,这是一个必要的话题。

什么是直方图?

H istogram 是图像中强度值的频率分布。直方图条目取决于图像的比特深度(k)。例如,8 比特灰度图像包含 2⁸ = 256 的强度,强度在 0 到 255 的范围内。每个直方图条目被定义为 h(i)

h(i) =强度值为 I 的图像中像素值的数量

最小强度值 0 指的是颜色为黑色的像素,最大强度值 255 指的是颜色为白色的像素。

图像的直方图只提供统计信息,不提供空间信息。这是给出相同强度分布的两幅图像的例子。

Two different pictures, a. and b., provide the same histogram due to the equal number of the intensities.

计算直方图

在本节中,直方图是通过 python 编程代码(Python 3.6)的实现来计算的。

对于 python 3.6,有很多常用的图像处理模块,如 Pillow、Numpy、OpenCV 等。但是在这个程序中使用了 Pillow 和 Numpy 模块。

要从您的计算机导入图像,请使用此代码并更改您的路径,这是您的图像的位置。

img = Image.open('/PATH/') 

下一步,您需要将图像转换为灰度,并将变量类型转换为 numpy 数组,以便轻松计算直方图。

img = img.convert("L")  #Convert photo to gray scale
img = np.asarray(img)   #Convert variable type to numpy array

现在,图像准备计算直方图。用这个代码算算吧!

h = [0]*256                      
for x in range(img.shape[0]):        
    for y in range(img.shape[1]):            
        i = img[x,y]                  
        h[i] = h[i]+1

最后一步,变量 h 包含每个强度值的个数。我们可以使用 matplotlib 模块绘制直方图。这是我程序结果的一个例子。

The example image (.jpeg) and the plot of histogram

下一章,主题是关于直方图的点操作和均衡化。这可能有助于提高图像质量。点击下面的链接,你可以很容易地找到下一篇文章。

[## 图像处理类(EGBE443) #3 —点操作

这篇文章是为了总结我在医学图像处理课上(EGBE443)学到的经验。

medium.com](https://medium.com/@ptchaya.p/image-processing-class-egbe443-3-point-operation-477ad38334f5)

图像处理等级#3 —点操作

原文:https://towardsdatascience.com/image-processing-class-egbe443-3-point-operation-477ad38334f5?source=collection_archive---------14-----------------------

这篇文章是为了总结我在医学图像处理课上(EGBE443)学到的经验。

这篇文章是关于基本的图像处理。如果你是这个领域的新手,你可以点击下面的链接阅读我的第一篇文章。😃

[## 图像处理类(EGBE443) #0.1 —图像采集

大家好!我叫皮查亚·西普克汉姆。我是玛希隆生物医学工程系四年级学生…

towardsdatascience.com](/image-processing-class-egbe443-0-1-image-aquisition-7e80cc89de84)

有时,相机拍出的照片质量可能很差。它们是当时可怕光线的结果。因此,图像处理中提高图像质量的一个基本方法就是点运算。

概述

  • 点运算
  • 自动对比度调整
  • 改进的自动对比度
  • 直方图均衡
  • 直方图规定化

什么是点操作?

点操作是在不改变图像的大小、几何形状和局部结构的情况下修改像素值。新的像素值仅取决于先前的值。它们由函数 f(a)映射

如果函数 f()不依赖于坐标,则称之为"全局或"齐次"运算。另一种叫做非齐次点运算,如果依赖于坐标的话。非均匀点操作用于补偿图像采集期间的不均匀光照。

同质操作的常见示例包括:

  • 修改对比度和亮度
  • 通过夹紧限制结果
  • 反转图像
  • 阈值操作

点操作的实现对直方图的影响。提高亮度会将直方图向右移动,提高图像的对比度会扩展直方图。这些点操作通过包含常数的映射函数来映射强度,该常数是图像内容,例如最高强度和最低强度。

自动对比度调整

自动对比度调整是将图像中的最低强度和最高强度分别映射到全强度范围的最小和最大强度的方法(对于 8 位灰度图像,全范围为 0–255)。自动对比度调整的映射函数定义为

从等式中,a 最小值、a 最大值、a 低值和 a 高值分别是范围内的最小值强度、最大值强度、最低强度和最高强度。在 8 位图像的情况下,最小值=0,最大值=255,因此映射函数定义为

修改自动对比度

最高强度和最低强度可能是图像的噪声,我们通过使用分位数使图像的强度饱和来排除这些噪声。它可以通过下面的等式计算出来。

映射方程定义为

直方图均衡化

执行此任务是为了使两幅图像之间的差异更易于比较并在印刷出版物中使用。其原理是将图像直方图映射成近似均匀分布。映射函数定义为:

其中 H(a)是像素值 a 的累积直方图,K 是最大强度值,MN 是最近的累积强度。

您可以使用 OpenCV 模块将其应用到您的 python 代码中

equ = cv2.equalizeHist(img)

这是直方图均衡化的结果。

直方图规定化

该任务类似于直方图均衡化,但是该过程的目的是将直方图的分布函数映射到参考分布。为了独立于图像大小,图像强度需要归一化到范围 0-1。归一化直方图被解释为随机过程的概率密度函数。其中 p(i)是像素值 I 的概率,h(i)是所有强度值的总和。所以所有概率函数的和等于 1。

H(i)定义为累积直方图,H(i)的统计对应部分是离散分布函数 P()。这也称为累积分布函数(cdf)。

直方图规定化原理

如图所示,我们需要将图像 A 的 pdf 映射到参考图像 r。我们获得新的像素值 A ’,如下所示

因此,映射函数定义为

确保参考图像 R 的 pdf 是可逆的(具有 b =[0,1]的现有值)。

然而,修改图像的方法不仅仅是点操作,还有另一种方法,叫做 【滤镜】 。我将在下一章向你介绍更多的信息。回头见!

现在,下一章出版了。你可以点击下面的链接阅读。😄

[## 图像处理类(EGBE443) #4 —过滤器

这篇文章是为了总结我在医学图像处理课上(EGBE443)学到的经验。

medium.com](https://medium.com/@ptchaya.p/image-processing-class-egbe443-4-filters-aa1037676130)

图像处理类别#4 —过滤器

原文:https://towardsdatascience.com/image-processing-class-egbe443-4-filters-aa1037676130?source=collection_archive---------5-----------------------

这篇文章是为了总结我在医学图像处理课上(EGBE443)学到的经验。

这一章是关于过滤图像。为了更容易理解,你可以通过下面的链接阅读上一章关于点操作的内容。

[## 图像处理类(EGBE443) #3 —点操作

这篇文章是为了总结我在医学图像处理课上(EGBE443)学到的经验。

towardsdatascience.com](/image-processing-class-egbe443-3-point-operation-477ad38334f5)

如果你是图像处理的新手,你可以点击下面的链接阅读我的第一篇文章。😃

[## 图像处理类(EGBE443) #0.1 —图像采集

大家好!我叫皮查亚·西普克汉姆。我是玛希隆生物医学工程系四年级学生…

towardsdatascience.com](/image-processing-class-egbe443-0-1-image-aquisition-7e80cc89de84)

轮廓

  • 过滤
  • 线性过滤器
  • 线性滤波器的属性
  • 非线性滤波器

什么是过滤器?

对图像应用滤镜是修改图像的另一种方式。与点操作的不同之处在于滤波器使用一个以上的像素来产生新的像素值。例如,平滑滤波器,其通过其相邻像素值的平均值来替换像素值。滤波器分为两种, 线性滤波器非线性滤波器** 。

线性滤波器

L 线性滤波器是以线性方式(即,作为加权求和)操作支持区域中的像素值的滤波器。支持区域由 【滤波矩阵】 指定,由表示为 H(i,j) 。H 的大小称为“过滤区域”,过滤矩阵有自己的坐标系,I 是列索引,j 是行索引。它的中心是原点位置,它被称为“热点”。

Applying weight median filter to the image I, a hotspot location is at the orange shade (center of the filter matrix H)

应用滤镜

要对图像应用滤镜,请遵循以下步骤。

  • 在图像上移动滤波器矩阵 I 和 H(0,0)必须跟随当前图像位置(u,v)
  • 将每个滤波器系数 H(i,j)乘以相应的图像元素 I(u+i,v+j)
  • 对上一步的所有结果进行平均,这就是当前位置 I(u,v)的结果

所有步骤都可以用下面的等式来描述

线性滤波器的类型

  1. 平滑滤镜 (这个滤镜只有正整数。)
  • 箱式过滤器。 这个过滤器的所有成员都是一样的。
  • 高斯滤波器。 过滤构件的重量取决于构件的位置。过滤器的中心承受最大的重量,随着与中心的距离增加而减少。

2。不同的过滤器

  • 拉普拉斯或墨西哥帽状滤波器。 此过滤器的某些成员是负过滤器,它可以通过正成员和负成员的求和来计算。

3D structure, 2D structure and example of filter (a) Box filter (b) Gaussian filter and (c) Laplace filter

线性滤波器的特性

首先,我将介绍一个与线性滤波器相关的操作。这个操作叫做 “线性卷积”。 对于二维函数 I 和 H,卷积运算定义为等式

其中*是卷积运算。看看这个等式,你会发现这个操作提供了与线性滤波器相似的结果,该线性滤波器具有在水平和垂直轴上都反映的滤波器功能。卷积矩阵 H 可以称为

线性卷积的性质

  • 交换性
  • 线性
  • 结合性
  • 可分离性:核 H 可以表示为多个核的卷积,并且可以在二维核 x 和 y 中分离。

注意 :在线性特性中,在与核进行卷积之前,将标量值 b 加到图像 I 上,不等于将标量值 b 加到图像与核之间的卷积结果上。

非线性滤波器

使用平滑滤波器(一种线性滤波器)去除噪声,使图像结构、线条和边缘变得模糊。非线性滤波器用于解决这个问题,它以非线性方式工作。

非线性滤波器的类型

  • 最小和最大滤波: 原始图像的运动区域 R 中的最小值和最大值分别是最小和最大滤波的结果。这些过滤器被定义为

The equation of minimum and maximum filter

  • 中值滤波器: 结果的计算方法与最小值和最大值滤波器相同。移动区域 R 中所有值的中值是中值滤波的结果。这种滤波器通常用于消除图像中的椒盐噪声。该过滤器被定义为

下图显示了中值滤波器的工作原理

python 3 中过滤器的实现非常简单。对于盒子、高斯和中值滤波,可以使用cv2.boxFilter()cv2.GaussianBlur()cv2.medianBlur()

这是这个项目的结果

Applying Box filter, Gaussian filter and Median filter to remove salt pepper noise in the image

在这篇文章中,你已经知道了滤镜的类型以及如何将它们应用到图像中。这有助于提高图像质量(例如,去除噪声)。下一次,我将利用过滤器来检测边缘和锐化图像。

现在你可以点击下面的链接进入下一章。😃

** [## 图像处理类(EGBE443) #5 —边缘和轮廓

这篇文章是为了总结我在医学图像处理课上(EGBE443)学到的经验。

medium.com](https://medium.com/@ptchaya.p/image-processing-class-egbe443-5-edge-and-contour-d5d410f4483c)**

图像处理类别#5 —边缘和轮廓

原文:https://towardsdatascience.com/image-processing-class-egbe443-5-edge-and-contour-d5d410f4483c?source=collection_archive---------8-----------------------

这篇文章是为了总结我在医学图像处理课上(EGBE443)学到的经验。

这篇文章是关于基本的图像处理。如果你是这个领域的新手,你可以点击下面的链接阅读我的第一篇文章。😃

[## 图像处理类(EGBE443) #0.1 —图像采集

大家好!我叫皮查亚·西普克汉姆。我是玛希隆生物医学工程系四年级学生…

towardsdatascience.com](/image-processing-class-egbe443-0-1-image-aquisition-7e80cc89de84)

边缘和轮廓在人类视觉系统中起着重要的作用。边缘是由沿着特定方向的强度的局部变化引起的。这篇文章是关于边缘检测的各种方法。

轮廓

  • 基于梯度边缘检测
  • 边缘算子
  • 二阶导数边缘检测
  • 边缘锐化

基于梯度边缘检测

这种边缘检测方法从沿着一条图像线的强度变化或强度轮廓检测边缘。因为基本上,它是由一阶导数计算出来的。在图像中,一阶导数函数需要估计,可以表示为它在位置 u 处切线的斜率。

多维函数沿一个轴的导数称为【偏导数】。因此,图像函数 I(u,v)沿 u 轴和 v 轴的偏导数表现为以下函数。

该函数被称为“梯度向量”,梯度的大小可以通过下式计算

沿着 x 和 y 轴的一阶导数函数可以实现为具有系数矩阵的线性滤波器

边缘算子

很多边缘算子的基本原理都是来自于一阶导数函数。它们的不同之处仅在于过滤器中组件的组合方式。

  • 普-索二氏手术

这些方法使用在 3 个相邻行和列上延伸的线性滤波器。对于 Prewitt 算子,沿 x 和 y 轴的滤波器 H 的形式为

和 Sobel 算子,滤波器 H 沿 x 和 y 轴的形式为

通过对 Prewitt 算子和 Sobel 算子进行适当的缩放,我们可以得到估计的局部梯度分量。

对图像应用梯度滤波器,给出 x 和 y 轴的两个梯度图像,Dx 和 d y

Dx 和 Dy 用于计算每个图像位置(u,v)的边缘奇异值 E 和方向。

总之,这些过滤器的过程如下所示

罗伯茨算子

这也是最简单的方法。两个尺寸为 2×2 的小滤波器用于边缘检测。

这些是这两个小过滤器的结果。

罗盘操作员

该方法不仅开发了单对滤波器,还开发了八个方向上 45 度方向的滤波器:

边缘强度和方向也需要被计算,但是它们以不同的方式被计算。边缘强度由来自八个滤波器的梯度图像的最大值来定义。

并且局部边缘方向被定义为

二阶导数边缘检测

这个想法就是这么简单。边缘位于一阶导数结果的最大值和最小值上。但是在二阶导数中,边缘位于过零点,如下图所示。

这种算子的一个常见例子是将高斯平滑滤波器和二阶导数(拉普拉斯)滤波器结合在一起的“拉普拉斯-高斯”(LoG) 算子。

边缘锐化

该任务通常用于解决扫描或缩放后图像锐度损失的问题。想法是放大图像分量的高频。这些过程显示了如何锐化图像的边缘。

  • 用拉普拉斯滤波器锐化边缘(二阶导数):通过减去二阶导数的某个分数 w 来锐化边缘。
  • 反锐化掩模:该方法包括两个主要步骤:

1.通过用内核 H(平滑滤波器)减去图像 I 的平滑版本来生成掩模 M。

2.将因子 a 加权到掩模 M 上,并添加到原始图像 I 上

我用 Python 3 实现了边缘检测,这是结果

这是我学到的边缘检测的基础,边缘检测是灵活的,它取决于你的应用。所以在下一章,可能是我图像处理的最后一章,我会描述 形态滤波器。再见:)

现在,下一章在这里!请点击下面的链接。

[## 图像处理类(EGBE443) #6—形态滤波器

这篇文章是为了总结我在医学图像处理课上(EGBE443)学到的经验。

medium.com](https://medium.com/@ptchaya.p/image-processing-class-egbe443-6-morphological-filter-e952c1ec886e)

图像处理类#6 —形态滤波器

原文:https://towardsdatascience.com/image-processing-class-egbe443-6-morphological-filter-e952c1ec886e?source=collection_archive---------13-----------------------

这篇文章是为了总结我在医学图像处理课上(EGBE443)学到的经验。

这篇文章是关于基本的图像处理。如果你是这个领域的新手,你可以点击下面的链接阅读我的第一篇文章。😃

[## 图像处理类(EGBE443) #0.1 —图像采集

大家好!我叫皮查亚·西普克汉姆。我是玛希隆生物医学工程系四年级学生…

towardsdatascience.com](/image-processing-class-egbe443-0-1-image-aquisition-7e80cc89de84)

在前一章中,我已经谈到了一种使用中值滤波器去除噪声的方法。中值滤波使图像结构发生了很大变化。下图显示了对二值图像应用中值滤波的结果。移除小结构、单线和点,并填充小尺寸孔。

所以在这一章中,我将介绍一个克服这个问题的想法。它被称为“”。

Shrink and grow process

形态滤波器

形态滤波器的思想是收缩和放任生长的过程。单词“收缩”意味着使用中值滤波器来圆化大的结构并移除小的结构,并且在生长过程中,剩余的结构以相同的量生长回来。

首先描述二值图像的形态学操作,并且将在下面的概述中讨论。

概述

  • 二元滤波器的结构元素
  • 膨胀和侵蚀
  • 复合操作

结构化元素

在形态滤波器中,矩阵中的每个元素称为“结构元素”,而不是线性滤波器中的系数矩阵。结构化元素只包含值 0 和 1。并且过滤器的热点是深色遮光元件。

二进制图像被描述为多组二维坐标点。这叫做 “点集” Q,点集由所有前景像素的坐标对 p = (u,v)组成。点集的一些操作类似于其他图像中的操作。对二值图像求逆运算是补码运算,对两个二值图像求并运算。通过将向量 d 加到点 p,将二进制图像 I 移动某个坐标向量 d,或者将二进制图像 I 的反射乘以-1 到点 p。

膨胀和侵蚀

  • 膨胀 是一个形态学操作符,它适用于我之前提到的生长过程。该算子的方程定义为

  • 侵蚀 是一个形态学操作符,也适用于我之前提到的收缩过程,等式定义为

膨胀和侵蚀的特性

  • 可交换的:仅在膨胀中
  • 联想:仅在膨胀中

注意: 中的侵蚀与膨胀相反,不具有交换性。

此外,腐蚀和膨胀是 对决 ,因为前景的膨胀可以通过背景的腐蚀来完成,随后的结果是两种不同性质但工作相似

复合操作

在形态学过程中,膨胀和腐蚀共同作用于复合运算。有常用的方法来表示这两种操作的顺序,打开和关闭。开放表示侵蚀,随后以相反的方式膨胀和关闭。

Opening and Closing process respectively

在打开前景等于关闭背景的意义上,打开和关闭也是双重的。

形态滤波器也可以应用于灰度图像,但在不同的定义。它是最小和最大运算符的推广。我将在下面的大纲中描述。

轮廓

  • 结构化元素
  • 膨胀和侵蚀
  • 打开和关闭

结构化元素

在灰度形态学中,结构元素被定义为实值 2D 函数,而不是点集

H 中的值可以是负值或零值。但与线性卷积不同,它使用零元素来计算结果。如果您不想在某个位置使用元素,您可以在该位置不放置元素。

膨胀和侵蚀

灰度形态学中膨胀和腐蚀的结果是由最大值和最小值运算贡献的。

对于膨胀,结果是 H 中的值的最大值加到当前子图像。

对于侵蚀,结果是差值的最小值。

这些操作会造成负值,所以我们需要对计算后的结果进行箝位。

Example of dilation in gray-scale morphology

打开和关闭

灰度形态学中的打开和关闭与二值形态学中的工作方式相同。区别只是膨胀和侵蚀中的操作符。

对于使用 OpenCV 模块在 Python 3 中的实现,可以使用函数cv2.erode(input,size)cv2.dilate(input,size)

这是程序的结果,侵蚀和扩张,打开和关闭。

The result of erosion and dilation of the program.

The result of opening and closing from the program.

这是我关于图像处理的最后一篇文章。感谢您阅读并关注我的帖子。继续享受 图像处理 !我很快就回来,祝你好运。😃

路上的图像识别

原文:https://towardsdatascience.com/image-recognition-on-the-road-6ed85bb08292?source=collection_archive---------6-----------------------

当谷歌宣布他们开源其内部物体检测系统 Tensorflow 物体检测 API 时,我知道必须尝试一下。在图像中检测物体是一个长期的挑战,由于深度学习的一系列研究,近年来已经取得了巨大的进展。这是一种非常适合深度学习的任务:易于描述和直观掌握,但很难正式解决。

谷歌的 API 提供了五种最先进的 Tensorflow 模型,可以识别和定位图像中的多个对象。这些型号涵盖了从轻量级(用于在手机上实时工作)到重型(计算成本更高但更精确)的所有型号。他们还在 COCO 数据集上对每个模型进行了预训练,这样它们就可以检测出 90 种现成的常见物体类别。还包括一个 Jupyter 笔记本,演示如何使用他们预先训练好的模型。

我设法拍了一些南湾交通路口的照片。对于检测通过十字路口的机动车、骑自行车的人和行人,有几个有前途的应用:基于观察到的汽车数量的更智能的交通灯信号定时,通过提醒司机注意迎面而来的车辆来预防事故,以及识别经常发生交通堵塞的区域。

由于要在十字路口检测的对象属于 COCO 的常见类别,所以我能够使用预先训练的模型。这意味着我不必忍受收集带标签的数据集和旋转 GPU 时钟周期来训练的单调乏味。下面是(相当粒状)原始图像。

而这里是运行最精确模型后的输出,faster _ rcnn _ inception _ resnet _ v2 _ atrous _ coco

Box colors and their classifications: {Light green: car, Purple: truck, Neon green: person, Pink: vase, White: motorcycle, Darker Green: traffic light}

结果给我留下了深刻的印象!它克服了几个障碍:低分辨率、重影、遮挡和缺乏颜色,但仍能识别每辆汽车、摩托车和骑摩托车的人。它还发现人行道上有一名行人。它确实犯了把树干归类为花瓶的错误(粉色方框)。

总而言之,Tensorflow 对象检测 API 是一个用于对象检测和定位的优秀系统。它对较差的图像质量很鲁棒,并且使用简单。

图像分割:Kaggle 体验

原文:https://towardsdatascience.com/image-segmentation-kaggle-experience-9a41cb8924f0?source=collection_archive---------11-----------------------

今天我在 Kaggle 上获得了我的第一枚金牌,参加了空中客车船舶探测挑战赛。我们的 3 人团队(奥列格·亚罗舍夫斯基德米特里·达涅夫斯基弗拉德·什米赫洛)在卫星图像上分割船只的任务中获得了 884 名中的第 4 名。之前,我们的团队在地震图像上分割盐层的类似比赛中获得了 3234 名中的第 30 名( TGS 盐识别挑战赛)。我决定这是一个分享我参加竞争性机器学习的经验的好机会。

重要的是要强调,虽然我们在这些比赛之前在计算机视觉和深度学习方面有一些经验,但我们从未做过任何与语义或实例分割相关的高级东西。为了取得好成绩,我们必须学习很多东西,并以非常快的速度工作。下面是分割问题的概述和我们解决方案的更详细的概要。

什么是图像分割?这是一项非常常见的计算机视觉任务,要求您为图像中的每个像素分配一些标签,描述这个特定像素是属于某个对象(例如船只)还是属于某个背景(例如水或地面)。有许多不同的技术可以解决图像分割问题,但在本文中,我想重点关注近年来利用的方法,尤其是基于深度学习的方法。

Photo taken from satellite and corresponding segmentation mask

这个想法是训练一个神经网络,在给定原始图像数据的情况下,给图像中的每个像素分配一个标签,特别适合这个问题的架构是 U-Net 。U-Net 是一种卷积神经网络,最初设计用于执行医学图像分割,但它在各种各样的任务中工作得很好,从分割显微镜图像上的细胞到检测卫星照片上的船只或房屋。

U-Net 由编码器和解码器网络组成。编码器网络负责构建从简单的特征(如边缘和形状)到复杂的特征(如船只、人脸、汽车等)的层次结构。解码器负责将细粒度的低级特征与粗粒度的高级特征合并,逐渐恢复位置信息,以实现精确的逐像素分割。

U-Net architecture (source: https://arxiv.org/abs/1505.04597)

你可以对默认的 U-Net 架构做很多调整,以提高它在特定情况下的性能。对于计算机视觉任务,使用迁移学习几乎总是一个好主意。你需要做的是将在不同任务上训练的网络参数用于你的问题。这是可行的,因为对于网络来说,当它已经有了关于边缘和形状的知识时,学习相关特征要比从头开始容易得多。这就是为什么我们使用 ImageNet 上预训练的 SE-ResNeXt-50 网络作为我们的编码器。至于解码器,我们从 AlbuNet 获得了灵感,它使用的架构与最初 U-Net 论文中描述的略有不同。

这将我们带到对默认 U-Net-ResNet 架构的第一个重要调整。默认情况下,为了减少计算成本,ResNet 的第一层(以及许多其他为图像分类设计的神经网络)应用 7×7 步距 2 卷积,有人可能会认为应用步距 2 卷积可能会丢失精确的逐像素分割所需的许多重要信息,经过一些简化,我们可以说,将步距 2 conv 应用于 256×256 图像类似于将步距 1 conv 应用于 128×128 图像,这意味着我们试图预测两倍于网络“看到”的图像大小的掩模。这对于在照片和其他任务中分割人的大多数情况是可以的,在这些情况下,我们主要处理大型对象,网络可以从上下文中恢复大部分信息,但在分割非常小的船只(20-30 个正像素)的情况下,这可能是至关重要的,因此我们在 ResNet 的第一层中从步幅 2 移动到步幅 1 卷积,并观察到分数的良好提升。缺点之一是,这种调整增加了巨大的计算开销,因为网络中的每个特征地图现在都是原来的两倍大。这大大减少了批量大小,降低了网络速度,但一个时期的训练时间仍然在足够的时间内,因为我们是在随机的 256 乘 256 作物上训练的,这将我们带到下一点。

为了降低计算成本,加快训练速度并增加批量大小,我们对随机的 256 乘 256 的作物进行了训练,这种方法的问题是,训练集中只有一小部分图像实际上至少有一些积极的标签,其中大多数只是空的,随机作物的情况甚至更糟,因为这些作物几乎总是根本没有船只。这导致了巨大的类别不平衡,这是图像分割中普遍面临的问题。

为什么这不好?这是不好的,因为为多数类计算的损失超过为少数类计算的损失,导致非常低的误差信号。有许多解决方案可以克服这个问题,这些解决方案在特定情况下有效,其中大多数是关于选择正确的损失函数(如焦点损失、骰子损失、平衡交叉熵)或重采样数据集以获得更好的类分布。

一个非常巧妙的技术被设计用来克服阶级不平衡,这个技术非常有效。这个想法是随机裁剪图像的一部分,这样至少有一些积极的像素出现在裁剪中,这大大提高了分数,在我看来,这是一个关键的设计决策,使我们比其他参与者更有优势。

在进行人工故障分析时,我们观察到两个问题:大船检测和对小物体(例如石油平台)的误报。我们认为假阳性的问题可能与智能作物逻辑有关,但没有时间来检查这是否是真的。

为了克服假阳性问题,我们决定训练一个额外的基于 CNN 的二元空/非空分类器。人们可能会认为 U-Net 擅长空/非空分类,但在实践中它容易犯分类错误。另一方面,专用分类器明确地最小化了错误分类率,并且由于它没有解码器,所以训练起来要快得多。如果我们考虑到数据集中有大约 80%的空图像,假阳性问题会变得更加严重。利用非空图像的过采样在所有可用图像上训练分类器,以克服类别不平衡。我们认为性能良好的二进制分类器对本次比赛至关重要,我们认为这是我们从公共排行榜的第 26 位跃升至私人排行榜第 4 位的主要原因之一。一个单独的分类模型也导致了更快的推断:我们没有用慢速 U-Net 模型预测所有 15k 图像,而是只预测了大约 3k,因为其余的已经被分类器作为空图像丢弃了。

大型船只的问题没有假阳性那么严重,但是我们仍然对我们的模型进行了一些修改,以更好地捕捉这些大型实例。也就是说,我们在 U-Net 模型的底部增加了一个额外的卷积层,由于计算成本增加,我们在开始时将其丢弃。这个简单的技巧增加了我们模型的感受域,使它们能够捕捉更多的全球背景。

同样重要的是要提到,这项任务是一种称为实例分割的图像分割。在实例分割中,您不仅必须标记图像中的每个像素,还必须为唯一的对象分隔分割遮罩。这意味着我们必须有一种方法来区分哪些像素属于一艘船,哪些属于另一艘船。我们使用了一种叫做分水岭的方法来将蒙版分成实例。

在本教程的第 2 部分,我将更多地关注我们的方法和我们尝试的东西的技术细节,我还将分享这次比赛的源代码,敬请期待!

在 Tensorflow 中使用各种自动编码器进行图像分割

原文:https://towardsdatascience.com/image-segmentation-using-varieties-of-auto-encoders-in-tensorflow-manual-back-prop-with-tf-2e688f2a98f7?source=collection_archive---------8-----------------------

GIF from this website

我想我需要练习表演分段,因此我发了这个帖子。我也想探索自动编码器的世界。下面是我想探究的案例。

情况 1)普通全卷积自动编码器
情况 2)多损耗自动编码器
情况 3)重复全卷积自动编码器
情况 4)全卷积
变分自动编码器

情况 1)普通全卷积自动编码器

蓝框 →卷积层
红框 →转置卷积层

现在,上述网络具有最简单的结构,其中输入是彩色图像,输出是分段的掩蔽图像。现在让我们看看这个网络的结果。

总的来说,网络在检测图像中的物体方面做得不错,正如上面测试图像的结果所示。它实际上做了一个很好的基础网络,下面是为结果创建的 gif。

左图 Gif →为一段时间内的训练图像生成的遮罩
右图 Gif →为一段时间内的测试图像生成的遮罩
右图 →训练期间的一段时间内的成本

情况 2)多损耗自动编码器

Image from this paper

这次我的灵感来自于论文“用于由粗到细的密集语义图像标注的门控反馈细化网络”,论文作者不仅引入了多损失函数,还引入了门控网络。在这里,我将只看到多重损失函数的影响。

**

对于具有多重损失函数的网络,看起来图像的某些部分比基本网络更清晰。这个网络做得很好,特别是粉红色花的形象。

左图 Gif →生成的训练图像随时间变化的蒙版
右图 Gif →生成的测试图像随时间变化的蒙版
右图 →训练期间的成本随时间变化

情况 3)重复全卷积自动编码器

**

蓝框 →卷积层
红框 →普通重复和卷积层

现在,这个网络的架构与之前的完全相同,但我只是想看看如果我们不使用转置卷积运算会发生什么。而只是天真地重复像素值两次,并执行卷积?

**

如上所述,当我们仅使用卷积运算并天真地重复像素来执行上采样时,生成的遮罩是位清晰和平滑的。但是,我们可以在生成的蒙版中观察到一些随机的黑点。

左图 Gif →为一段时间内的训练图像生成的遮罩
右图 Gif →为一段时间内的测试图像生成的遮罩
右图 →训练期间的一段时间内的成本

情况 4)全卷积 变分自动编码器

我从未见过任何用于分段目的的自动编码器的变化。(如果有人知道论文的名字请告诉我!)但我想使用它,下面是生成的面具。关于这个网络生成的掩码,我注意到的一件事是掩码中存在的噪声量,这可能是因为我们在训练期间从正态分布中抽取样本。

左图 Gif →为一段时间内的训练图像生成的遮罩
右图 Gif →为一段时间内的测试图像生成的遮罩
右图 →训练期间的一段时间内的成本

互动码

对于 Google Colab,你需要一个 Google 帐户来查看代码,而且你不能在 Google Colab 中运行只读脚本,所以在你的操场上复制一份。最后,我永远不会请求允许访问你在 Google Drive 上的文件,仅供参考。编码快乐!

要访问案例 a 的代码,请点击此处。
要访问案例 b 的代码,请点击此处。
要访问案例 c 的代码,请点击此处。
要访问案例 d 的代码,请点击此处

最后的话

现在必须指出的是,所有这些模型都不能直接相互比较。超参数存在差异。但是我们仍然可以得到每个建筑的总体效果。

如果发现任何错误,请发电子邮件到 jae.duk.seo@gmail.com 给我,如果你想看我所有写作的列表,请点击这里查看我的网站。

同时,在我的推特这里关注我,并访问我的网站,或我的 Youtube 频道了解更多内容。我还实现了广残网,请点击这里查看博文 pos t。

参考

  1. 图像调整:转换图像内容—浏览 v0.15.dev0 文档。(2018).Scikit-image.org。检索于 2018 年 7 月 9 日,来自http://sci kit-image . org/docs/dev/user _ guide/transforming _ image _ data . html
  2. 伊斯兰,m .,罗昌,m .,那霸,s .,布鲁斯,n .,,王,Y. (2018)。用于由粗到细的稠密语义图像标注的门控反馈细化网络。Arxiv.org。检索于 2018 年 7 月 9 日,来自https://arxiv.org/abs/1806.11266
  3. 直观地理解变分自动编码器-走向数据科学。(2018).走向数据科学。检索于 2018 年 7 月 9 日,来自https://towards data science . com/直觉-理解-变分-自动编码器-1bfe67eb5daf
  4. 图片|张量流。(2018).张量流。检索于 2018 年 7 月 9 日,来自https://www.tensorflow.org/api_guides/python/image
  5. tf.random_normal | TensorFlow。(2018).张量流。检索于 2018 年 7 月 9 日,来自https://www.tensorflow.org/api_docs/python/tf/random_normal

使用自动编码器的图像相似性

原文:https://towardsdatascience.com/image-similarity-with-auto-encoders-937f6f3feaba?source=collection_archive---------16-----------------------

计算机视觉项目中一个非常具有挑战性的任务是确定图像之间的相似性。像每个像素的平均差异这样的东西实际上只是测量图像之间颜色使用的差异,而不是图像的任何真正的语义特征。

自动编码器通过编码器和解码器网络工作。编码器获取输入图像,并通过一个或多个隐藏层对其进行映射,直到最终达到具有比原始图像低得多的维度的隐藏层表示,例如 2 或 5 个神经元。然后,解码器将低维层中神经元的输出映射回原始图像。原始图像和从编码器→解码器重建的图像之间的差异被称为重建损失,并用于训练网络。

这如何用于图像相似性?

我们可以获取两幅图像,将它们通过自动编码器,并检查低维表示中的激活,以确定图像之间的相似性。

当表现为 2 或 3 维时,可视化这些激活很容易完成,但是对于更高维,我们需要使用聚类技术进行可视化,例如 t-SNE。T-SNE 聚类创建一个较低维度的映射,然后在较高维度中保持空间距离。我们可以利用这一点得出自动编码特征空间的可视化,从而得出图像之间的视觉差异。

我们可以通过在编码器中添加卷积层和在解码器中添加去卷积层来增强图像自动编码器的功能。解卷积层可以被认为类似于 DCGAN (深度卷积生成对抗网络)中的生成器网络。

视觉相似性的应用

视觉相似性度量有许多有趣的应用,例如图像推荐和搜索。然而,一个非常有趣的应用是数据聚类和标记未标记数据。许多深度学习项目有大量未标记的数据,很难找出如何标记这些数据。基于自动编码器的聚类是解决这个问题的好方法。感谢阅读!

CShorten

Connor Shorten 是佛罗里达大西洋大学计算机科学专业的学生。对深度学习和软件工程感兴趣。

使用 OpenCV 进行图像拼接

原文:https://towardsdatascience.com/image-stitching-using-opencv-817779c86a83?source=collection_archive---------2-----------------------

如你所知,Google photos 应用程序具有令人惊叹的自动功能,如视频制作、全景拼接、拼贴制作、根据照片中人的存在整理照片等等。我一直想知道为什么这些都是可能的。但是有一天,我觉得自己做全景拼接非常酷。

当我要做一个图像拼接的项目时,我感到非常兴奋。当我终于成功地建立了我自己的图像拼接器时,那是一个灵光一现的时刻:)。我在Python——我一直最喜欢的语言和使用 OpenCV 3.1.0 中做的。

尽管互联网上有很多这方面的资源,但今天我想和代码一起展示我的工作。下面的代码和解释都是为了把两张图片拼接在一起。

首先,让我们导入必要的模块。

import cv2
import numpy as np
import matplotlib.pyplot as plt
from random import randrange

正如我们所知,我们正在拼接 2 幅图像,让我们来阅读它们。

left.jpg and right.jpg

img_ = cv2.imread(‘right.JPG’)
img1 = cv2.cvtColor(img_,cv2.COLOR_BGR2GRAY)img = cv2.imread(‘left.JPG’)
img2 = cv2.cvtColor(img,cv2.COLOR_BGR2GRAY)

cv2.cvtColor 将输入的 RGB 图像转换成灰度形式。

对于图像拼接,我们遵循以下主要步骤:

  1. 计算两幅图像的 sift 关键点和描述符。
  2. 计算一幅图像中的每个描述符和另一幅图像中的每个描述符之间的距离。
  3. 为图像的每个描述符选择前“m”个匹配项。
  4. 运行 RANSAC 来估计单应性
  5. 缝合时要对齐的经线
  6. 现在把它们缝在一起

非常感谢…,

首先,我们必须找出两幅图像中匹配的特征。这些最匹配的特征充当缝合的基础。我们提取两幅图像的关键点和 sift 描述符,如下所示:

sift = cv2.xfeatures2d.SIFT_create()
# find the keypoints and descriptors with SIFT
kp1, des1 = sift.detectAndCompute(img1,None)
kp2, des2 = sift.detectAndCompute(img2,None)

kp1 和 kp2 是关键点,des1 和 des2 是相应图像的描述符。

现在,在一幅图像中获得的描述符也将在该图像中被识别。我们的做法如下:

bf = cv2.BFMatcher()
matches = bf.knnMatch(des1,des2, k=2)

BFMatcher() 匹配更相似的特征。当我们设置参数 k=2 时,我们要求 knnMatcher 为每个描述符给出 2 个最佳匹配。

“匹配”是一个列表列表,其中每个子列表由“k”个对象组成。为了理解这一点,并更好地跟踪接下来的部分,请通过这个

通常在图像中,这些特征很有可能存在于图像的许多地方。这可能会误导我们在实验中使用琐碎的特征。因此,我们从所有匹配中筛选出最佳匹配。因此,我们使用上面获得的前 2 个匹配来应用比率测试。如果下面定义的比率明显大于规定的比率,我们认为匹配。

# Apply ratio test
good = []
for m in matches:
if m[0].distance < 0.5*m[1].distance:
good.append(m)
matches = np.asarray(good)

现在是对齐图像的时候了。如您所知,执行转换需要单应矩阵,并且单应矩阵需要至少 4 个匹配,我们执行以下操作。点击了解更多

if len(matches[:,0]) >= 4:
src = np.float32([ kp1[m.queryIdx].pt for m in matches[:,0] ]).reshape(-1,1,2)
dst = np.float32([ kp2[m.trainIdx].pt for m in matches[:,0] ]).reshape(-1,1,2)H, masked = cv2.findHomography(src, dst, cv2.RANSAC, 5.0)
#print H
else:
raise AssertionError(“Can’t find enough keypoints.”)

最后是最后一部分,图像的拼接。既然我们已经找到了变换的单应性,现在我们可以继续将它们扭曲并缝合在一起:

dst = cv2.warpPerspective(img_,H,(img.shape[1] + img_.shape[1], img.shape[0]))
plt.subplot(122),plt.imshow(dst),plt.title(‘Warped Image’)
plt.show()
plt.figure()
dst[0:img.shape[0], 0:img.shape[1]] = img
cv2.imwrite(‘output.jpg’,dst)
plt.imshow(dst)
plt.show()

我们使用 matplotlib 绘制扭曲的图像,以便很好地可视化扭曲。

结果如下:

TensorFlow 1.3 中使用 Keras 的图像标记

原文:https://towardsdatascience.com/image-tagging-with-keras-in-tensorflow-1-2-bc43c1058019?source=collection_archive---------5-----------------------

我们已经了解了如何通过 TensorFlow 使用 Scikit-learn,并大致讨论了 TensorFlow 的高级 API。TensorFlow 直接支持的另一个流行的高级 API 是 Keras。

TensorFlow 1.3 的发布让美国用户可以直接在 TensorFlow 中使用 Keras。 Keras 是一个高级 API 规范,由Fran ois Chollet积极构建,主要是为了降低开发机器学习模型的门槛,并提供一个单一的 API 来访问许多底层的机器学习工具包。Keras 的流行意味着许多模型的框架(代码+预处理)都是现成的,并且由社区很好地维护和改进。

Keras — supported ML toolkits [TensorFlow, Theano, MXNet and Cognitive Toolkit]

为什么对 TensorFlow 开发者很重要?

就提交、开发者和更新的数量而言,TensorFlow 是迄今为止开发最活跃的 ML 工具包。然而,随着的积极发展,API 也发生了变化。另一方面,Keras 为底层的 ML 工具包提供了更高层次的抽象。因此,原型快速 ML 框架的可行性是不可知的变化酝酿之下。

将 Keras 放在 TensorFlow 中还可以避免安装其他库。如果您以前使用过 Keras,在您的机器上安装 Keras 也意味着安装 Theano(直到最近才支持两个框架)。当只使用 TensorFlow 和 Keras 时,这是一个不必要的 Theano 安装,当您想要部署使用 Keras 开发的 ML 模型时,这也是一个需要关注的原因。

在过去的两篇博客中,我们一直在讨论如何从 Scikit-learn 迁移到 TensorFlow,以及如何将 TensorFlow 和 Scikit-learn 库结合起来开发我们的 ML 模型。将 Keras 集成到 TensorFlow 中带来了一个类似的特性,只是除了 TensorFlow 之外,不需要安装其他库。

为什么对 Keras 开发者很重要?

我们不得不承认,TensorFlow 正在成为集成新的 ML 函数和库的领导者。因此,在训练大型深度网络时,Keras 开发人员将极大地受益于 TensorFlow 的分布式训练。

Keras 开发者可以使用的另一个有趣的功能是 TensorFlow 的 TensorBoard 。TensorBoard 不仅提供了培训和评估的可视化,也是可视化嵌入的简洁实现。

Keras 开发人员还可以访问 TensorFlow ServingGoogle Cloud ML ,它们允许部署 ML 模型来对生产环境中的新数据进行推理。

用 5 行深 CNN 标记图像

深度卷积神经网络已经证明在图像分类方面优于人类。虽然训练这种深度模型所需的 GPU 和 CPU 资源是昂贵的,但推理在计算上并不昂贵。因此,我们看看如何利用不同的艺术级图像分类模型,在少于五行代码中对图像进行推理。

并且,为了使这样的推论成为可能,我们使用 Keras 来使这成为可能。以下几行显示了我们如何在 TensorFlow 1.2 中使用 Keras 实现这一点:

img = image.load_img('niagara.jpeg', target_size=(224, 224))
x = image.img_to_array(img)
x = np.expand_dims(x, axis=0)
x = preprocess_input(x)

preds = model.predict(x)

正如所承诺的,我们处理图像并在 5 行代码中推断其内容(忽略导入,咄!)。在上面的代码中我们还没有定义的一件事是模型。有两个非常好的深度 CNN 模型,其性能优于人类。我们对用于执行分类的残差网络Inception v3 CNN 模型特别感兴趣。这两个模型都是深度网络,需要数周时间在 ImageNet 数据上进行训练。然而,我们将简单地站在巨人的肩膀上,下载这些模型并对我们的图像进行推理。我们如下初始化剩余网络(50 层深的 CNN ):

model = ResNet50(weights='imagenet')

我们可以类似地使用一个 Inception v3 模型来为我们的预测加载权重。我们如下初始化 Inception v3 模型:

model = InceptionV3(weights='imagenet')

我们对之前加载的图像进行推断,以获得我们预测的类别和概率,如下所示:

preds = model.predict(x)

我们可以如下解码来自模型的图像预测:

print('Predicted:', decode_predictions(preds, top=5)[0])

从图像加载到执行预测的端到端框架的笔记本可以在我的 GitHub 存储库中找到。《盗梦空间》v3 T1 和《T2》残网 T3 笔记本上市了。在我的 GitHub 上的 Keras 资源库中有一些更有趣的脚本,供那些想使用 Keras 探索其他 TensorFlow 应用程序的人使用。

在 TensorFlow 最近的更新中,使用最先进的深度 CNN 标记图像变得非常容易。Keras 作为高级 API,肯定降低了进入 ML 的门槛。查看我的 Keras ,了解更多使用 Keras 和 TensorFlow 构建的应用程序。

让我知道你想要建造什么。请在下一篇博文中留下您希望我讨论的内容!干杯!

公共/私人区块链中的不变性—第 1 部分

原文:https://towardsdatascience.com/immutability-in-public-private-blockchains-part-1-7affda04dbfd?source=collection_archive---------8-----------------------

Photo by Donnie Rosie on Unsplash

不变性是区块链实现的核心价值。在公开和私下的区块链谈论这个问题的技术细节之前,退一步想想它意味着什么以及它为什么重要可能是有益的。

不变性是什么意思?

尽可能字面上的不变性是指某件事不能改变。好吧,这很简单,对吧?。有点…我们首先需要定义什么是真正的改变。

想象一下,现在你有一辆白色的汽车。现在你决定你想要一个红色的。你至少有两个选择:

  1. 把你现在的车涂成红色。
  2. 卖掉你现在的车,买一辆红色的。

前者,你可以说你的车变了,因为颜色是你车的一个属性。因为这个属性已经改变了,所以你可以放心地说你的车已经改变了。后者,你不能真的说你的车自从你买了另一辆车后就变了。

那么这有什么意义呢?。首先,在分析对象的可变性之前,我们必须弄清楚是什么定义了对象的身份。将这个想法发挥到极致,如果一个对象的身份被定义为它的所有属性,那么改变其中任何一个属性都意味着我们有了另一个对象,因此原始对象没有改变。

还有一个关于如何定义身份的哲学讨论。当然,这不是这篇文章的目的,但是如果你感兴趣的话,你可以看看太阳的船。

TL;DR:在考虑一个对象是否已经改变之前,我们应该首先对它的身份有一个清晰的定义。

为什么不变性很重要?

让我们考虑以下情况。你是一个房屋所有者,你居住的国家决定房屋所有权将由分类账中的记录来定义。

考虑以下索赔:

我是房子的主人,所以账本里有记录支持这个事实。

这种说法并不准确。以下说法是这个国家房屋所有权的正确表述:

账本上有记录,所以我是房主。

现在,这听起来很不一样。由于拥有自己的房子需要付出很多努力,你可能会开始考虑问以下问题:

  • 如果账本被销毁了呢?
  • 如果我房子的相关记录被删除了怎么办?
  • 如果不知何故记录被更改,另一个人拥有我的房子怎么办?
  • 账本查不到怎么办?

这些都是合理的问题,因为房子是非常高价值的资产。如果我们谈论的不是房子,而是糖果,你不介意在这些方面冒险。

前面的问题分析了分类账可能面临的不同风险,特别是,第二个问题听起来应该是不可改变的。第三个不是关于不变性,而是关于授权。

也许不可变这个词现在开始变得有意义了。但是,等等,房地产业务就是转让所有权,所以我们有突变。

现实在变,但历史不会变。

这才是重点。一个新的转让所有权的交易并不能改变一个事实,那就是在那之前的某个时候,我是那栋房子的主人。

如果我们使用分类账中的信息做出重要决策,我们希望这些信息是不可变的;我们需要建立因果关系,并保持它的永久性。更准确地说,把时间看作一个维度,考虑到时间是单行道,我们应该得出这样的结论:历史应该是不可改变的。

我们仍然没有讨论账本是否是数字的。它可以是基于纸张的分类账、关系数据库、区块链等;但是这是一个实现细节,无论如何都不会改变我们例子中不变性的重要性。不变性是一个设计决策。

在区块链的上下文中,不变性是什么意思?

作为复习,请记住以下几点:

  • 区块链是分布式总账。
  • 分布式部分指的是很多参与节点,特别是有一个账本的副本。
  • 区块链共识算法负责所有节点最终汇聚到同一个账本。
  • 区块链由有序的块组成,其中每个块包含前一个块的散列(这就是它被称为区块链的原因;块用散列来链接)。
  • 区块链是只附加的数据结构。

区块链 as 分类帐实施用于对事务处理历史进行建模。一个交易发生如果是历史的一部分。正如我们前面提到的,历史是不变的,因此区块链也应该是不变的。

上面列表的最后一点提到区块链是只附加的数据结构;这是必不可少的,因为每个生成的块不能被改变以保持不变性。

如果我们有相同的事务有序历史记录,但在块中分组不同(例如,我们使用两倍大小的块),会怎么样?我们可以问,对于同一段历史,我们是否有多个区块链。这是一个更微妙的讨论,因为我们有两个相同历史的表述。在比特币的情况下,当生成一个块时,生成交易矿工包含,其中包含奖励,如果相同的有序交易被不同地分组在块中,则历史会不同。

在区块链,打破不变性指的是说服大多数节点改变现有块的难度。如果这是可能的,我们将改变历史导致可能无法接受的后果。

在第 2 部分中,我将比较两种解决方案中这一设计目标的实现差异:

  • 使用工作证明(PoW)共识机制的公共区块链,例如比特币。
  • 一个私人的区块链,特别是 Hyperledger 面料。

我认为两者之间的对比非常有趣,因为链接块的核心思想在不变性中有非常不同的重要性。

人工智能和机器学习对交易和投资的影响

原文:https://towardsdatascience.com/impact-of-artificial-intelligence-and-machine-learning-on-trading-and-investing-7175ef2ad64e?source=collection_archive---------2-----------------------

Source: Wikipedia

以下是我几个月前在欧洲做的一次演讲的节选,当时我是一名受邀演讲者,面对的是一群低调但高净值的投资者和交易者。主题被主办方确定为关于人工智能和机器学习对交易和投资的影响。以下节选分为四个部分,涵盖了原演示文稿的 50%左右。

1。人工智能和机器学习对交易的一般影响

人工智能(AI)允许用机器代替人类。在 20 世纪 80 年代,人工智能研究主要集中在专家系统和模糊逻辑上。随着计算能力变得越来越便宜,使用机器解决大规模优化问题在经济上变得可行。由于硬件和软件的进步,如今人工智能专注于使用神经网络和其他学习方法来识别和分析预测器,也称为特征或因素,这些预测器具有经济价值,可以与分类器一起使用,以开发有利可图的模型。人工智能的这种特殊应用通常被称为机器学习(ML)。

基于人工智能开发交易策略的方法在短期和长期投资中的应用越来越受欢迎,有一些对冲基金在这一领域非常活跃。然而,由于各种因素,这种新技术的广泛接受是缓慢的,最重要的是人工智能需要对新工具和人才的投资。大多数基金使用基本面分析,因为这是经理们在 MBA 课程中学到的东西。单纯依靠 AI 的对冲基金并不多。人工智能在零售层面的应用越来越多,但大多数交易者仍然使用二十世纪中期提出的方法,包括传统的技术分析,因为它们容易学习和应用。

请注意,人工智能和 ML 不仅用于开发交易策略,还用于其他领域,例如开发流动性搜索算法和向客户建议投资组合。因此,随着人工智能应用的普及,参与交易和投资决策的人数减少了,这显然会影响市场和价格行为。现在推测这种新技术对行业的整体影响还为时过早,但人工智能的广泛使用可能会导致更有效的市场,在更长的时间内波动性更低,随后由于制度变化而偶尔出现波动性峰值。这是可能的,因为人类对信息的主观评估的影响将被最小化,并且相关的噪声也将被最小化。但这还有待实践检验。

2。人工智能和机器学习对阿尔法一代的影响

在这些采用人工智能技术的初始阶段,对于那些了解它并知道如何管理其风险的人来说,将会有机会。基于人工智能的交易策略的一个问题是,它们可能产生比随机模型更差的模型。我将试着解释我的意思:传统的技术分析是一种无利可图的交易方法,因为基于图表模式和指标的策略在任何交易成本之前从零均值分布中获得回报。有些交易者总是出现在分布的右尾,这给人一种错误的印象,认为这些方法有经济价值。我的研究表明,特别是在期货和外汇市场,无论使用哪种方法都很难实现长期盈利,因为这些市场旨在让做市商受益。然而,在较短的时间内,由于运气好,一些交易者可以在杠杆市场上获得高额利润。然后,这些交易者把他们的成功归因于他们的策略和技巧,而不是运气。

对于 AI 和 ML,还有额外的影响,如偏差-方差权衡。数据挖掘偏差可能导致策略过度适应过去的数据,但对新数据立即失效,或者策略过于简单,没有捕捉到数据中具有经济价值的重要信号。这种权衡的结果是比随机策略更差的策略,甚至在交易成本增加之前,这些交易者的回报分布也是负的。在后量化宽松时代,这为大型基金和投资者带来了获利机会。然而,随着比随机更差的人工智能交易者被从市场上清除,只有那些拥有稳健模型的交易者留下来,利润之战将变得激烈。现在猜测人工智能交易员或大型投资者是否会赢得这场战斗还为时过早。

我还想提一下这方面一个常见的误解:有些人认为值在使用的 ML 算法中。这不是真的。真正的价值在于所使用的预测因素,也称为特征或因素。最大似然算法无法在没有金子的地方找到金子。一个问题是,大多数 ML 专业人员使用相同的预测器,并试图以迭代的方式开发模型,这将产生最佳结果。这一过程受到数据挖掘偏见的困扰,并最终失败。简而言之,数据挖掘偏差是由对许多模型多次使用数据的危险做法造成的,直到结果在训练和测试样本中可以接受。我在这一领域的研究表明,如果一个简单的分类器,如二元逻辑回归,不能令人满意地与一组给定的预测因子一起工作,那么它很可能没有经济价值。因此,成功取决于所谓的功能工程,这既是一门科学,也是一门艺术,需要知识、经验和想象力来提出具有经济价值的功能,只有一小部分专业人士可以做到这一点。

3。人工智能和机器学习对技术分析的影响

我们必须区分传统技术分析和定量技术分析,因为所有依赖于价格和交易量序列分析的方法都属于这一范畴。传统的技术分析,即图表模式、一些简单的指标、某些价格行为理论等。,一开始就没有效果。除了一些范围和深度有限的不完整的努力,吹捧这些方法的出版物从未提出他们的长期统计预期,而只是承诺如果使用这种或那种规则,将有利润潜力。由于市场的利润和亏损遵循某种统计分布,总有人把他们的运气归功于这些方法。与此同时,整个行业围绕这些方法发展起来,因为这些方法简单易学。不幸的是,许多人认为他们可以通过更好地使用其他人都知道的方法来获利,结果是大量财富从这些天真的交易员转移到做市商和其他消息灵通的专业人士手中。

在 20 世纪 90 年代早期,一些市场专业人士意识到大量的散户在用这些幼稚的方法交易。一些人开发了算法和人工智能专家系统,以提前识别地层,然后根据它们进行交易,这导致了散户交易者(也称为弱手)无法应对的过程波动。从更根本的角度来说,传统技术分析的失败可以归因于从 20 世纪 90 年代开始的市场中高序列相关性的消失。基本上是高度的序列相关性提供了这些方法有效的错误印象。如今,除了少数例外,市场正在回归均值,没有给简单的技术分析方法留下空间。然而,一些定量的技术分析方法往往效果很好,如均值回复和统计套利模型,包括使用具有经济价值的特征的 ML 算法。

请注意,这种类型的套利不太可能在人工智能和 ML 的案例中重复,因为模型的种类繁多,而且大多数模型都是专有的,但这种新技术的主要问题不是确认偏差,就像传统技术分析的情况一样,而是数据挖掘偏差。

在我看来,观察市场,看图表,正在成为一个过时的过程。交易的未来是关于实时处理信息、开发和验证模型。未来的对冲基金将不再依赖图表分析。有些人仍然这样做,因为他们正处于新旧时代的交接点。许多不熟悉人工智能的交易者将发现未来很难竞争,并将退出。

4。新交易技术的赢家和输家

人工智能的应用将在许多方面改变交易,这已经在发生。投资者可能很快就会发现,在 QE 引发的当前趋势结束后,中期回报将远低于预期。如果这种情况成为现实,那么投资者将不得不回到老路上,寻找一位优秀的财务顾问,他可以建议投资组合,并挑选会升值的证券。在某些情况下,顾问将是一个人工智能程序,这个过程将在线执行。

交易者需要熟悉这项新技术。大多数交易者仍在旧方法中挣扎,只是希望“买入下跌”会奏效,并为未来几年提供利润。

其中一个问题是在过去的八年里,中央银行在金融市场的直接支持下培育的道德风险。许多交易员和投资者现在认为,熊市是不可能的,因为央行将把他们的损失重新分配给其他所有人,尽管他们可以保留自己的利润。因此,大多数市场参与者对下一次重大的市场机制变化毫无准备,可能会面临毁灭性的损失。

网上有关于 ML、AI 和交易的优秀资源。最好的学习方法是试图解决一些实际问题。但我认为,对大多数交易者来说,这种转变是不可能的。理解和应用人工智能所需的技能组合排除了 95%习惯于在图表上画线和观察均线的交易者。

投资者应该自己做研究,并咨询熟悉这些新发展的有能力的财务顾问。每个投资者都有不同的风险规避特征,很难提供通用的指导方针。机器人顾问很快就会激增,选择一个适合特定需求和目标的机器人顾问可能会成为一项具有挑战性的任务。

任何不熟悉 ML 和 AI 以及它们与交易和投资的关系的人可能会发现,向熟悉这一领域的专业人士咨询比开始阅读书籍和文章更有利可图,阅读书籍和文章可以在理解基础知识后进行。我希望我已经在这次演讲中提供了一个大概的想法,可以作为这个有趣且可能有回报的努力的起点。

注来自《走向数据科学》的编辑: 虽然我们允许独立作者根据我们的 规则和指导方针 发表文章,但我们不认可每个作者的贡献。你不应该在没有寻求专业建议的情况下依赖一个作者的作品。详见我们的 读者术语

如有任何问题或意见,欢迎在推特上联系: @mikeharrisNY

关于作者:迈克尔·哈里斯是一名交易者和畅销书作家。他也是 17 年前第一个识别价格行为无参数模式的商业软件的开发者。在过去的七年里,他一直致力于开发 DLPAL,这是一个软件程序,可以用来识别市场数据中的短期异常,与固定模型和机器学习模型一起使用。点击此处了解更多信息。

社交媒体对票房的影响:最佳影片提名的 twitter 活动分析| 2018 年奥斯卡与 Python

原文:https://towardsdatascience.com/impact-of-social-media-on-box-office-analysis-of-twitter-activities-on-best-picture-nominees-7961c5c8ba40?source=collection_archive---------12-----------------------

photo credit: 889noticias.mx

你认为观众在 twitter 等社交媒体渠道上的帖子和评论能左右公众舆论,增加或减少电影的票房吗?

这是我们要做的,为我们的问题找到可能的答案:我们将收集关于 2018 年奥斯卡最佳影片提名的推文;我们在每部电影上映前 4 周开始收集推文,在电影结束后 1 周停止收集。 接下来我们分析推特活动(主角演员推特账号、推文数量、推文情绪、电影评分和评论)并探索推特活动和票房销售之间可能的关系。

从技术角度来看,我们将使用数据科学和数据可视化技术和工具来解决这个问题。我们广泛使用 python 来实现这个项目。为了收集推文,我们有两个选择:1-使用 twitter API(像 tweepy )。2-使用 web 抓取技术来手动解析推文。在这种情况下,我决定使用网络抓取来收集推文,因为 tweepy API 非常慢,而且有一些限制。对于抓取任务,我决定使用 python 中的 beautiful Soup 编写一个 web scraper,但随后我做了一个随机搜索,以检查是否有人已经这样做了。我发现了 Twitter 搜索的一个很好的 python 实现,它让我的生活变得更加轻松。然后我修改了它的代码,这样推文就可以保存到 sql 数据库中。

下一步是评估推文的情绪。简单解释一下,谷歌对情感分析的定义是:“通过计算识别和分类一段文本中表达的观点的过程,特别是为了确定作者对特定主题、产品等的态度。,是积极的,消极的,还是中性的。”对于这个任务,我们将使用 python 中的Vader perspection包。Vader perspective 是一个专门针对社交媒体上表达的情绪的工具。对于每条推文,该工具将给出一个介于[-1,+1]之间的数值分数。完全负面情绪为-1,完全正面情绪为+1,0 代表中性情绪。

在收集推文并计算情绪后,我们使用 python 中的 pandas 和 matplotlib 来可视化每周情绪变化和推文数量与票房之间的关系。以下是工作流程的整体架构:

Overall Workflow

值得一提的是,门票销售数据是从 boxofficemojo 收集的。评分是从 metacritic.com 的挑选出来的。现在我们来看看每部电影的总销量和推文总数:

%matplotlib inline
import pandas as pd
import matplotlib.pyplot as plt# this csv contains the records for total sales and total tweets
total_sales = pd.read_csv('totally.csv')fig, ax1 = plt.subplots()#plotting the bar plot to show the distribution of sales
ax1.bar(total_sales.index, total_sales['total_sales'], width = 0.6)
ax1.set_title('Total Sales', fontsize = 14)
ax1.tick_params('y', colors='b')
ax1.set_xticks(ticks=total_sales.index-0.8)
ax1.set_xticklabels((total_sales['movie']), rotation = 45)
plt.show()

total sales

total number of tweets for each movie

我们可以立即看到两部电影在总销售图中脱颖而出(《敦刻尔克》和《滚出去》)。这是该类别中唯一票房超过 1 亿美元的电影。我让你们评论一下为什么这两部电影有更高的票房,稍后,我们会看到这两部电影的周销售图也不同于这一类别的其他电影。

谈到推文的总数,我们可以看到几乎所有人在大约 5 个月的时间里平均有 3000 到 4000 条推文。

分析(为本文开头的问题找到可能的答案)

  • 让我们从这个问题开始分析:twitter 上主要角色演员的追随者和门票销售之间的关系是什么?

嗯,我觉得答案是没有很强的关系。这些票房巨大的电影中的一些主要角色演员甚至没有 twitter 账户,或者即使他们有,也没有那么多粉丝。

  • 接下来,每周的推文数量与门票销售相比如何?

我们首先从 sqlite 数据库中读取数据,其中包含推文的日期、推文本身和情感评分,并将其保存到熊猫数据帧中。然后,我们将数据重新采样到每周粒度。接下来,我们使用 matplotlib 展示推文数量相对于销售额的变化。

import pandas as pd
import sqlite3
import matplotlib.pyplot as pltconn3 = sqlite3.connect('twitterDunkirk.db')
c3 = conn.cursor()
dunkirk = pd.read_sql('select * from sentiment', conn3)dunkirk.tail()

# this file contains all the weekly sales info
weekly_track = pd.read_csv('weeklysales.csv')# we convert the date from string to date format
dunkirk['date'] = pd.to_datetime(dunkirk['date'])
dunkirk.sort_values('date', inplace = True)
dunkirk.set_index('date', inplace=True)# resample the data to weekly granularity
weekly_tweets = dunkirk.resample('w').size()
weekly_sentiment = dunkirk.sentiment.resample('w').mean()# print(weekly_sentiment)
weekly_sales = weekly_track['dunkirk']adjusted = []
for item in weekly_sales:
    adjusted.append(int(item))
    if len(adjusted) == len(weekly_tweets):
        break# print(len(weekly_sales), len(weekly_sentiment), len(weekly_tweets))# this is the new weekly dataframe
weekly = pd.DataFrame({'dates': weekly_tweets.index,'tweet_count': weekly_tweets.values,
                      'sentiment': weekly_sentiment.values, 'sales': adjusted})# print(weekly.head())
fig, ax1 = plt.subplots()
ax1.bar(weekly.index, weekly['sales'])
ax1.set_title("Dunkirk (Release Date: July 21, 2017)", fontsize = 16)
ax1.set_xlabel('Weeks')
ax1.set_ylabel('Weekly Sales', color='b')
ax1.tick_params('y', colors='b')
ax1.set_xticks(ticks=weekly.index-0.6)
ax1.set_xticklabels(labels=( "4 Weeks Out", "3 Weeks Out", "2 Weeks Out", "1 Week Out", " Release Week",
              "1 Week After", "2 Weeks After","3 Weeks After","4 Weeks After","5 Weeks After","6 Weeks After","7 Weeks After",
              "8 Weeks After","9 Weeks After","10 Weeks After","11 Weeks After","12 Weeks After","13 Weeks After","14 Weeks After",
               "15 Weeks After","16 Weeks After","17 Weeks After","18 Weeks After","19 Weeks After","20 Weeks After","21 Weeks After",
                "22 Weeks After","23 Weeks After","24 Weeks After","25 Weeks After","26 Weeks After","27 Weeks After",
                "28 Weeks After", "29 Weeks After"), rotation=45, size="medium" )
ax2 = ax1.twinx()
ax2.plot(weekly.index, weekly['tweet_count'],'k-')
ax2.set_ylabel('Weekly Tweets', color='k')
plt.show()

我们可以看到,门票销售不受推文数量的影响。然而,我们可以在图表中看到一些模式。我把这个留给读者进一步讨论。

  • 接下来,我们来评估推文的情绪之间的关系,看看它对门票销售是否有影响。我们遵循与之前相同的过程,只是在绘制图表时将“tweet_count”更改为“perspective”。

同样,我们可以看到门票销售总体上不受推文情绪的影响。然而,我们可以在所有的图中看到一些模式,除了一个。我把这个留给读者去发现哪个情绪图是不同的,为什么?

  • 现在我们来看看回归图,它显示了每部电影的总体平均情绪与 metacritic.com 提供的评级之间的相关性。等级从 0 到 10。
# in this section, we try to find any possibel correlation between the sentiment and rating scoresimport numpy as npweekly_data = pd.read_csv('weeklt_data.csv')
ratings = pd.read_csv('ratings.csv')m_names = ["ladyb", "thepost", "threebill", "shapeofwater", "phantom", "getout", "dunkirk", "darkest", "callme"]threebill = weekly_data[weekly_data['movie']== 'threebill']
ladyb = weekly_data[weekly_data['movie']== 'ladyb']
thepost = weekly_data[weekly_data['movie']== 'thepost']
shapeofwater = weekly_data[weekly_data['movie']== 'shapeofwater']
phantom = weekly_data[weekly_data['movie']== 'phantom']
getout = weekly_data[weekly_data['movie']== 'getout']
dunkirk = weekly_data[weekly_data['movie']== 'dunkirk']
darkest = weekly_data[weekly_data['movie']== 'darkest']
callme = weekly_data[weekly_data['movie']== 'callme']list_x = [callme['sentiment'].mean(), darkest['sentiment'].mean(), dunkirk['sentiment'].mean(), thepost['sentiment'].mean()
        , getout['sentiment'].mean(), threebill['sentiment'].mean(), shapeofwater['sentiment'].mean(), 
         ladyb['sentiment'].mean(), phantom['sentiment'].mean()]
list_y = ratings['rating']fit = np.polyfit(list_x,list_y,1)
fit_fn = np.poly1d(fit)
# fit_fn is now a function which takes in x and returns an estimate for yplt.plot(list_x,list_y, 'yo', list_x, fit_fn(list_x), '--k')plt.show()

我想我只能说,根据我对上图的解释,大多数情感得分分布在 0.05 和 0.2 之间,它们与回归线不太一致。这里的离群值是最黑暗的时刻;它有负面情绪,原因是这部电影的大多数推文中有“最黑暗”这个词,这使得情绪倾向于负面。

  • 最后,让我们看看所有电影的推文、情感和销售的累积图,以便更好地理解每个类别中的可能模式。

我不打算在这里添加更多的解释,希望这篇文章的读者能提出问题和评论。

非常感谢您的反馈。

我的 github 页面 上有这个项目的源代码、python 笔记本和数据集。

利用 AWS SageMaker 实现清晰的数据科学

原文:https://towardsdatascience.com/implement-crisp-data-science-with-aws-sagemaker-59163a63b0ad?source=collection_archive---------6-----------------------

本文旨在展示 AWS 开发和托管行业标准机器学习产品和研究级算法的能力和敏捷性。

该概念通过使用“对象检测算法”示例(https://github.com/wutianchen/object-detection-algo)在 AWS 云上实施 CRISP 数据科学工作流得到验证。

数据科学中关注点的分离

CRISP(数据挖掘的跨行业标准流程)是一个敏捷的工作流或框架,它很好地捕捉了数据科学中关注点的分离。

CRISP Workflow

标准 CRISP 包括上述 7 个组件和 4 个阶段。

  1. 形成业务问题并收集数据
  2. 处理数据并基于数据建立模型
  3. 将模型打包到数据产品中并部署
  4. 监控模型并收集信息

过程中来来回回并不少见。例如,我们可能被迫收集某些数据来回答一个业务问题,或者尝试各种统计模型来提高模型的准确性。

SageMaker—CRISP 的 AWS 实现

SageMaker 涵盖了从“数据理解”到“监控”的脆。前 SageMaker 时代的另一个类似工具是

SageMaker and CRISP

SageMaker 笔记本: (Jupyter 笔记本)启用从数据处理到统计建模,从分布式模型训练到评估的所有数据科学工作。

SageMaker 既允许定制算法,也允许内置算法

SageMaker 端点:利用微服务容器架构部署数据科学的成果。也允许在单个端点后部署集合模型(加权模型集合)。

sage maker 和 Cloudtrail 的集成:自动记录结果。监控对于数据科学非常重要,因为它可以检测模型在现实世界中的“真实”准确性和数据分布漂移,以支持下一次清晰迭代中的决策。

一个例子——检测图像中的对象

  • 我们来形成一个问题:

用概率检测图像中预定义对象列表的位置和标签。

  • 问题需要算法:

为了解决这个问题,我们借用 Keras RetinaNet 对象检测算法(后端 tensorflow)的实现,在论文密集对象检测的焦损失中有详细描述。

使用快速 R-CNN 实现的以前版本的解决方案可以在这里找到(博客:用更快的 R-CNN 计算对象)

可以在 Pascal VOC 数据集以及 MS COCO 数据集等上轻松训练模型。使用存储库中提供的脚本。然后在特定领域数据集上应用迁移学习来提高其回答特定问题的性能。

由于关注点的分离,模型可以在不涉及项目其他部分的情况下被改变和部署。

把算法的东西还给算法,把基础设施的东西还给基础设施。

  • 算法需要一个 web 服务器:

为了在 AWS 上部署该算法,必须实现两个接口。

  1. web 服务器路由接口
  2. 预测功能界面

(由于 AWS Lambda 的上传限制,以无服务器方式在 AWS 上部署机器学习算法仍然很困难。)

实现 web 服务器路由接口(/ping 和/invocations)

实现预测接口(get_model 和 predict 函数)

带有轻量级 python web 服务器 flask 和 docker 脚本的通用模板可以在这里找到。

  • 服务器需要端点:

使用 Sagemaker,有两种面向客户端的端点可能性

Build Endpoint for ML Model

  1. HTTP 端点(https://AWS . Amazon . com/blogs/machine-learning/call-an-Amazon-sage maker-model-Endpoint-using-Amazon-API-gateway-and-AWS-lambda/)
  2. SageMaker API 端点(https://docs . AWS . Amazon . com/SageMaker/latest/DG/API _ runtime _ invokeendpoint . html

模型被打包到 docker 容器中,并自动部署到 AWS ECR 上。然后可以通过端点调用 predict()方法来提供推断。

  • 测试终点:

我们可以用 Sagemaker Notebook 调用和测试已部署的 ML 端点,并可视化结果。

Invoke the Endpoint

在原始图像上绘制结果:

总结和下一次迭代

总之,AWS SageMaker 是目前市场上在敏捷框架下实现数据科学概念的最佳工具。它还集成了其他 AWS 本地服务,如 S3,红移,AWS Lambda,AWS IoT 等。很好。例如,结合 Kinesis KVS,我们可以将图像对象检测扩展到视频流中的对象检测。

因为这是敏捷的…所以我们从简单开始,经过多次迭代来添加特性。

在 Python 中实现梯度下降

原文:https://towardsdatascience.com/implement-gradient-descent-in-python-9b93ed7108d1?source=collection_archive---------0-----------------------

什么是梯度下降?

这是一种寻找函数最小值的优化算法。我们从函数上的一个随机点开始,沿着函数的梯度的负方向移动,到达局部/全局最小值

Homer descending !

手动示例:

问题:求从点 x=3 开始的函数 y=(x+5)的局部极小值

解法:我们只要看图就知道答案了。当 x = -5 时,y = (x+5)达到最小值(即当 x=-5,y=0 时)。因此 x=-5 是函数的局部和全局最小值。

现在,让我们看看如何使用梯度下降获得相同的数值。

第一步:初始化 x =3。然后,求函数的梯度,dy/dx = 2*(x+5)。

第二步:向渐变的负方向移动(为什么?)。但是等等,要移动多少?为此,我们需要一个学习率。让我们假设学习率→ 0.01

步骤 3 :让我们执行 2 次梯度下降迭代

第四步:我们可以观察到 X 值在慢慢减小,应该收敛到-5(局部最小值)。然而,我们应该执行多少次迭代呢?

让我们在算法中设置一个精度变量,用于计算两个连续“x”值之间的差值。如果连续两次迭代的 x 值之差小于我们设置的精度,停止算法!

Python 中的渐变下降:

第一步:初始化参数

cur_x = 3 # The algorithm starts at x=3
rate = 0.01 # Learning rate
precision = 0.000001 #This tells us when to stop the algorithm
previous_step_size = 1 #
max_iters = 10000 # maximum number of iterations
iters = 0 #iteration counter
df = lambda x: 2*(x+5) #Gradient of our function 

步骤 2 :运行一个循环执行梯度下降:

I .当两次连续迭代的 x 值之差小于 0.000001 或迭代次数超过 10,000 时,停止循环

while previous_step_size > precision and iters < max_iters:
    prev_x = cur_x #Store current x value in prev_x
    cur_x = cur_x - rate * df(prev_x) #Grad descent
    previous_step_size = abs(cur_x - prev_x) #Change in x
    iters = iters+1 #iteration count
    print("Iteration",iters,"\nX value is",cur_x) #Print iterations

print("The local minimum occurs at", cur_x)

输出:从下面的输出中,我们可以观察到前 10 次迭代的 x 值——这可以与我们上面的计算进行交叉检查。该算法在终止之前运行 595 次迭代。下面嵌入了代码和解决方案以供参考。

LinkedIn 上连接。

线性回归(第 2 部分):用 python 实现,从头开始的例子。

原文:https://towardsdatascience.com/implementation-linear-regression-in-python-in-5-minutes-from-scratch-f111c8cc5c99?source=collection_archive---------5-----------------------

5 分钟机器学习实现示例。用 python 实现多元线性回归模型(第 3 部分)。

Linear Regression

先决条件: 【线性回归(第一部分)

既然理论已经讨论过了,现在让我们从实际的实现开始。有不同的数据集可用,但让我们用自己的数据集来实现它。简单的线性回归有因变量(Y)和自变量(X)。

步骤 1:准备数据集

dataset to be used

  • X —房子大小从 1K 平方英尺到 10K 平方英尺。
  • Y —从 30 万到 120 万的房价。

所以我们的数据集已经准备好了,因为它是一个简单的线性回归,所以我们只有一个因素:房子的大小影响房子的价格。在多元线性回归的情况下,我们会有更多的因素影响房价,如位置、房间数量等。(这将在线性回归 ie 的下一部分中实现。第三部分)。

Plotted data on a graph

现在我们需要找到回归线(在上面的散点图中最符合的一条线,这样我们就可以预测响应 y (即。房子的成本)为任何新的价值 x (即。房子的大小)。

第二步:让我们开始编码吧!!!

导入所需库

  1. Numpy 是 Python 编程语言的一个库。我们在机器学习中使用它,因为我们必须在机器学习中处理大量数据,这比普通数组更快。(习惯了 numpy 数组,我们在哪里都会用到)。有关安装说明,请点击此处
  2. Matplotlib : Matplotlib 是 Python 编程语言及其数字数学扩展 NumPy 的绘图库。基本上,这有助于绘制图表。

这里我们使用了“numpy as np”和“matplotlib.pyplot as plt ”,这样做是为了将庞大的名称重命名为较小的名称(便于使用)。而不是写 1numpy . array()简称为 np.array()
2。 matplotlib.pyplot.plot(x,y)
简称为 plt.plot(x,y)这些都是为了便于编码。

如何知道自己是否安装正确??运行上面两行的文件,如果没有发现错误,就可以运行了。

定义所需功能

Function1: 这是一个确定或估计系数的函数,其中 x 和 y 值被传递到该函数中。

步骤包括:

  1. 计算 n
  2. 计算 x 和 y 数组的平均值。
  3. 计算交叉偏差和偏差:记住这里我们计算的是 SS_xy 和 SS_xx,它们是误差平方和。如前文所述 【线性回归(第一部分)
  4. 计算回归系数:回归线需要移动的量或值。

功能 2 :根据计算值绘制图形的功能。

步骤包括:

  1. 绘制点:" plt.scatter "在图上绘制点,其中
  • x 和 y 是图上点的位置
  • 颜色是标绘点的颜色,将其更改为红色或绿色或橙色,并尝试更多可能的颜色 点击此处
  • 【马克笔】是点的形状像一个圆或者其他什么符号代表不同类型的马克笔 在这里找到

2.预测回归线值:取可能的最小误差,回归线在此决定。

3.绘制回归线

4.标签放在这里,而不仅仅是 x 和 y,即 x 和 y 的名称放在这里的图表上。

5.显示绘制的图形

功能 3 :主功能

步骤包括:

  1. 收集 ie 所需的数据集。x 和 y。
  2. 计算所需的系数。回归线在 x 和 y 方向上的移动值。
  3. 绘制图表

最后,编写 main 并调用 main 函数:

所以最终结果,

因此,如果在这里询问 7Ksq 英尺大小的房子的价格,答案将是 92 万左右,而实际价值将是 90 万左右,因此误差为 2 万。

GitHub 上找到代码,链接如下:
https://github.com/chethangn/SimpleLinearRegression

更多参考资料:

  1. 人工智能是真实存在的还是只是这十年的炒作??
  2. 人工智能:定义、类型、实例、技术
  3. 人工智能 vs 机器学习
  4. 机器学习为什么要实现人工智能?
  5. 机器学习类型和算法
  6. 【线性回归部分-1】

接下来是 线性回归(第 3 部分),我们将实现多元线性回归。

请务必关注我的***,LinkedInTwitterinsta gram获取更多更新。如果你喜欢这篇文章,请鼓掌并分享它。*****

在这里加入我们的 WhatsApp 社区。

基于聚类质心的多数欠采样技术在 Python 中的实现

原文:https://towardsdatascience.com/implementation-of-cluster-centroid-based-majority-under-sampling-technique-ccmut-in-python-f006a96ed41c?source=collection_archive---------7-----------------------

在机器学习和深度学习中,数据不平衡分别是许多分类算法和深度神经网络性能下降的主要原因。不平衡数据是指属于不同类或类别的实例或样本数量不相等,差异显著。二进制不平衡数据的一个这样的例子是 19668 个,其中有 2 个类,但包含不相等数量的实例,76,090 个实例带有标签“0 ”,而 76,090 个实例带有标签“1 ”:

Binary Imbalanced Data

为了最小化不平衡的程度,必须将数据挖掘特征空间几何整合到解决机器学习分类问题的经典方法中。有许多用于数据平衡的数据挖掘方法。一种重要的方法是基于聚类质心的多数欠采样技术 ( CCMUT )。

在多数欠采样中,不重要(或不那么重要)的实例在多数样本中被移除。在 CCMUT 中,重要和不重要实例的划分是通过使用特征空间几何上的聚类概念来完成的。

聚类是一种无监督的学习方法。但是 CCMUT 仅使用寻找聚类质心的概念(聚类是围绕属于多数类的数据点创建的),因为实例已经被标记。通过在属于特征空间中多数类的数据点上获得所有特征的平均特征向量来找到聚类质心。

在找到多数类的聚类质心之后,在特征空间中距离聚类质心最远的属于该聚类(多数类)的实例被认为是最不重要的实例。相反,属于多数类的实例,即在特征空间中最接近聚类质心的实例被认为是最重要的实例。

因此,在 CCMUT 中,属于多数类的实例根据其重要性被删除,欠采样的样本数取决于欠采样或 CCMUT 的 %。

CCMUT 的 Python 实现:

从实现角度来看,特征空间几何中的所有距离都被认为是欧几里德距离

下面以函数 CCMUT()的形式给出了 CCMUT 的 Python 实现,它采用:

  1. 多数样本矩阵= X
  2. CCMUT 或欠采样的百分比= f

作为自变量,并返回欠采样后的多数样本矩阵= X_f。

import numpy as np
from math import sqrtdef **CCMUT**(X,f):
    # 1\. finding cluster centroid....
    cluster_centroid = np.sum(X,axis=0)/X.shape[0]
    # 2\. finding **Euclidean Distance** from cluster centroid to samples
    euclidean = [None]*X.shape[0]
    for i in range(0,X.shape[0]):
        euclidean[i] = sqrt(sum((cluster_centroid-X[i])**2))
    # 3\. tracking indices of samples in descending order of distance
    indices = list(reversed(sorted(range(len(euclidean)), 
    key = lambda j: euclidean[j])))
    # 4\. removing the instances or under-sampling order-wise....
    X_f = np.delete(X, indices[:int(f/100*X.shape[0])], axis=0)
    # 5\. returning the under-sampled Majority Sample Matrix
    return X_f

因此,使用多数样本矩阵和%欠采样调用 CCMUT(),将获得欠采样多数样本矩阵。显然,在欠采样之后,它不会以大幅度或差异被称为多数。

此后,欠采样的多数样本矩阵可以与少数样本矩阵连接(在 CCMUT 之前被分离),并被混洗以用于使用机器学习的预测分析或预测分类模型开发。

也有许多可用的研究,其中 CCMUT 已被直接应用或经过某些修正。

  1. 使用 AdaBoost 改进说话人确认决策的基于聚类的欠采样技术IAPR 模式识别统计技术国际联合研讨会(SSPR) 。施普林格,柏林,海德堡,2004。
  2. 甄子丹、秀珍和李月诗。"不平衡数据分布的基于聚类的欠采样方法."专家系统与应用36.3(2009):5718–5727。
  3. 拉赫曼、莫斯塔菲祖尔和戴维斯。“不平衡心血管数据的基于聚类的欠采样。”世界工程大会会议录。第三卷。2013.
  4. Sobhani,Parinaz,Herna Viktor 和 Stan Matwin。“使用集成方法和基于聚类的欠采样从不平衡数据中学习。”采矿复杂模式新前沿国际研讨会。施普林格,查姆,2014 年。
  5. Srividhya 和 R. Mallika。"基于欠采样的聚类同心圆处理不平衡数据."中东科学研究杂志24(2016):314–319。
  6. 阿奴拉达、那伽苏里和 g .帕萨萨拉迪瓦尔玛。"基于抽样技术聚类的非平衡数据分类方法."印度科技期刊 10.18 (2017)。
  7. 阿拉法特,医学博士亚希尔,萨贝拉霍克,和万德医学博士法里德。“基于聚类的欠采样随机森林多类不平衡分类。” 2017 第十一届软件、知识、信息管理与应用国际会议(SKIMA) 。IEEE,2017。

用 Keras 实现卷积神经网络

原文:https://towardsdatascience.com/implementation-of-convolutional-neural-network-using-keras-9ace67916c07?source=collection_archive---------13-----------------------

在本文中,我们将看到在 MNIST 数据集上使用 Keras 实现卷积神经网络(CNN ),然后将结果与常规神经网络进行比较。强烈建议在继续学习 CNN 实现之前,先阅读文章“卷积神经网络—简而言之”,以培养对 CNN 的直觉。

1-简介

MNIST 数据集最常用于影像分类研究。MNIST 数据库包含美国人口普查局雇员和美国高中生手写的数字图像,从 0 到 9。分为 6 万张训练图像和 1 万张测试图像。Tensorflow 和 Keras 都允许我们使用 API 直接下载 MNIST 数据集。

2-使用 API 下载数据集

我们将只使用两行代码来导入 TensorFlow 并在 Keras API 下下载 MNIST 数据集。我们将把数据分配到训练集和测试集中。x_train 和 x_test 部分包含灰度 RGB 代码(从 0 到 255 ),而 y_train 和 y_test 部分包含从 0 到 9 的标签。
我们将使用‘matplotlib’库可视化图像。

需要强调的是,MNIST 数据集中的每幅图像大小为 28 X 28 像素,这意味着 x_train 的形状为(60000,28,28 ),其中 60,000 是样本数。作为通过 Keras API 进行处理的要求,我们必须将 x_train 从 3 维重塑为 4 维。此外,我们必须标准化我们的数据,否则我们的计算成本将非常高。我们可以通过将 RGB 代码划分为 255 来实现,如下所示:

3-卷积神经网络结构

首先,我们将卷积神经网络架构定义如下:

1-第一个隐藏层是一个卷积层,称为卷积 2D。我们将使用 32 个尺寸为 5×5 的过滤器。

2-然后是池大小为 2×2 的最大池层。

3-具有 64 个滤波器的另一个卷积层,每个滤波器的大小为 5×5。

4-然后是池大小为 2×2 的最大池层。

5-然后下一步是扁平化层,在建立完全连接的层之前,将 2D 矩阵数据转换为 1D 矢量。

6-之后,我们将使用一个具有 1024 个神经元和 relu 激活功能的全连接层。

7-然后我们将使用一个正则化层称为辍学。它被配置为随机排除该层中 20%的神经元,以减少过度拟合。

8-最后,输出层,其具有用于 10 个类别的 10 个神经元和用于输出每个类别的概率状预测的 softmax 激活函数。

决定上述内容后,我们可以用如下几行代码建立一个神经网络模型:

注:

–注释带有' # '来解释命令。

–您可以下载 iPython 笔记本 并在您的 PC 上训练模型,或者只是复制并粘贴这些代码。py 文件。

步骤 1 —创建模型:

Keras 首先创建一个模型对象的新实例,然后一个接一个地向其添加层。它被称为顺序模型 API。我们可以通过调用 model.add 并传入我们想要添加的层的类型来向神经网络添加层。最后,我们将用两个重要信息编译模型,损失函数和成本优化算法。

一旦我们执行了上面的代码,Keras 将在幕后构建一个 TensorFlow 模型。

步骤 2 —训练模型:

我们可以通过调用 model.fit 并传入训练数据和预期输出来训练模型。Keras 将运行培训过程,并将进度打印到控制台。训练完成后,它将报告训练数据达到的最终准确度。

步骤 3 —测试模型:

我们可以通过调用 model.evaluate 并传入测试数据集和预期输出来测试模型。

步骤 4 —保存并加载模型:

一旦达到最佳结果,我们可以使用 model.save 保存模型,并传入文件名。这个文件将包含我们在另一个程序中使用我们的模型所需要的一切。

您的模型将以扩展名为. h5 的分层数据格式(HDF)保存。它包含科学数据的多维数组。

我们可以通过调用 load model 函数并传入一个文件名来加载之前训练好的模型。然后,我们调用 predict 函数并传入新数据进行预测。

总结

  • 我们学习了如何加载 MNIST 数据集并对其进行归一化。
  • 我们学习了使用 Keras 实现 CNN。
  • 我们看到了如何保存训练好的模型并在以后加载它进行预测。
  • 准确率超过 98%,这比我们用常规神经网络实现的准确率高得多。

从零开始使用梯度下降优化在 Python 中实现多变量线性回归

原文:https://towardsdatascience.com/implementation-of-multi-variate-linear-regression-in-python-using-gradient-descent-optimization-b02f386425b9?source=collection_archive---------5-----------------------

学习、实施和调整…

机器学习的大多数实际应用涉及目标结果所依赖的多个特征。类似地,在回归分析问题中,存在目标结果依赖于许多特征的情况。多元线性回归是解决这类问题的一种可能的方法。在本文中,我将讨论多变量(多特征)线性回归,它的 Python 实现,在一个实际问题上的应用和性能分析。

由于它是一种“线性”回归技术,在构建假设时,将只采用每个特征的线性项。设 x_1,x_2,… x_n 是目标结果所依赖的特征。然后,多元线性回归的假设:

where theta_0, theta_1, theta_2, theta_3,…., theta_n are the parameters

此外,上述假设也可以根据向量代数重新构建:

还有一个与依赖于参数θ_ 0,θ_ 1,θ_ 2,…,θ_ n 的假设相关的成本函数(或损失函数)

这里的成本函数与多项式回归的情况相同[1]。

因此,这些参数θ_ 0,θ_ 1,θ_ 2,…,θ_ n 必须采用这样的值,对于这些值,成本函数(或简单地成本)达到其可能的最小值。换句话说,必须找出成本函数的最小值。

在这种情况下,分批梯度下降可用作优化策略。

使用批量梯度下降实现多元线性回归:

实现是通过创建 3 个模块来完成的,每个模块用于在培训过程中执行不同的操作。

=> hypothesis():是计算并输出目标变量的假设值的函数,给定 theta (theta_0,theta_1,theta_2,theta_3,…,theta_n),矩阵中的特征,维数为[m X (n+1)]的 X 其中 m 是样本数,n 是特征数。假设()的实现如下所示:

def **hypothesis**(theta, X, n):
    h = np.ones((X.shape[0],1))
    theta = theta.reshape(1,n+1)
    for i in range(0,X.shape[0]):
        h[i] = float(np.matmul(theta, X[i]))
    h = h.reshape(X.shape[0])
    return h

=>BGD():它是执行批量梯度下降算法的函数,将当前的θ值(theta_0,theta_1,…,theta_n)、学习速率(alpha)、迭代次数(num_iters)、所有样本的假设值列表(h)、特征集(X)、目标变量集(y)和特征数(n)作为输入,并输出优化的 theta (theta_0,theta_1,theta_2,theta_3,…,theta_n)和包含所有迭代的成本函数值的成本历史或成本 BGD()的实现如下所示:

def **BGD**(theta, alpha, num_iters, h, X, y, n):
    cost = np.ones(num_iters)
    for i in range(0,num_iters):
        theta[0] = theta[0] - (alpha/X.shape[0]) * sum(h - y)
        for j in range(1,n+1):
            theta[j] = theta[j] - (alpha/X.shape[0]) * 
                                   sum((h-y) * X.transpose()[j])
        h = hypothesis(theta, X, n)
        cost[i] = (1/X.shape[0]) * 0.5 * sum(np.square(h - y))
    theta = theta.reshape(1,n+1)
    return theta, cost

=>linear_regression():它是主函数,以特征矩阵(X)、目标变量向量(y)、学习速率(alpha)和迭代次数(num_iters)作为输入,输出最终优化的 theta,即[ theta_0,theta_1,theta_2,theta_3,…]的值。成本函数在批量梯度下降后几乎达到最小值的θ_ n****和存储每次迭代的成本值的成本

def **linear_regression**(X, y, alpha, num_iters):
    n = X.shape[1]
    one_column = np.ones((X.shape[0],1))
    X = np.concatenate((one_column, X), axis = 1)
    # initializing the parameter vector...
    theta = np.zeros(n+1)
    # hypothesis calculation....
    h = hypothesis(theta, X, n)
    # returning the optimized parameters by Gradient Descent...
    theta, cost = BGD(theta,alpha,num_iters,h,X,y,n)
    return theta, cost

现在,让我们继续讨论多元线性回归在实际数据集上的应用。

让我们考虑俄勒冈州波特兰市的房价数据。它包含房子的大小(平方英尺)和卧室的数量作为特征,房子的价格作为目标变量。该数据集可从以下网址获得:

** [## navoneel 1092283/多元回归

通过在 GitHub 上创建帐户,为 navoneel 1092283/multivariate _ regression 开发做出贡献。

github.com](https://github.com/navoneel1092283/multivariate_regression.git)

问题陈述:给定房子的大小和卧室数量,分析预测房子可能的价格"

数据读入 Numpy 数组:

data = np.loadtxt('data2.txt', delimiter=',')
X_train = data[:,[0,1]] #feature set
y_train = data[:,2] #label set

特征标准化或特征缩放:

这包括缩放特征以实现快速高效的计算。

Standard Feature Scaling Strategy

其中 u 是平均值,sigma 是标准偏差:

特征缩放的实现:

mean = np.ones(X_train.shape[1])
std = np.ones(X_train.shape[1])for i in range(0, X_train.shape[1]):
    mean[i] = np.mean(X_train.transpose()[i])
    std[i] = np.std(X_train.transpose()[i])
    for j in range(0, X_train.shape[0]):
        X_train[j][i] = (X_train[j][i] - mean[i])/std[i]

这里,

  1. 特征“房子的大小(平方。英尺)或 F1: 2000.6808
  2. 特征“床位数”的平均值或 F2: 3.1702
  3. F1 的标准偏差:7.86202619e+02
  4. F2 的标准偏差:7.52842809e-01
# calling the principal function with **learning_rate = 0.0001** and 
# **num_iters = 300000**
theta, cost = linear_regression(X_train, y_train,
                                               0.0001, 300000)

theta after Multi-Variate Linear Regression

在分批梯度下降迭代过程中,成本得到了降低。成本的降低借助于曲线显示出来。

import matplotlib.pyplot as plt
cost = list(cost)
n_iterations = [x for x in range(1,300001)]
plt.plot(n_iterations, cost)
plt.xlabel('No. of iterations')
plt.ylabel('Cost')

Line Curve Representation of Cost Minimization using BGD in Multi-Variate Linear Regression

使用三维散点图并排显示特征和目标变量实际值和预测值:

= >实际目标变量可视化:

from matplotlib import pyplot
from mpl_toolkits.mplot3d import Axes3Dsequence_containing_x_vals = list(X_train.transpose()[0])
sequence_containing_y_vals = list(X_train.transpose()[1])
sequence_containing_z_vals = list(y_train)fig = pyplot.figure()
ax = Axes3D(fig)ax.scatter(sequence_containing_x_vals, sequence_containing_y_vals,
           sequence_containing_z_vals)
ax.set_xlabel('Living Room Area', fontsize=10)
ax.set_ylabel('Number of Bed Rooms', fontsize=10)
ax.set_zlabel('Actual Housing Price', fontsize=10)

= >预测目标变量可视化:

# Getting the predictions...
X_train = np.concatenate((np.ones((X_train.shape[0],1)), X_train)
                         ,axis = 1)
predictions = hypothesis(theta, X_train, X_train.shape[1] - 1)from matplotlib import pyplot
from mpl_toolkits.mplot3d import Axes3Dsequence_containing_x_vals = list(X_train.transpose()[1])
sequence_containing_y_vals = list(X_train.transpose()[2])
sequence_containing_z_vals = list(predictions)fig = pyplot.figure()
ax = Axes3D(fig)ax.scatter(sequence_containing_x_vals, sequence_containing_y_vals,
           sequence_containing_z_vals)
ax.set_xlabel('Living Room Area', fontsize=10)
ax.set_ylabel('Number of Bed Rooms', fontsize=10)
ax.set_zlabel('Housing Price Predictions', fontsize=10)

Actual Housing Price Vs Predicted Housing Price

性能分析:

  1. 平均绝对误差:51502.7803(美元)
  2. 均方差:4086560101.2158(美元平方)
  3. 均方根误差:63926.2082(美元)
  4. r 平方得分:0.7329

需要注意的一点是,平均绝对误差、均方误差和均方根误差不是无单位的。为了使它们无单位,在训练模型之前,可以用缩放特征的相同方式缩放目标标注。除此之外,还获得了 0.7329 的下降 R 平方分数。

这就是使用梯度下降法在 Python 中实现多元线性回归的全部内容。

参考文献

[1]https://towards data science . com/implementation-of-uni-variable-linear-regression-in-python-using-gradient-descent-optimization-from-3491 a13c a2 b 0**

2017 年深度学习优化实现亮点(feat。塞巴斯蒂安·鲁德)

原文:https://towardsdatascience.com/implementation-of-optimization-for-deep-learning-highlights-in-2017-feat-sebastian-ruder-616766fe37f0?source=collection_archive---------12-----------------------

GIF from this website

Sebastian Rude r 是自然语言处理专业的博士生,也是 T2 AYLIEN 的研究科学家。他有一个关于自然语言处理和机器学习的最有趣、信息量最大的博客。(我一直都在读,我强烈推荐任何人也去读!)

我在这篇文章中讲述了我从他的博客文章中了解到的所有优化算法。现在这篇文章是第二个版本,涵盖了更先进的优化技术。

网络架构/基准比较

Network Architecture of ELU Network, from this blog post

我最近报道了' 通过指数线性单元(ELUs)进行快速准确的深度网络学习'单击此处阅读博文,不幸的是,我们在那里实现的模型遭受了对训练图像的过度拟合。所以让我们来看看这些方法是如何提高模型的性能的。(换句话说,它能概括得多好)我之所以这么说,是因为所有这些方法都在解决概括的问题。

请注意,为了公平比较(我想知道这些方法如何改进网络),所以我没有添加任何额外的层,如批量标准化或任何数据预处理。此外,所有的网络都是使用 Adam Optimizer 的某种变体来训练的。

上图是同一个网络在使用 L2 正则化的自动微分(adam optimizer)进行训练时的表现。因此,总的来说,我们的目标是用新的优化方法在测试图像上达到 64%的准确率。

修正 Adam 中的权重衰减正则化

上述论文是塞巴斯蒂安在他的博客文章中使用的主要参考资料之一。所以我认为把它链接到这里也是一个好主意。

案例 1)解耦重量衰减/结果

左图 →常规 Adam 优化器
右图 →带解耦权重衰减的 Adam
红框 →添加权重衰减项

第一种方法非常简单,当更新新的权重时,我们将添加某种权重衰减项(小于 1 ),将其乘以权重以及学习速率。当用 python 实现时,它看起来像下面这样。

红线 →添加重量衰减调整线

我已经将重量衰减率设置为 0.512,并且在每 10、50、100 和 150 次迭代中,我将重量衰减值减半。

左图 →一段时间内的训练精度/成本
右图 →一段时间内的测试精度/成本

由于成本上升到 80 英镑,右边的图表是倾斜的,但是不要担心,我已经附上了下面的图像,以显示模型的最终准确性。

如上所述,使用这种方法,我们能够在测试图像上实现 56%的准确率。考虑到仅亚当和 L2 正则化就能达到 64%的准确率,这还不算太好。

案例 2)固定指数移动平均值/结果

红框 →新旧 v 值之间的最大值

上图显示了 Adam 的新更新规则(该算法的另一个名称是 AMSGrad)。另外,请注意,对于这条规则,我已经将 Beta 2 的值更改为 0.9,而不是使用默认值 0.999。(如下图所示)

最后,当在 Tensorflow 中实现时,它可能如下所示。

Followed Filip KRZN’s implementation

红框 →新旧 v 值之间的最大值

我个人最喜欢这种方法,因为它实现起来非常简单。但是我明白当比较张量时,减少和可能不是最好的方法,另一种方法可以是比较欧几里得范数。但是现在让我们看看这个方法是如何提高模型的性能的。

左图 →一段时间内的训练精度/成本
右图 →一段时间内的测试精度/成本

如上所述,这种方法并没有完全防止模型过度拟合,但是它确实比我们的基准测试获得了更好的性能。

在测试图像上有 66%的准确性,而在训练图像上有 99%的准确性,除了我们在反向传播中所做的改变之外,没有其他形式的正则化方法。

情况 3)调整学习率/结果

红框 →更改 Adam 的 Hyper 参数
蓝框 →模型参数的计算数量
紫框 →等式选择当前步骤的学习率

为此,我们将计算我们网络中的参数数量。如果有人想知道怎么做,请点击这个链接。下面是 VGG 16 计算参数值的一个简单例子。

Image from this [website](http://networks?, H. (2018). How to calculate the number of parameters of convolutional neural networks?. Stack Overflow. Retrieved 8 May 2018, from https://stackoverflow.com/questions/28232235/how-to-calculate-the-number-of-parameters-of-convolutional-neural-networks)

下面是一个为我们的网络计算参数的例子。

红框 →参数计算
蓝框 →网络架构参考

现在,既然我们已经准备好了参数的数量,让我们来看看计算学习率的等式。

通过简单的 tf.cond(),我们能够在 step_num^(-0.5 和 step_num*warmup_steps^(-1.5).之间选择最小值最后让我们看看结果。

左图 →一段时间内的训练精度/成本
右图 →一段时间内的测试精度/成本

如上所述,使用这种方法,模型甚至不能在训练图像上表现良好。我怀疑这种方法的学习率会更高。

请注意,我将步骤数解释为迭代(或当前迭代)数,如果这是错误的,请在下面评论。

对于训练图像和测试图像,该模型最终精度大约为 23%。

情况 4)带重启/结果的 Adam

上面是重启的随机梯度下降(SGD)方程。总之,对于每次迭代 Ti,学习率被重置。所以当我们绘制学习率随时间变化的曲线时,它看起来会像下面这样。

如上所述,学习率在迭代 1 时被设置为 1,再次设置为 300,700 等等。现在让我们来看看如何将这个方法应用到亚当身上。

红框 →如何将此方法应用于 Adam 优化器

如上所述,我们首先需要修复重量衰减,我们已经看到了这一点。(这是我们在案例 1 中使用的方法)。现在让我们看一下实现。

红框→Ti 和 Tcur 的可变占位符
蓝框 →学习率计算公式

实现重启的方法有很多种,但我选择最简单的方法 LOL。另外请注意,原始论文的作者建议将学习率的最大值设置为 1,我设置为 0.001。当我们绘制学习率如何随时间变化(200 次迭代)时,它看起来像下面这样。

重启迭代次数设置为 10、30、70 和 150。(当我们将第一次重启迭代设置为 10 时)。现在让我们来看看模型的性能。

左图 →一段时间内的训练精度/成本
右图 →一段时间内的测试精度/成本

嗯……毫无疑问,这个模型做得很糟糕。我实际上花了很多时间试图让这个模型工作,但是这个模型似乎总是只在迭代的开始学习一些东西,并且在训练期间的某个地方,它似乎过了头,停止了所有的学习过程。

由于我很想知道我做错了什么,如果你对这款车型有什么推荐,请在下面评论。

训练图像和测试图像的最终准确度都是 9%。

互动代码/透明度

对于谷歌实验室,你需要一个谷歌帐户来查看代码,你也不能在谷歌实验室运行只读脚本,所以在你的操场上做一个副本。最后,我永远不会请求允许访问你在 Google Drive 上的文件,仅供参考。编码快乐!同样为了透明,我在训练期间上传了所有的日志。

要访问案例 1 的代码请点击此处,要访问日志请点击此处
访问案例 2 的代码请点击此处,访问日志请点击此处
访问案例 3 的代码请点击此处,访问日志请点击此处
要访问案例 4 的代码请点击此处,要访问的日志请点击此处。

最后的话

这些都是由许多聪明的研究人员完成的惊人的工作,然而,对于这个实验来说,没有一个看起来像是灵丹妙药。

如果发现任何错误,请发电子邮件到 jae.duk.seo@gmail.com 给我,如果你想看我所有写作的列表,请在这里查看我的网站。

同时,在我的 twitter 上关注我这里,访问我的网站,或者我的 Youtube 频道了解更多内容。我还实现了广残网,请点击这里查看博文 t。

参考

  1. 2017 年深度学习优化亮点。(2017).塞巴斯蒂安·鲁德。检索于 2018 年 5 月 7 日,来自http://ruder.io/deep-learning-optimization-2017/
  2. 只有 Numpy:实现和比较梯度下降优化算法+谷歌大脑的…(2018).走向数据科学。2018 年 5 月 7 日检索,来自https://towards data science . com/only-numpy-implementing-and-comparison-gradient-descent-optimization-algorithms-Google-brains-8870 b 133102 b
  3. 克利夫特博士、安特辛纳、t .和霍克雷特博士(2015 年)。通过指数线性单元(ELUs)进行快速准确的深度网络学习。Arxiv.org。检索于 2018 年 5 月 7 日,来自https://arxiv.org/abs/1511.07289
  4. [ICLR 2016]通过指数线性单元(ELUs)进行快速准确的深度网络学习,具有…(2018).走向数据科学。2018 年 5 月 7 日检索,来自https://towards data science . com/iclr-2016-fast-and-accurate-deep-networks-learning-by-index-linear-units-elus-with-c 0 cdbb 71 bb 02
  5. 张量流正则化。(2018).ritchieng . github . io . 2018 年 5 月 7 日检索,来自http://www . ritchieng . com/machine-learning/deep-learning/tensor flow/regulation/
  6. tf.cond |张量流。(2018).张量流。检索于 2018 年 5 月 7 日,来自https://www.tensorflow.org/api_docs/python/tf/cond
  7. '开关'),V. (2018)。值错误:形状的等级必须为 0,但对于“cond _ 11/Switch”(op:“Switch”)的等级为 1。堆栈溢出。2018 年 5 月 8 日检索,来自https://stack overflow . com/questions/47739707/value error-shape-must-be-rank-0-but-is-rank-1-for-cond-11-switch-op-switch
  8. tensorflow?,H. (2018)。如何在 tensorflow 中求圆周率?。堆栈溢出。检索于 2018 年 5 月 8 日,来自https://stack overflow . com/questions/45995471/how-to-get-pi-in-tensor flow
  9. 网络?,H. (2018)。如何计算卷积神经网络的参数个数?。堆栈溢出。检索于 2018 年 5 月 8 日,来自https://stack overflow . com/questions/28232235/how-to-calculation-the-number of-parameters-of-convolutionary-neural-networks
  10. Loshchilov,I .,& Hutter,F. (2017)。修正 Adam 中的权重衰减正则化。 arXiv 预印本 arXiv:1711.05101
  11. 示例:基础— imgaug 0.2.5 文档。(2018).img aug . readthe docs . io . 2018 年 5 月 8 日检索,来自http://img aug . readthe docs . io/en/latest/source/examples _ basics . html
  12. [ICLR 2016]通过指数线性单元(ELUs)进行快速准确的深度网络学习,具有…(2018).走向数据科学。2018 年 5 月 8 日检索,来自https://towards data science . com/iclr-2016-fast-and-accurate-deep-networks-learning-by-index-linear-units-elus-with-c 0 cdbb 71 bb 02
  13. (2018).Arxiv.org。于 2018 年 5 月 8 日检索,来自https://arxiv.org/pdf/1711.05101.pdf

从零开始使用梯度下降优化在 Python 中实现单变量多项式回归

原文:https://towardsdatascience.com/implementation-of-uni-variate-linear-regression-in-python-using-gradient-descent-optimization-from-3491a13ca2b0?source=collection_archive---------10-----------------------

学习、实施和调整…

回归是一种对特征空间中的数据或数据点进行连续分类的方法。弗朗西斯·高尔顿在 1886 年发明了回归线的用法[1]。

线性回归

这是多项式回归的一个特例,假设中多项式的次数是 1。一般多项式回归将在文章的后半部分讨论。顾名思义,“线性”,这意味着关于机器学习算法的假设本质上是线性的,或者仅仅是线性方程。耶!!这确实是一个线性方程。在单变量线性回归中,目标变量依赖于单一特征或变量。

单变量线性回归的假设如下:

where theta_0 and theta_1 are the parameters and x is the single feature or variable

上述假设也可以用矩阵乘法格式或向量代数的形式写成:

存在与取决于参数θ_ 0 和θ_ 1 的假设相关联的成本函数。

线性回归的成本函数通常如下所示:

现在,这两个参数 theta_0 和 theta_1 必须采用这样的值,使得该成本函数值(即成本)采用可能的最小值。因此,现在的基本目标是找到成本最小的θ_ 0 和θ_ 1 的值,或者简单地找到成本函数的最小值。

梯度下降是最重要的凸优化技术之一,使用它可以找到函数的最小值。梯度下降算法如下所示:

梯度下降有两种方法:

  1. 随机梯度下降
  2. 批量梯度下降

使用随机梯度下降实现线性回归:

在随机梯度下降中,运行梯度下降算法,一次从数据集中取一个实例。

实现是通过创建具有不同操作的 3 个模块来完成的:

=>hypothesis():是在给定 theta (theta_0 和 theta_1)和 Feature,X 作为输入的情况下,计算并输出目标变量的假设值的函数。假设()的实现如下所示:

def **hypothesis**(theta, X):
    h = np.ones((X.shape[0],1))
    for i in range(0,X.shape[0]):
        x = np.concatenate((np.ones(1), np.array([X[i]])), axis = 0)
        h[i] = float(np.matmul(theta, x))
    h = h.reshape(X.shape[0])
    return h

=>SGD():该函数执行随机梯度下降算法,将当前值 theta_0 和 theta_1、alpha、迭代次数(num_iters)、假设值(h)、特征集(X)和目标变量集(y)作为输入,并在由实例表征的每次迭代时输出优化的 theta (theta_0 和 theta_1)。SGD()的实现如下所示:

def **SGD**(theta, alpha, num_iters, h, X, y):
    for i in range(0,num_iters):
        theta[0] = theta[0] - (alpha) * (h - y)
        theta[1] = theta[1] - (alpha) * ((h - y) * X)
        h = theta[1]*X + theta[0] 
    return theta

=>sgd_linear_regression():它是主函数,将特征集(X)、目标变量集(y)、学习速率和迭代次数(num_iters)作为输入,输出最终的优化θ,即代价函数在随机梯度下降后几乎达到最小值的θ_ 0 和θ_ 1 的值。

def **sgd_linear_regression**(X, y, alpha, num_iters):
    # initializing the parameter vector...
    theta = np.zeros(2)
    # hypothesis calculation....
    h = hypothesis(theta, X)    
    # returning the optimized parameters by Gradient Descent...
    for i in range(0, X.shape[0]):
        theta = SGD(theta,alpha,num_iters,h[i],X[i],y[i])
    theta = theta.reshape(1, 2)
    return theta

现在,我们来看一个实践数据集,它包含了公司利润如何依赖于城市人口的信息。该数据集可在 GitHub link 上获得,

[## navoneel 1092283/单变量 _ 回归

通过在 GitHub 上创建帐户,为 navoneel 1092283/univariate _ regression 开发做出贡献。

github.com](https://github.com/navoneel1092283/univariate_regression)

问题陈述:给定一个城市的人口,用线性回归分析预测一家公司的利润

数据读入 Numpy 数组:

data = np.loadtxt('data1.txt', delimiter=',')
X_train = data[:,0] #the feature_set
y_train = data[:,1] #the labels

数据可视化:可以使用散点图来可视化数据集:

import matplotlib.pyplot as plt
plt.scatter(X_train, y_train)
plt.xlabel('Population of City in 10,000s')
plt.ylabel('Profit in $10,000s')

散点图数据可视化看起来像-

Scatter Plot

使用三模块线性回归-SGD:

# calling the principal function with **learning_rate = 0.0001** and 
# **num_iters = 100000**
theta = sgd_linear_regression(X_train, y_train, 0.0001, 100000)

θ输出结果为:

theta after SGD

散点图上θ的可视化:

获得的θ的回归线可视化可以在散点图上完成:

import matplotlib.pyplot as plt 
# getting the predictions...
training_predictions = hypothesis(theta, X_train)
scatter = plt.scatter(X_train, y_train, label="training data")
regression_line = plt.plot(X_train, training_predictions
                           , label="linear regression")
plt.legend()
plt.xlabel('Population of City in 10,000s')
plt.ylabel('Profit in $10,000s')

回归线可视化结果为:

Regression Line Visualization after SGD

使用批量梯度下降实现线性回归:

在批量梯度下降中,梯度下降算法运行,一次从数据集中提取所有实例。

实现是通过创建具有不同操作的 3 个模块来完成的:

=>hypothesis():是在给定 theta (theta_0 和 theta_1)和 Feature,X 作为输入的情况下,计算并输出目标变量的假设值的函数。假设()的实现保持不变。

=>BGD():它是执行批量梯度下降算法的函数,将当前的θ_ 0 和θ_ 1、α、迭代次数(num_iters)、所有样本的假设值列表(h)、特征集(X)和目标变量集(y)作为输入,并输出优化的θ(θ_ 0 和θ_ 1)、θ_ 0 历史(θ_ 0)和θ_ 1 历史(θ_ 1),即每次迭代的θ_ 0 和θ_ 1 的值,以及最终包含成本函数值的成本历史 Gradient_Descent()的实现如下所示:

def **BGD**(theta, alpha, num_iters, h, X, y):
    cost = np.ones(num_iters)
    theta_0 = np.ones(num_iters)
    theta_1 = np.ones(num_iters)
    for i in range(0,num_iters):
        theta[0] = theta[0] - (alpha/X.shape[0]) * sum(h - y)
        theta[1] = theta[1] - (alpha/X.shape[0]) * sum((h - y) * X)
        h = hypothesis(theta, X)
        cost[i] = (1/X.shape[0]) * 0.5 * sum(np.square(h - y))
        theta_0[i] = theta[0]
        theta_1[i] = theta[1]
    theta = theta.reshape(1,2)
    return theta, theta_0, theta_1, cost

=>linear_regression():它是主函数,将特征集(X)、目标变量集(y)、学习速率和迭代次数(num_iters)作为输入,并输出最终优化的 theta,即成本函数在批量梯度下降后几乎达到最小值的 theta_0 和 theta_1 的值,以及存储每次迭代的成本值的 cost

def **linear_regression**(X, y, alpha, num_iters):
    # initializing the parameter vector...
    theta = np.zeros(2)
    # hypothesis calculation....
    h = hypothesis(theta, X)    
    # returning the optimized parameters by Gradient Descent...
    theta,theta_0,theta_1,cost= BGD(theta,alpha,num_iters,h,X,y)
    return theta, theta_0, theta_1, cost

在相同的利润估算数据集上使用 3 模块线性回归 BGD:

data = np.loadtxt('data1.txt', delimiter=',')
X_train = data[:,0] #the feature_set
y_train = data[:,1] #the labels
# calling the principal function with **learning_rate = 0.0001** and 
# **num_iters = 300**
theta,theta_0,theta_1,cost=linear_regression(X_train,y_train,
                                             0.0001,300)

θ输出结果为:

theta after BGD

散点图上θ的可视化:

获得的θ的回归线可视化可以在散点图上完成:

import matplotlib.pyplot as plt
training_predictions = hypothesis(theta, X_train)
scatter = plt.scatter(X_train, y_train, label="training data")
regression_line = plt.plot(X_train, training_predictions, label="linear regression")
plt.legend()
plt.xlabel('Population of City in 10,000s')
plt.ylabel('Profit in $10,000s')

回归线可视化结果为:

Regression Line Visualization after BGD

此外,在逐迭代的批量梯度下降过程中,成本已经降低。成本的降低借助于线形曲线和曲面图显示出来。

代表 300 次迭代中成本降低的线形曲线:

import matplotlib.pyplot as plt
cost = list(cost)
n_iterations = [x for x in range(1,301)]
plt.plot(n_iterations, cost)
plt.xlabel('No. of iterations')
plt.ylabel('Cost')

线条曲线显示为:

Line Curve Representation of Cost Minimization using BGD

表示成本降低的曲面图:

J = np.ones((300,300))
in1 = 0
in2 = 0
theta_0 = theta_0.reshape(300)
theta_1 = theta_1.reshape(300)
for i in theta_0:
    for j in theta_1:
        t = np.array([i,j])
        h = hypothesis(t, X_train)
        J[in1][in2]=(1/X_train.shape[0])*0.5*sum(np.square(h-y_train))
        in2 = in2 + 1
    in1 = in1 + 1
    in2 = 0from mpl_toolkits.mplot3d import Axes3Dfig = plt.figure()
ax = fig.add_subplot(111, projection='3d')X,Y = np.meshgrid(theta_0, theta_1)
ax.plot_surface(X, Y, J)
ax.set_xlabel('theta_0')
ax.set_ylabel('theta_1')
ax.set_zlabel('J')

Surface Plot Representation of Cost Minimizaion with values of theta_0 and theta_1

表现分析(新加坡元对 BGD)

模型性能分析基于以下指标:

= >平均绝对误差:实例样本中预测值和实际观测值之间的平均模(差)。

寻找梅:

ae = 0 # Absolute Error
for i in range(0,y_train.shape[0]):
    ae = ae + abs(training_predictions[i] - y_train[i])
MAE = ae/y_train.shape[0] # Mean Absolute Error

= >均方误差:实例样本中预测值和实际观测值之间的平方差的平均值。

查找 MSE:

from math import *
se = 0 # Square Error
for i in range(0,y_train.shape[0]):
    se = se + pow((training_predictions[i] - y_train[i]), 2)
MSE = se/y_train.shape[0] # Mean Square Error

= >均方根误差:在一个实例样本中,预测值和实际观测值之间的平方差的平均值的平方根。

寻找 RMSE:

from math import *
RMSE = sqrt(MSE) # Root Mean Square Error

=>R 平方得分或决定系数:

import numpy as np
y_m = np.mean(y_train)SStot = 0
for i in range(0,y_train.shape[0]):
    SStot = SStot + pow((y_train[i] - y_m), 2)SSres = 0
for i in range(0,y_train.shape[0]):
    SSres = SSres + pow((y_train[i] - training_predictions[i]), 2)R_Square_Score = 1 - (SSres/SStot)

新加坡元和 BGD 的比较:

因此,批量梯度下降在各方面都明显优于随机梯度下降!!

这就是使用梯度下降在 Python 中实现单变量线性回归的全部内容。

多项式回归

在涉及对单个特征或变量进行回归的预测分析问题中(称为单变量回归),多项式回归是回归分析的一个重要变体,主要用作线性回归的性能助推器。在本文中,我将介绍多项式回归、它的 Python 实现以及在一个实际问题上的应用和性能分析。

正如前缀“多项式”所暗示的,机器学习算法的相应假设是多项式或多项式方程。因此,这可以是任何次数的,比如如果假设是一次多项式,那么它是一个线性方程,因此称为线性回归,如果假设是二次多项式,那么它是一个二次方程,类似地,如果是三次多项式,那么它是一个三次方程,等等。因此,可以说:

线性回归是多项式回归的真子集或特例方法,因此多项式回归也称为广义回归

多项式回归的假设如下:

where theta_0, theta_1, theta_2, theta_3,…., theta_n are the parameters and x is the single feature or variable

其中θ_ 0,θ_ 1,θ_ 2,θ_ 3,…,theta_n 是参数, x 是单一特征或变量

上述假设也可以用矩阵乘法格式或向量代数的形式写成:

这里,也存在与依赖于参数θ_ 0,θ_ 1,θ_ 2,θ_ 3,…的假设相关联的成本函数。,theta_n。

一般来说,广义回归的成本函数如下所示:

因此,这些参数θ_ 0,θ_ 1,θ_ 2,…,θ_ n 必须采用这样的值,对于这些值,成本函数(或简单地成本)达到其可能的最小值。换句话说,需要找出成本函数的最小值。

批量梯度下降可以用作优化函数。

使用批量梯度下降实现多项式回归:

实现是通过创建 3 个执行不同操作的模块来完成的。

=>hypothesis():是计算并输出目标变量的假设值的函数,给定 theta (theta_0,theta_1,theta_2,theta_3,…,theta_n),特征 X 和多项式回归中多项式的次数(n)作为输入。假设()的实现如下所示:

def **hypothesis**(theta, X, n):
    h = np.ones((X.shape[0],1))
    theta = theta.reshape(1,n+1)
    for i in range(0,X.shape[0]):
        x_array = np.ones(n+1)
        for j in range(0,n+1):
            x_array[j] = pow(X[i],j)
        x_array = x_array.reshape(n+1,1)
        h[i] = float(np.matmul(theta, x_array))
    h = h.reshape(X.shape[0])
    return h

=>BGD():该函数执行批量梯度下降算法,将当前的θ值(theta_0,theta_1,…,theta_n)、学习速率(alpha)、迭代次数(num_iters)、所有样本的假设值列表(h)、特征集(X)、目标变量集(y)和多项式回归中多项式的次数(n)作为输入,并输出优化的 theta (theta_0,theta_1,theta_2,theta_3,…,theta_n)、theta_history(包含每次迭代的 theta 值的列表)和最终 BGD()的实现如下所示:

def **BGD**(theta, alpha, num_iters, h, X, y, n):
    theta_history = np.ones((num_iters,n+1))
    cost = np.ones(num_iters)
    for i in range(0,num_iters):
        theta[0] = theta[0] — (alpha/X.shape[0]) * sum(h — y)
        for j in range(1,n+1):
            theta[j]=theta[j]-(alpha/X.shape[0])*sum((h-y)*pow(X,j))
        theta_history[i] = theta
        h = hypothesis(theta, X, n)
        cost[i] = (1/X.shape[0]) * 0.5 * sum(np.square(h — y))
    theta = theta.reshape(1,n+1)
    return theta, theta_history, cost

=>poly_regression():它是主函数,将特征集(X)、目标变量集(y)、学习率(alpha)、多项式回归中多项式的次数(n)和迭代次数(num_iters)作为输入,输出最终优化的 theta,即[ theta_0,theta_1,theta_2,theta_3,…]的值。成本函数在批量梯度下降后几乎达到最小值的θ_ n****,存储每次迭代的θ值的θ_ history,以及存储每次迭代的成本值的 cost

def **poly_regression**(X, y, alpha, n, num_iters):
    # initializing the parameter vector…
    theta = np.zeros(n+1)
    # hypothesis calculation….
    h = hypothesis(theta, X, n)
    # returning the optimized parameters by Gradient Descent
    theta,theta_history,cost=BGD(theta,alpha,num_iters,h, X, y, n)
    return theta, theta_history, cost

现在,我们来看一个实践数据集,它包含了公司利润如何依赖于城市人口的信息。

在利润估算数据集上使用 3 模多项式回归,

[## navoneel 1092283/单变量 _ 回归

通过在 GitHub 上创建帐户,为 navoneel 1092283/univariate _ regression 开发做出贡献。

github.com](https://github.com/navoneel1092283/univariate_regression)

问题陈述:给定一个城市的人口,用多项式回归分析预测一家公司的利润

data = np.loadtxt(‘data1.txt’, delimiter=’,’)
X_train = data[:,0] #the feature_set
y_train = data[:,1] #the labels
**# calling the principal function with learning_rate = 0.0001 and 
# n = 2(quadratic_regression) and num_iters = 300000** theta,theta_history,cost=poly_regression(X_train,y_train,
                                         0.00001,2,300000)

theta after Polynomial Regression

散点图上θ的可视化:

获得的θ的回归线可视化可以在散点图上完成:

import matplotlib.pyplot as plt
training_predictions = hypothesis(theta, X_train, 2)
scatter = plt.scatter(X_train, y_train, label=”training data”) regression_line = plt.plot(X_train, training_predictions
                          ,label=”polynomial (degree 2) regression”)
plt.legend()
plt.xlabel(‘Population of City in 10,000s’)
plt.ylabel(‘Profit in $10,000s’)

回归线可视化结果为:

Regression Line Visualization after Quadratic Regression

此外,在逐迭代的批量梯度下降过程中,成本已经降低。成本的降低借助于曲线显示出来。

import matplotlib.pyplot as plt
cost = list(cost)
n_iterations = [x for x in range(1,300001)]
plt.plot(n_iterations, cost)
plt.xlabel(‘No. of iterations’)
plt.ylabel(‘Cost’)

线条曲线显示为:

Line Curve Representation of Cost Minimization using BGD in Quadratic Regression

现在,必须进行模型性能分析以及多项式回归与线性回归的比较(迭代次数相同)。

因此,线性回归是使用批量梯度下降完成的,迭代次数为 3,00,000 次,学习速率(alpha)为 0.0001,使用的是我上一篇文章中的实现:

[## 使用梯度下降优化在 Python 中实现单变量线性回归…

学习、编码和调整…

towardsdatascience.com](/implementation-of-uni-variate-linear-regression-in-python-using-gradient-descent-optimization-from-3491a13ca2b0)

data = np.loadtxt(‘data1.txt’, delimiter=’,’)
X_train = data[:,0] #the feature_set
y_train = data[:,1] #the labels
# calling the principal function with **learning_rate = 0.0001** and
# **num_iters = 300000**
theta,theta_0,theta_1,cost=linear_regression(X_train,y_train,
                                             0.0001,300000)

theta after Linear Regression

散点图上θ的可视化:

获得的θ的回归线可视化可以在散点图上完成:

import matplotlib.pyplot as plt
training_predictions = hypothesis(theta, X_train)
scatter = plt.scatter(X_train, y_train, label=”training data”)
regression_line = plt.plot(X_train, training_predictions
                           , label=”linear regression”)
plt.legend()
plt.xlabel(‘Population of City in 10,000s’)
plt.ylabel(‘Profit in $10,000s’)

Regression Line Visualization after Linear Regression

此外,在逐迭代的批量梯度下降过程中,成本已经降低。成本的降低借助于曲线显示出来。

import matplotlib.pyplot as plt
cost = list(cost)
n_iterations = [x for x in range(1,300001)]
plt.plot(n_iterations, cost)
plt.xlabel(‘No. of iterations’)
plt.ylabel(‘Cost’)

线条曲线显示为:

Line Curve Representation of Cost Minimization using BGD in Linear Regression

性能分析(使用 BGD 优化的线性回归与二次回归):

但是在这里,使用批量梯度下降优化,我们最终得到的线性回归在所有方面都优于多项式(二次)回归。但是,在实践中,多项式(高次或广义)回归总是比线性回归表现更好。虽然使用 BGD,但由于 BGD 优化本身的一些缺点,我们无法获得与命题相匹配的实验结果。还有另一种优化或寻找多项式(也称线性)回归中成本函数最小值的方法,称为【OLS(普通最小二乘法)】正规方程法

我将在以后的文章中讨论这些内容,并提到本文的参考资料。使用 OLS,可以清楚地证明多项式(在本实验中是二次的)比线性回归表现得更好。除了单变量问题,使用适当的特征工程技术,多项式回归也可用于多变量问题(多特征)。

这就是多项式回归的全部内容。

参考文献

[1]迈克尔·布尔默(2003 年)。弗朗西斯·高尔顿:遗传和生物统计学的先驱。约翰霍普金斯大学出版社ISBN0–8018–7403–3

实现 DeepMind 基线星际强化学习代理

原文:https://towardsdatascience.com/implementing-a-deepmind-baseline-starcraft-reinforcement-learning-agent-7b1ef6f41b52?source=collection_archive---------9-----------------------

将研究用语翻译成代码

实现研究论文中描述的深度学习模型是一种具有挑战性但具有启发性的体验,它显示了有多少信息可以压缩到少数几个句子或段落中。

本周,在了解了《星际争霸 python API 和强化学习环境的诀窍之后,我开始构建《T4》中描述的三个基线代理中的第一个:强化学习的新挑战。

具体来说,一个优势行动者-批评家代理使用卷积神经网络架构来估计状态值和最佳策略,该架构基于深度强化学习的异步方法中的架构。由于资源限制,我没有实现 A3C 的“异步”部分,这意味着我一次只运行一个代理,而不是并行运行多个代理。

在这篇文章中,我将重点介绍这两篇研究论文中关于代理设计的部分,其中包含了与技术实现相关的最多信息。我希望这将作为一个有用的例子,说明如何将研究人员的语言翻译成代码。我的完整实现可以在这里找到。

概括地说,深度强化学习代理需要满足五个要求:

  1. 接收包含状态信息的感知(输入)
  2. 通过深层网络处理感知以产生状态表示。
  3. 使用状态表示来通知策略(从状态到动作的功能映射)。
  4. 使用该策略选择操作并与环境交互。
  5. 从环境中获得奖励,并利用这些奖励来改进国家和政策的模式。

这只是一个任意的分解,但是我发现它直观上是有帮助的,并将使用它来指导本文的结构。

输入

因此,主要的观察来自于以 N × M 像素渲染的特征层集合…除了屏幕和小地图,游戏的人机界面还提供了各种非空间观察。

对于与 PySC2 交互的代理,它必须有一个在每个时间步长调用的step(self, obs)方法。此外,它可能有一个在每集开始时调用的reset(self)方法。

我喜欢为我的深度神经网络使用单独的类,如下所示。以要素图层形式出现的输入相对直接地对应于张量流图中的占位符。API 将它们暴露在形状为[channels, y, x]的数组中,所以后来在我的网络中,我确保适当地排列这些维度,以便它们可以被馈送到卷积层,并且在将一批 1 馈送到图中时经常使用np.expand_dims

国家代表权

我们将包含分类值的所有要素图层嵌入到一个连续空间中,这相当于在信道维度中使用一键编码,然后进行 1 × 1 卷积。我们也用对数变换重新缩放数字特征,因为它们中的一些如生命值或矿物可能达到相当高的值。

虽然我发现“嵌入”的语言有点吓人,但随后的细节证明实现起来更简单。比起在卷积层之后应用一键编码,我发现推断一个特征是分类的还是数字的是更费力的任务。

它处理屏幕和小地图要素图层,这两个图层分别有 16,32 个大小为 8,4 和步幅为 4,2 的过滤器。非空间特征向量由具有双曲正切非线性的线性层处理。结果被连接并通过一个带有 ReLU 激活的线性层发送。

Figure from https://arxiv.org/abs/1708.04782

虽然论文的这些段落对应于一些最长的代码块,但它们很容易实现,因为有强大的深度学习框架可用,其中 Tensorflow 是我在这里选择的工具。

策略表示

…我们建议利用链式法则,以自动回归的方式表示策略:

我在这里困惑的一点是关于“链式法则”它指的是概率论中的一般乘积规则,而不是微积分中也称为“链式规则”的规则。

在我们的大多数实验中,我们发现独立地对子动作建模就足够了…对于空间动作(坐标),我们独立地对策略建模,以选择(离散的)x 和 y 坐标。

基本上,因为在星际争霸 2 中任何给定的动作(称为函数标识符)可能需要可变数量的参数,一种有效的方法来表示函数标识符和参数上的策略是对每种类型有一个独立的策略,其中任何参数给定一个不需要它的函数标识符的概率变为零。

PySC2 中大约有 10 种通用类型的函数标识符,每一种都需要不同的参数序列。在 Tensorflow 图中实现时,我发现使用字典是跟踪所有输出层的好方法。我还为占位符构建了一个字典,稍后将用于训练网络。

动作选择

为了确保我们的代理永远不会选择不可用的动作,我们屏蔽了 a0 的功能标识符选择,这样只有适当的子集可以被采样,模仿玩家随机点击 UI 上的按钮的方式。我们通过屏蔽动作和重整 a0 上的概率分布来实现这一点。

虽然在我的第一遍中,我在 Tensorflow 图之外实现了这个屏蔽,但在实际选择动作时,它也可以在图中实现,在未来的更新中,我可能会将它移到那里。

培养

在 A3C 中,我们在网络的 K = 40 个前向步骤之后或者如果接收到终端信号,就切断轨迹并运行反向传播。

这句话实际上启发了整个帖子。最初我不知道“切断轨迹”意味着什么,于是我踏上了知识之旅。以下两句语录来自原 A3C 论文。

像我们的 n 步 Q-learning 的变体一样,我们的 actor-critic 的变体也以前瞻的观点操作,并使用相同的 n 步回报组合来更新策略和价值函数。

当然,我直接跳到了 A3C 代理的部分,但是我知道线索越来越多了。

然后,该算法为自上次更新以来遇到的每个状态-动作对计算 n 步 Q 学习更新的梯度。每个 n 步更新使用最长的可能 n 步返回,导致最后一个状态的一步更新,倒数第二个状态的两步更新,等等,总共最多 t_max 个更新。在单个梯度步骤中应用累积的更新。

最后,一切都清楚了!不,不是真的。这仍然是一篇高度密集的研究论文,但是在附录中一些伪代码的帮助下,我终于明白了一些关于用来训练网络的目标是如何产生的。

额外收获:A3C(或 A2C)渐变

A3C 梯度定义如下:

我打算将来写这方面的东西,但是这个等式中有太多东西需要解开,所以我认为把它包括进来会很有趣。有趣的一点是,策略和值梯度代表了性质上不同的东西,但是通过简单的加法将它们结合在一起仍然能够产生可行的优化目标(提供了一些可以调整的超参数旋钮)。

令我感兴趣的还有“优势”(观察到的回报和估计值之间的差异,梯度成分通过该差异进行缩放)作为一个常数因子,尽管它在计算中包括了网络输出值。这意味着我必须使用[tf.stop_gradient](https://www.tensorflow.org/api_docs/python/tf/stop_gradient),这样权重就不会以游戏化等式的方式更新以改变价值估计。

结论

我在两篇指导性研究论文中最重要的部分加了下划线,并展示了它们如何映射到代码上。这个项目让我对研究人员能够将堆积如山的信息浓缩成短到可以在 Twitter 上分享的句子有了新的认识。

虽然我的评论很简短——也是故意如此,因为我希望强调科学报道和代码之间的关系——但我计划继续写一篇文章,更深入地探究所有这些概念的含义

实现生成性对抗网络(GAN/DCGAN)来绘制人脸

原文:https://towardsdatascience.com/implementing-a-generative-adversarial-network-gan-dcgan-to-draw-human-faces-8291616904a?source=collection_archive---------0-----------------------

在上一个教程中,我们学习了使用 Tensorflow 来设计一个变分自动编码器 (VAE),它可以绘制 MNIST 字符。大多数创建的数字看起来很好。只有一个缺点——一些创建的图像看起来有点模糊。用均方误差损失函数训练 VAE。然而,很难对精确的字符边缘位置进行编码,这导致网络无法确定这些边缘。如果一个字符的边缘开始向左或向右多几个像素真的有关系吗?我不这么认为。

在本文中,我们将了解如何训练一个不依赖于均方误差或任何相关损失函数的网络,而是让它自己学习真实图像的样子。我们将要了解的架构叫做 深度卷积生成对抗网络(DCGAN) 。罗威尔·阿蒂恩萨在三月下旬写的一篇很棒的文章启发我完成了这个项目,他教我们如何在 keras 应用同样的技术。为了能够与上一个基于 VAE 的模型进行比较,我们将首先看看如何实现一个能够绘制 MNIST 角色的 DCGAN。之后,我们将在一个更酷的项目中应用我们的知识——只需一些小的调整,我们的网络将学会如何绘制(半)逼真的人脸!

深度卷积生成对抗网络

像 VAE 一样,DCGAN 是一种学习生成新内容的架构。就像 VAE 一样,DCGAN 由两部分组成。在这种情况下,它们是:

  • 鉴别器,,学习如何从我们想要创建的类型的真实对象中辨别出赝品
  • 生成器,**创建新内容并试图欺骗鉴别器

基本思想是两个网络部分相互竞争。当鉴别器变得更好时,生成器也需要变得更好,否则它不能再欺骗鉴别器了。类似地,当发生器变得更好时,鉴别器也必须变得更好,否则它将失去区分真假内容的能力。

如果你想对 GANs 有更多的直觉,这里有一篇的文章,作者chan chana sornsountorn,描述了一些应用了 DCGANs 的创意项目。其中一个项目是 MNIST 人物的生成,另一个是人脸的生成。在本文中,我们将了解如何在 Python 和 Tensorflow 中实现所描述的技术。我们将从 MNIST 的角色开始。如果你想看这个教程的全部代码,去我的 github 账号看看 MNIST人脸生成的代码。

* [## Felix mohr/使用 Python 进行深度学习

在 GitHub 上创建一个帐户,为深度学习 Python 开发做贡献。

github.com](https://github.com/FelixMohr/Deep-learning-with-Python)

设置基础

所以,让我们直接进入代码。

和上一篇教程一样,我们使用 tensorflow 自己的方法来访问批量的 MNIST 字符。我们将批量大小设置为 64。我们的生成器将噪声作为输入。这些输入的数量被设置为 100。批量标准化大大改善了这个网络的训练。对于 tensorflow 应用批处理规范化,我们需要让它知道我们是否处于训练模式。keep_prob变量将由我们的辍学层使用,我们引入辍学层是为了获得更稳定的学习结果。lrelu定义了流行的 leaky ReLU,希望 tensorflow 的未来版本能够支持它!我首先尝试将标准 ReLUs 应用于这个网络,但这导致了众所周知的 死亡 ReLU 问题 ,并且我收到了看起来像 Kazimir Malevich 的艺术品的生成图像——我只是得到了黑色方块

然后,我们定义一个函数binary_crossentropy,我们将在以后计算损失时使用它。

鉴别器

现在,我们可以定义鉴别器。它看起来类似于我们的 VAE 的编码器部分。作为输入,它采用真实或虚假的 MNIST 数字(28 x 28 像素灰度图像)并应用一系列卷积。最后,我们使用 sigmoid 来确保我们的输出可以被解释为输入图像是真实的 MNIST 字符的概率。

发电机

发生器——就像我们的 VAE 中的解码器部分——接收噪音,并尝试学习如何将噪音转换为数字。为此,它应用了几个转置卷积。一开始我没有对生成器应用批量归一化,它的学习好像真的效率不高。应用批量标准化图层后,学习能力有了很大提高。此外,我首先有一个更大的密集层接受发电机的输入。这导致发生器总是产生相同的输出,不管输入噪声是什么,例如,它总是输出看起来完全相同的 9(模式崩溃)。另一方面,根本不使用密集层会导致生成器在多次迭代后没有学到任何有意义的东西。老实说,调整发电机需要相当大的努力!

损失函数和优化器

现在,我们将两部分连接在一起,就像我们在上一个教程中对 VAE 的编码器和解码器所做的那样。但是,我们必须创建两个鉴别器对象:

  • 第一个对象接收实像
  • 第二对象接收假图像

第二个对象的reuse被设置为True,所以两个对象共享它们的变量。我们需要两种情况来计算两种类型的损失:

  • 当接收真实图像时,鉴别器应该学会计算高值(接近 1 ),这意味着它确信输入图像是真实的
  • 当接收到假图像时,它应该计算低值(接近 0 ,这意味着它确信输入图像不是真实的

为此,我们使用前面定义的二元交叉熵函数。生成器试图实现相反的目标,它试图让鉴别器给假图像分配高值。

现在,我们也应用一些正则化。我们创建了两个不同的优化器,一个用于鉴别器,一个用于生成器。我们必须定义允许这些优化器修改哪些变量,否则生成器的优化器可能会弄乱鉴别器的变量,反之亦然。

在应用批处理规范化时,我们必须向我们的优化器提供update_ops——看看 tensorflow 文档,了解关于这个主题的更多信息。

训练 GAN

最后,有趣的部分开始了——让我们训练我们的网络!我们向生成器输入随机值,它将学习从这些噪音中生成数字。我们还注意,通过平衡它们的损失,生成器和鉴别器都不会变得太强,否则,这将抑制任一部分的学习,甚至可能阻止网络学习任何东西(我有过这种经验)。

MNIST 结果

看看我们的生成器绘制的图片——它们看起来比 VAE 绘制的图片更真实,后者的边缘看起来更模糊。然而,训练比训练另一个模型花费的时间要长得多。我还必须提到,在创建的角色看起来有意义之前,我需要比罗威尔·阿蒂恩萨更多的迭代,所以特别是如果你没有强大的 GPU,你可能想参考本文顶部提到的他的架构。

MNIST characters created by our DCGAN

这是一个真正的优势,我们不依赖于基于像素位置的损失函数,使结果看起来不那么模糊。这在创建更复杂的数据时尤其重要,例如人脸图片。所以,只要有点耐心,结果最终会回报你的。

画人脸

我不会详细介绍生成人脸的完整代码,因为架构基本上是一样的。主要区别在于,我们现在使用三个颜色通道,而不是像以前那样使用一个通道,并且我们允许卷积转置层针对这种更复杂的输入数据学习更多的滤波器。你可以在我的 github 找到完整的代码。

我使用的数据集是麻省大学的 LFW(野外标记人脸)数据集。或许使用更大的数据集可以改善结果,但我还没有尝试过。为了让学习在相当长的时间内发生,我将图像缩小到 40 x 40 像素,并以前面提到的相同方式训练 DCGAN。生成器的卷积变换层创建了更多的过滤器,因为这个数据集比 MNIST 数据集更复杂。

Faces drawn by our neural network

看看结果吧!我在特斯拉 K80 GPU 上训练了大约一个小时的网络,以获得这些。也许这些家伙不会骗你相信他们是真人。但是想想看,神经网络以前从未见过任何人,在完成 MNIST 项目后,我们对它的重新设计付出了多么少的努力!这项技术显然有很大的应用潜力。

如果你喜欢这篇文章,你可能也会对我的关于使用变分自动编码器 生成 MNIST 字符的 教程感兴趣。*

用 Python 实现 Trie(不到 100 行代码)

原文:https://towardsdatascience.com/implementing-a-trie-data-structure-in-python-in-less-than-100-lines-of-code-a877ea23c1a1?source=collection_archive---------0-----------------------

介绍

让我问你一件事。一些我们经常遇到并且(几乎)总是忽略的有趣的事情。

你肯定还记得你的手机键盘上的那个漂亮的功能,你开始输入一个单词,它就开始向你显示建议。这真他妈的方便!事实上,由于这个原因,我几乎可以一直写英语单词而没有拼写错误。

你觉得,电脑到底怎么样(对!你的智能手机也是一台电脑)想出了这些建议?

事实证明,在许多情况下,使用某种特定的数据结构在您键入时向您显示单词建议。这种特殊的数据结构被称为 Trie

那么,什么是特里呢?在我开始定义它之前,让我给你看一张图。

(image courtsey — http://www.mathcs.emory.edu)

从上图可以看出,它是一个树状结构,每个节点代表给定字符串的一个字符。与二叉树不同,一个节点可能有两个以上的子节点。

我们来分析一个例子。我们假设我们从零开始,这意味着我们只有一个空的根节点,其他什么都没有。我们从“买”字开始。从图中可以清楚地看到,我们的 Trie 实现没有在根节点中存储一个字符。所以我们添加第一个字符,即“b”作为它的子节点。我们这样做是因为它在任何一个孩子身上都没有这种性格。否则,我们将跳过添加子节点。因为我们已经有了。然后是“u”字。在添加这个字符时,有一点我们必须注意,那就是我们需要搜索“u”是否出现在“b”的任何子节点中(我们最后添加的节点)以及T5【而不是 的根

而“y”也是如此。因此,一旦添加整个单词“buy”的操作完成,我们的 Trie 看起来就像这样

而现在是“牛”的时候了。我们重复同样的步骤,在我们的 Trie 中添加“bull”。只是这一次,我们不再添加“b”和“u”。因为它们已经存在。所以一旦手术完成,它看起来像这样-

我相信,这让您对什么是 Trie 以及在其中添加字符的操作是如何工作的有了一个清晰的概念。详细情况,你可以去维基百科。

在解决 Hackerrank 中的一个挑战时,我偶然发现了这种稍微有点非传统且讨论较少的数据结构。在摆弄了几个小时的代码后,我成功地编写了代码并解决了这个难题。这是我的代码的样子-

代码

Trie implementation in Python 3

它是如何工作的?

现在,我将简要介绍一下算法的主要步骤

  1. 要考虑的第一件事是我们如何添加新单词。add函数正是这样做的。它的工作方式非常简单。它将根节点(没有分配任何字符值的节点)和整个单词作为输入。
  2. 然后,它遍历这个单词,从第一个字符开始,一次一个字符。
  3. 它检查当前的“节点”(在指向根节点的过程的开始)是否有一个具有该字符的子节点。
  4. 如果找到了,它只是增加该节点的计数器,以表明它得到了该字符的重复出现。
  5. 如果没有找到,那么它只是添加一个新节点作为当前节点的子节点。
  6. 在这两种情况下(4 & 5),在从单词的下一个字符开始之前,它将子节点指定为“当前节点”(这意味着在下一次迭代中,它将从这里开始)。

这就是在特里树中添加一个单词的全部内容。它还做了一件事,就是在整个过程结束后标记一个单词的结束。这意味着特里树的每个叶节点将把word_finished设为真。

搜索前缀有几个简单的步骤-

  1. 它从根节点和要搜索的前缀开始。
  2. 它一次从前缀中取出一个字符,并搜索“当前节点”的子节点(在指向根节点的开头)以找到包含该字符的节点。
  3. 如果找到了,它将该子节点重新分配为“当前节点”(这意味着在下一个迭代步骤中,它将从这里开始)
  4. 如果没有找到,则返回 False,表示前缀不存在。
  5. 在这个算法中有一个小的变化来处理试图找到一个比单词本身更大的前缀的情况。这意味着,我们有hammer作为一个 Trie,我们正在搜索hammers

这就是用 Python 构建和遍历通用 Trie 数据结构的全部内容。

这里给出的代码是可重用的(和良好的注释:),并在公共领域。如果你需要,请随意使用它!

那都是乡亲们!我希望你喜欢这篇文章,如果是的话,请尽可能多的点击拍手。如果您有任何反馈或建议,请通过评论或直接通过我的 Linkedin 告诉我。这些将鼓励我在未来写更多的文章。回头见!

实施分析:向上扩展!

原文:https://towardsdatascience.com/implementing-analytics-scaling-up-93884c1bf1ed?source=collection_archive---------4-----------------------

你终于到了那个时刻:你知道你想用你的分析实现做什么,你的利益相关者都在船上,你准备好将其扩展到整个组织。现在怎么办?

在向更广泛的受众推广您的分析平台之前,您需要考虑几件事情:数据集的结构和存储,扩展您的分析的正确工具;您确保数据质量的方法;和适当的文档来指导您的团队正确使用数据。

结构和存储

您将在哪里以及如何存储您的数据?您的数据是结构化的还是非结构化的?真的需要“数据湖”吗?需要进行多少数据操作?什么是正确的安全和访问控制级别?一些用户(如您组织中的数据科学家)是否需要访问更多非结构化数据集来进行分析,而其他人则在寻找 BI 仪表盘、数据可视化和更结构化的报告?

SQL Server、Teradata 等关系数据库或 MySQL、PostgreSQL 等开源数据库支持大规模高效的数据存储。这些数据库使用结构化查询语言或 SQL,它允许用户编写用于基本数据过滤、组合和聚合的查询。您是希望使用关系数据库,还是选择提供更大灵活性的 Hadoop 框架,这将取决于您正在处理的数据类型以及您的用户可能想要回答的问题。

合适的工具

随着您需求的发展,您对满足这些需求的“正确工具”的定义也将随之变化。您可以从开源工具开始,随着您在企业范围内的扩展而转向许可产品。

虽然传统数据库可以使用查询和存储过程进行一些数据操作,但它们的主要目的是数据存储和检索。为了获得更强大的复杂数据分析、建模和报告功能,您可以尝试 Python 之类的脚本语言或 R 或 SAS 之类的统计软件包。它们可用于从数据库中提取数据,执行数据准备,然后将结果存储回数据库。他们还可以连接、提取和集成来自任何其他数据源(原始文件、网页、API)的数据,并执行数据验证和错误处理。

对于企业级数据集市,有许多商业和开源的、专门的提取、转换、加载(ETL)软件可用。许多已经与上游的数据库或商业智能和分析产品集成。大多数 ETL 产品不需要任何编码,数据管道可以以图形方式创建、可视化和执行。

确保数据质量

越早解决数据质量问题越好;终端用户花在数据争论上的时间越少,他们就可以更多地关注高价值分析。随着您组织的数据基础设施的成熟,从电子表格迁移到数据库和数据仓库,数据质量检查应该正式定义、记录和自动化。应该在数据输入期间使用预定义的业务规则逻辑自动处理异常,或者要求用户立即干预以纠正任何错误。

向终端用户提供干净、集中且可供分析的数据不应是单向的过程。允许最终用户专注于高价值分析,如数据挖掘、网络图、聚类等。,他们可以发现数据中的某些异常值和异常。有效的数据管理应该包括一个反馈循环来交流这些发现,并且如果必要的话,合并 ETL 过程中的任何变化,使得集中的数据管理更加动态和灵活。

证明文件

如果你是一个把数据集放在一起的人,你可能知道关于它的一切。数据来自哪里,您用来填充缺失值的插值方法,或者支出日期是指从资金承诺日期到组织收到资金的实际日期之间的任何时间。随着越来越多的人开始关注你的数据集,你不能再把这些知识视为理所当然。这就是适当的数据治理和质量文档的来源。

除了描述数据元素的内容、格式和结构的数据字典之外,源到目标映射允许用户追溯每个数据元素的原始来源。随着计算、转换和数据丰富数量的增长,这对于保持透明度和准确性变得越来越重要。实施和维护这些类型的文档可以降低滥用数据的风险。

这也是为强大的数据治理框架奠定基础的时刻!

实施分析:数据监管案例

原文:https://towardsdatascience.com/implementing-analytics-the-case-for-data-curation-647a0dd39e8b?source=collection_archive---------0-----------------------

“策展”是一个经常与博物馆和图书馆联系在一起的术语,但对于数据分析来说,它是发现、收集和展示数据的行为。

数据监管是选择最相关信息的过程,以满足业务用户对特定主题的需求;喜欢好的编辑或者博物馆馆长!它是将独立创建的数据源(结构化和半结构化数据)转化为可用于分析的统一数据集的过程,使用领域专家来指导该过程,以呈现最佳可用内容。适当的数据监管不仅需要数据管理、编程技能和领域专业知识,还需要整合正确信息的创造力,让业务用户发现新的见解。数据科学就是这样一个从需求中成长起来的领域。但是,数据科学家到底是什么?

“数据科学家是一个罕见的混合体,一个计算机科学家拥有构建软件的编程能力,能够收集、组合和管理来自各种来源的数据,一个统计学家知道如何从信息中获得洞察力。他们将创建新原型的技能与询问和回答关于数据及其秘密的最深层问题的创造力和彻底性相结合。”—杰克·波威

为什么数据监管是必要的?

组织拥有的数据在规模和复杂性上都在增长。然而,研究表明,许多组织只使用了大约 10%的数据,因为这些数据分散在组织的各个孤岛中。

数据集成 是跨组织的共同挑战。它可能由许多不同的因素驱动,例如:独立业务单位的孤立流程、业务过程中对其他公司的收购、遗留系统的数据质量,甚至只是尝试集成项目的预期劳动力成本。在 2008 年金融危机期间,许多银行面临的主要挑战之一是无法及时汇总整个组织的风险敞口。获取所有业务线和法律实体的总风险敞口可能需要数周时间,而不是数小时。随着危机在 2008 年秋季迅速恶化,这使得银行大大低估了它们对某些市场事件和交易对手的风险敞口。

Tableau 等 自助式分析工具 越来越受欢迎,这增加了在数据库中管理数据的必要性。这些工具旨在让最终用户能够“以思考的速度”直观地从数据仓库中查询数据,并快速可视化结果。这种类型的功能允许用户对数据进行多次不同的迭代,以真正探索数据并产生独特的见解。当底层数据库表没有被正确管理时,这些工具不能很好地工作。

数据监管的好处是什么?

  • 有效的数据监管流程或策略可以让组织在数据准备上花费更少的时间和金钱,而有更多的时间来回答业务问题。
  • 查看跨业务线报告可以帮助组织了解其风险,并准确衡量外部事件对运营的影响。
  • 结构合理的数据可以有效利用自助服务分析工具,帮助业务用户获得洞察力,而无需额外开发新的仪表板和报告。

有序逻辑回归

原文:https://towardsdatascience.com/implementing-and-interpreting-ordinal-logistic-regression-1ee699274cf5?source=collection_archive---------1-----------------------

R 中的概述和实现

Fig 1: Performance of an individual — Poor, Fair, Excellent

你能猜出下面提到的变量中有什么共同联系吗:

  • 工作满意度— 不满意、满意、高度满意
  • 个人表现— 差、一般、优秀
  • 监管对银行绩效的影响— 正面、中性、负面

变量不仅是分类的,而且它们也遵循一个顺序(从低到高/从高到低)。

如果我们想预测这样的多类有序变量那么我们可以使用 比例优势逻辑回归 技术。

目标

为了理解有序逻辑回归的工作原理,我们将考虑世界价值观调查的一项研究,该研究着眼于影响人们对政府减贫努力的看法的因素。

我们的目标是根据个人的国家、性别、年龄等因素,预测个人对政府减贫努力的看法。在给定的案例研究中,个人的感知可以取以下三个值- 太少、大约合适、太多。

在我们的分析中,我们将使用来自澳大利亚、挪威、瑞典和美国的世界价值观调查数据。

**library(carData)
library(MASS)****data(WVS) 
head(WVS)**

Fig 2 — Dataset

数据的描述

贫困是多级有序因变量,分类为“太少”、“差不多”和“太多”。我们有以下五个独立变量

  • 宗教:宗教成员——否或是
  • 学位:拥有大学学位——否或是
  • 国家:澳大利亚、挪威、瑞典或美国
  • 年龄:年龄(岁)
  • 性别:男性或女性

现在让我们分析这个数据集的描述性统计数据:

**summary(WVS)**

Fig 3 — Descriptive Statistics

我们还可以分析不同年龄、性别和国家的贫困分布

ggplot(WVS, aes(x = poverty, y = age, fill = poverty)) +   geom_boxplot(size = .75) +   facet_grid(country ~ gender, margins = FALSE) +   theme(axis.text.x = element_text(angle = 45, hjust = 1, vjust = 1))

拟合模型

我们现在将使用质量包中的 polr 函数来拟合比例优势逻辑回归模型。

**model_fit <- polr(poverty~religion+degree+country+age+gender, data = WVS, Hess = TRUE)
summary(model_fit)**

Fig 4 — Model Summary

在上面的输出中,我们得到了关于

  • 模型方程
  • 回归系数及其值、标准误差和 t 值。默认情况下没有显著性检验,但我们可以通过将 t 值与标准正态分布进行比较来计算 p 值。
  • 两次截距的估计值
  • 剩余偏差和 AIC,用于比较不同模型的性能

系数和截距的重要性

**summary_table <- coef(summary(model_fit))
pval <- pnorm(abs(summary_table[, "t value"]),lower.tail = FALSE)* 2
summary_table <- cbind(summary_table, "p value" = round(pval,3))
summary_table**

Fig 5 — Model Significance

由于所有变量的 p 值<0.05, hence they are statistically significant at 95% CI

解释了比例优势模型

为了解释这个模型,我们首先需要理解比例优势模型的工作原理。

设 J 为因变量的总类别数,M 为自变量的个数(在给定的数据集中,J=3,M = 5)。

比例优势模型的数学公式如下所示

Fig 6 — Equation for Proportional Odds Model

这里,J 是具有 J 个级别的有序范畴的级别,I 对应于独立变量

在我们的情况下

  • j = 1 表示“太少”
  • j = 2 表示“大约正确”
  • j = 3 表示“太多”
  • i = 1 指“宗教”
  • i = 2 表示“程度”
  • i = 3 表示“国家”
  • i = 4 表示“年龄”
  • i = 5 表示“性别”

解释图 4T3 中的模型统计

系数:

  • 性别这样的分类变量可以解释为:与女性个体相比,男性个体更有可能对政府的减贫努力产生积极的看法。t 值大于 2,因此在 5%的水平上具有统计学意义。
  • 年龄这样的连续变量可以解释为:年龄每增加一个单位,对政府减贫努力持正面看法的概率对数就增加 0.011

截距:

  • 数学上,截距'过小|左右'对应 logit[P(Y ≤ 1)] 。它可以被解释为相信政府做得“太少”与相信政府做得“差不多”或“太多”的概率对数
  • 同样,截距'左右|太多'对应 logit[P(Y ≤ 2)] 。它可以被解释为相信政府做得“太少”或“差不多”与相信政府做得“太多”的概率对数

对新数据进行预测

假设我们想要预测与具有以下特征的个人的每个感知相对应的概率

  • 宗教:是的
  • 学位:否
  • 国家:挪威
  • 年龄:30 岁
  • 性别:男
  1. 数学计算

通过使用模型摘要中的截距和斜率值,我们可以按以下方式估计期望的概率

对应于太少感知的概率将被计算为:

logit[P(Y≤1)]= 0.7298-[(0.17973 * 1)+(0.14092 * 0)+(-0.32235 * 1)+(0.01114 * 30)+(0.17637 * 1)]

=> logit[P(Y ≤ 1)] =0.36185

= > P(Y≤1)= exp(0.36185)/(1+exp(0.36185))= 0.589

在我们的例子中, P(Y ≤ 1) = P(Y =1) = 0.589

类似地,对应于右感知的的概率将被计算为:

logit[P(Y≤2)]= 2.5325-[(0.17973 * 1)+(0.14092 * 0)+(-0.32235 * 1)+(0.01114 * 30)+(0.17637 * 1)]

=> logit[P(Y ≤ 2)] =2.16455

= > P(Y≤2)= exp(2.16455)/(1+exp(2.16455))= 0.897

因此,P(Y = 2)= P(Y≤2)—P(Y≤1)= 0.897-0.589

=> P(Y = 2) = 0.308

对应于感知过多的概率将被计算为:

因此,P(Y = 3) = 1-P(Y ≤2)

= > P(Y = 3) = 0.103

2。在 R 中计算

幸运的是,我们可以通过使用 R 中的预测函数来绕过上面的数学计算

**new_data <- data.frame("religion"= "yes","degree"="no","country"="Norway","age"=30,"gender"="male")****round(predict(model_fit,new_data,type = "p"), 3)**

Fig 7 —Model Prediction

我们的模型预测,个体测试者认为政府减少贫困的努力太少

如果您希望了解更多关于这一概念的信息,我建议您访问以下链接:

谢谢!

用 Postgres 和 Python 实现自动完成

原文:https://towardsdatascience.com/implementing-auto-complete-with-postgres-and-python-e03d34824079?source=collection_archive---------5-----------------------

(linguistics something linguistics) Photo by Skyler Gerald on Unsplash

介绍

No, she hasn’t learned Python yet. © alphabet inc

如果没有某种自动完成功能,搜索引擎看起来几乎是不完整的。这里有一个从头构建你自己的自动完成的快速指南。我们将使用 Python,Postgres 和 Spacy。弹性搜索是 Postgres 的一个非常好的替代品,但是对于不涉及数百万行的简单任务,Postgres 尽管没有内存能力,但也不算太差。这里的是一篇强调两者区别的有趣文章。

我们将遵循的流程概述:

  • 处理文本数据以提取搜索时弹出的相关短语。
  • 将这些数据存储在搜索优化的实体化视图中。
  • 创建相关索引。
  • 查询该视图并解析自动完成的结果。

提取关键短语

Spacy 提供了一个工业级的文本解析框架。我们将使用它从文本中提取名词块。代码就像这样简单:

Extraction of noun chunks

此外,您可以使用 Python 的Counter来计算这些短语的频率,用于排名和其他目的。下面的代码片段还显示了一个 pg 查询,用于在数据库中插入这些短语,并在发生冲突时采取必要的措施。在我们的例子中,我们通过添加新发现的短语来更新现有短语的频率。

Storing the noun chunks

对于事务性目的,表更适合。我们将把这个表的精选版本放入一个物化视图,用于分析任务,比如搜索。

物化视图

了解 Postgres 提供的不同类型的视图之间的区别是很重要的,我们将会看到两种类型:(普通)视图和物化视图。

物化视图将它包含的数据存储在磁盘上,而普通视图在每次查询视图时运行底层查询。这意味着物化视图必须定期刷新。刷新 es 既可以手动进行,也可以通过主表上的触发器或监听/通知系统之类的机制进行。我们暂时不讨论这个问题。

主表*prompts* 看起来如下:

You can add several conditions on the types of phrases that you want: ngram size, presence of certain POS tags, all phrase as lowercase text, excluding certain stop-words, and so on.

这里的,id 是这个表的主键。在 ngram 字段上有一个唯一的约束,类型为 varchar(256)。我们不希望关键词太长,因此太具体。

我们现在将创建这个表的物化视图,并在这个视图上建立一个索引。对底层提示表的任何更改都可以通过简单地刷新该视图来解决。

Creation, Indexing and Refreshing of a Materialized View

对于生产级应用程序,请查看并发刷新视图。

获取提示

有几种搜索视图的方法,我们将坚持使用下面的方法:

select ngram from <schema_name>.mv_prompts
where tsquery('charges' || ':*') @@ to_tsvector(ngram) 
limit 10

另一个巧妙的技巧是在查询的tsquery(‘charges’ || ‘:*’)部分包含|| ‘:*’。这也可以通过正则表达式搜索得到不完整单词的搜索结果!

搜索结果

这里,' charges' '是一个示例搜索词。我们有一个关于to_tsvector(ngram)的索引,这将优化搜索。

查询执行时间:109 毫秒。

注意:此搜索词仅检索到 9 个结果。

Prompts for search term ‘charg’

下图显示了搜索术语' charg '的前 10 个结果。这完全符合我们的目的,因为除了搜索“费用”得到的提示外,我们还得到类似于“应支付利息”“应支付会计期间”的提示。

查询执行时间:182 毫秒。

没有通配符搜索应该会缩短执行时间,但也会限制结果的数量。这是一个应用程序特有的功能。

用一个 API 把它包装起来

(i had a nice dad joke about hitting a space-bar after long day at work, turns out everyone is paranoid about potential copyright infringement and i could not find the source for the original dad joke. So here, enjoy this mildly futuristic bar 😕). Photo by Skyler Gerald on Unsplash

后端现已准备就绪。现在我们需要反复调用 API 端点来获取用户输入的搜索建议。从前端应用程序中获取方法应该能行。这个调用可以在每次按键、按下空格键、输入延迟达到某个阈值或者这些情况的任意组合时触发。

包扎

带有 Flask API 处理程序和后续数据库查询的 Python 脚本如下所示:

We done yet?

在活动

Straight outta iOS! © ME 😎

进一步的部分包括包括相关的动词短语,解析以保持语义的相似性,以及理解为什么媒体不允许作者定制他们的媒体。

二元逻辑回归

原文:https://towardsdatascience.com/implementing-binary-logistic-regression-in-r-7d802a9d98fe?source=collection_archive---------0-----------------------

R 中的概述和实现

Customer satisfaction for a product — Satisfied vs Dissatisfied (Source: pixabay.com)

你有没有遇到过这样的情况,你想预测一个二元的结果,比如:

  • 一个人对一个产品是否满意?
  • 一个考生是否会被研究生院录取?
  • 两位总统候选人中谁会赢得选举?
  • 飞机是否会在预定时间到达目的地?

一个非常简单的机器学习算法将会拯救你,那就是逻辑回归。

逻辑回归是一种分类算法,当我们想要基于一组独立变量预测分类变量(是/否,通过/失败)时使用。

在逻辑回归模型中,因变量的比值对数被建模为自变量的线性组合。

让我们使用 R. 中的一个实际例子来更清楚地了解二元逻辑回归

考虑这样一种情况,您希望根据血糖浓度、血压、年龄等特征将一个人归类为糖尿病或非糖尿病患者。

数据描述

对于我们的分析,我们将使用来自 R 中的 mlbench 包的皮马印第安人糖尿病数据库

**install.packages('mlbench')
install.packages('MASS')
install.packages('pROC')****library(mlbench)
library(MASS)
library(pROC)****data(PimaIndiansDiabetes2)
head(PimaIndiansDiabetes2)**

糖尿病是该数据集中的二元因变量,分类为 pos/neg。我们有以下八个独立变量

  • 怀孕:怀孕次数
  • 葡萄糖:血浆葡萄糖浓度(葡萄糖耐量试验)
  • 压力:舒张压(毫米汞柱)
  • 三头肌:皮褶厚度(mm)
  • 胰岛素 : 2 小时血清胰岛素(μU/ml)
  • 体重:体重指数(体重公斤/(身高米) )
  • 谱系:糖尿病谱系功能
  • 年龄:年龄(岁)

现在让我们分析该数据集的描述性统计数据:

**summary(PimaIndiansDiabetes2)**

从汇总统计数据中可以明显看出,数据集中存在某些缺失值,它们被突出显示为 NA。

作为一种保守的措施,我们可以删除这样的观察。

**newdata <- na.omit(PimaIndiansDiabetes2)
summary(newdata)**

我们来分析一下各个自变量的分布情况:

**par(mfrow = c(4,2))****for( i in 1:8){
  hist(newdata[,i], main = colnames(newdata)[i],xlab =     colnames(newdata)[i], col = 'yellow')
}**

Histogram of independent variables

从上面的直方图来看,很明显变量——怀孕和年龄是高度倾斜的,我们可以分桶分析它们。

对于年龄,我们可以创建以下四个时段:20–30 岁、31–40 岁、41–50 岁和 50 岁以上

**newdata$age_bucket <- as.factor(ifelse(newdata$age<=30,"20-30",ifelse(newdata$age<=40,"31-40",ifelse(newdata$age<=50,"41-50","50+"))))**

对于怀孕的人,我们可以创建以下三个桶:0-5,6-10 和 10+

**newdata$preg_bucket <- as.factor(ifelse(newdata$pregnant<=5,"0–5",ifelse(newdata$pregnant<=10,"6–10","10+")))**

对于连续的自变量,我们可以通过分析它相对于因变量的分布来得到更清晰的分布。

**par(mfrow = c(3,2))****boxplot(glucose~diabetes, ylab="Glucose", xlab= "Diabetes", col="light blue",data = newdata)****boxplot(pressure~diabetes, ylab="Pressure", xlab= "Diabetes", col="light blue",data = newdata)****boxplot(triceps~diabetes, ylab="triceps", xlab= "Diabetes", col="light blue",data = newdata)****boxplot(insulin~diabetes, ylab="Insulin", xlab= "Diabetes", col="light blue",data = newdata)****boxplot(mass~diabetes, ylab="Mass", xlab= "Diabetes", col="light blue",data = newdata)****boxplot(pedigree~diabetes, ylab="Pedigree", xlab= "Diabetes", col="light blue",data = newdata)**

Box Plot for Continuous Independent Variables

从上面的图中,我们可以推断糖尿病患者的葡萄糖含量中位数更高。对于其余的变量,可以得出类似的推论。

对于分类自变量,我们可以分析每个分类因变量的频率

**xtabs(~diabetes + age_bucket, data = newdata)
xtabs(~diabetes + preg_bucket, data = newdata)**

我们现在将创建一个相关建模变量的新数据框。

**newdata2 <- newdata[,c("diabetes","glucose","pressure","triceps","insulin","mass","pedigree","age_bucket","preg_bucket")]**

实施逻辑回归以预测数据集“新数据 2 ”中的二元结果——糖尿病。

**logit_1 <- glm(diabetes~., family = binomial,data = newdata2)**

模型总结分析

**summary(logit_1)**

汇总统计数据通过提供以下信息帮助我们更好地理解模型:

  1. 偏差残差的分布
  2. 截距和斜率估计值以及标准误差、z 值和 p 值
  3. AIC 值
  4. 剩余偏差和零偏差

结果解读

对于 连续变量 ,解释如下:

葡萄糖每增加一个单位,糖尿病【阳性】(相对于糖尿病【阴性】)的对数几率增加*0.039。
同样,
压力**每增加一个单位,患糖尿病【阳性】(相对于患糖尿病【阴性】)的对数几率减少 0.0045。***

对于 分类变量 ,每个类别的表现都以基本类别为基础进行评估。变量“age_bucket”的基本类别是 20–30,变量“preg_bucket”的基本类别是 0–5。这些变量的解释如下:

处于 31-40 岁的年龄段相对于 20-30 岁年龄段,患糖尿病“阳性”(相对于患糖尿病“阴性”)的对数几率变化 0.854。**

处于 6-10 的怀孕区间相对于 0-5 的怀孕区间,患糖尿病“阳性”(相对于患糖尿病“阴性”)的对数概率变化了-0.24。**

变量选择

对于给定的一组独立变量,模型“logit_1”可能不是最佳模型。

变量选择有多种方法。在本文中,我们将只探索“stepAIC”函数。

R 中的“stepAIC”函数执行逐步模型选择,目标是最小化 AIC 值。

***logit_2 <- stepAIC(logit_1)***

为新创建的具有最小 AIC 的模型分析模型摘要

***summary(logit_2)***

实现“stepAIC”函数后,我们现在剩下四个独立变量—葡萄糖、质量、谱系和 age_bucket。在所有可能的模型中,这个模型(logit_2)具有最小的 AIC 值。

此外,入围变量非常重要。

结果分析

为了分析将“糖尿病”的值作为“pos”的预测概率,我们可以使用如下的汇总函数

***summary(logit_2$fitted.values)***

我们还可以分析“pos”糖尿病的预测概率的分布。

***hist(logit_2$fitted.values,main = " Histogram ",xlab = "Probability of 'pos' diabetes", col = 'light green')***

现在,如果拟合值超过 0.5,我们将预测分类为“正”,否则为“负”。

***newdata2$Predict <- ifelse(logit_2$fitted.values >0.5,"pos","neg")***

模型性能评估

我们现在可以使用以下参数评估模型的性能:

  1. AIC

AIC 代表 Akaike 信息标准。它是类似于调整后的 R,是惩罚模型自变量数量的拟合度。我们总是喜欢最小 AIC 值的模型。

我们可以比较原始模型 logit_1 和由阶梯函数导出的模型 logit_2 的 AIC。

***logit_1$aic
logit_2$aic***

正如所料,由阶梯函数导出的模型对应于较低的 AIC 值。

2。混乱矩阵

它是观察值与预测值的表格表示。它有助于量化模型的效率(或准确性)。

现在让我们比较“糖尿病”的观察值和预测值:

***mytable <- table(newdata2$diabetes,newdata2$Predict)
rownames(mytable) <- c("Obs. neg","Obs. pos")
colnames(mytable) <- c("Pred. neg","Pred. pos")
mytable***

***efficiency <- sum(diag(mytable))/sum(mytable)
efficiency***

从混淆矩阵来看,我们的模型的准确率为 81.4%。

3。ROC 曲线

ROC 代表接收机工作特性。它通过评估敏感性和特异性来解释模型的性能。

***roc(diabetes~logit_2$fitted.values, data = newdata2, plot = TRUE, main = "ROC CURVE", col= "blue")***

ROC 曲线下的面积是准确性的指标。曲线下的面积越大,模型的预测能力越强。

完美预测模型的 AUC 等于 1。

***auc(diabetes~logit_2$fitted.values, data = newdata2)***

模型' logit_2 的曲线下面积为 0.863。

在下一篇文章中,我们将学习另一种广泛使用的逻辑回归技术— 有序逻辑回归

谢谢!

在人工智能部署中实现防御性设计

原文:https://towardsdatascience.com/implementing-defensive-design-in-ai-deployments-fc8fdff11c27?source=collection_archive---------22-----------------------

来自医疗器械设计领域的一系列见解和战斗创伤

Picture from Pixabay on Pexels.com

随着我们的人工智能产品之一即将推出,客户一直在问一个重复的问题。这个问题偶尔也会出现在我们的咨询项目中,只是程度较轻,但仍然需要一个答案。这个问题的简单版本是这样的:

我怎么知道人工智能做得好不好?

现在很容易向客户抛出混淆矩阵和神经活动图,但他们有一个更深层次的问题——和一个非常有效的关注。他们不是在问系统的性能,而是在问系统是否与他们自己的问题一致。如果这个模型现在负责他们的一个或多个业务流程,如果他们看不到它如何执行任务的标准,他们如何管理它?

这涉及到管理基础、商业逻辑和机器学习领域的持续发展的结合。定制人工智能解决方案的目标是加速关键流程,以减轻其余员工的工作量,或实时做出决策。因此,如果一个系统不能在可信任的容差范围内可靠地执行流程,那么这个系统可能根本就无法实现。

以下是我们在过去几个月中遇到的一些真实案例:

  • 如果系统需要审查、组织和突出法律报告中的关键句子,该怎么办?每一个遗漏或贴错标签的关键句子都有相关的成本吗?
  • 如果它在进行医学诊断呢?如果病人被要求接受几个月的痛苦治疗,有人能证明或质疑结果吗?
  • 如果恶意代理成功穿透服务器的防火墙会怎样?对于攻击是如何进行的,而不是简单地对其进行分类,有什么教训可以吸取吗?

询问模型可靠性的主要原因是质量保证。主管可能会接受员工在做出某些决定时缺乏理由,但会想要一份记录或历史证明,证明员工的判断是可靠的、有弹性的和可重复的。(这也是为什么我建议我所有的工程师和数据科学家同事在寻找新工作或项目时建立一个投资组合和一份简历。)

什么是防御性设计?

防御性设计是一种设计方法,它假设一个系统会失败,因此,应该在不损害系统的其余部分、患者或任何其他相关事物的情况下失败。它的目的是在东西“什么时候”会坏,而不是“如果”坏了,来减轻损害。防御性设计的前提是包含多个缓解层,这样部署的系统就不会陷入非常非常小的困境。

新的机器学习专家和数据科学家没有 devops 和安全工程师那样的血统和战斗伤痕,这可能会很快成为一个问题——特别是当越来越多的机器学习解决方案被播种到一个组织的业务逻辑中时。

救援医疗器械设计

让我们来看一个有大量需求工程活动的行业,它可以激发最佳实践:医疗器械设计。至少可以说,可能出错的地方很多,最糟糕的情况也可能是多姿多彩的。事实上,很多事情都可能出错,我们只为一种新的神经病学设备所需的安全系统申请了专利。

就从头设计新医疗器械而言,有一种推荐的方法可以确保一定程度的验证和可追溯性,称为 V 型。这仅仅是画可怕的瀑布模型的一种奇特方式吗?也许吧!但有一些有用的主题和想法,我们可以应用于大多数人工智能部署。

The V-Model of software development. I also call it “The Waterfall Model’s bastard child”. Although it’s not as cyclical and responsive as Continuous Deployment, it does ensure that there is traceability back to the original design. From Wikimedia.

v 型外卖

以下主题可以从 V-Model 中提取出来:

  1. 做事情是有刻意的原因的。无论是客户需求、技术限制,还是性能期望,每一个行动都有一个可以追溯到项目起源的原因。
  2. 每一个设计都有验证和实现。不管是子子模块还是整个系统,都有一种方法可以对照预期性能来验证系统的真实性能。
  3. 验证和确认是有区别的。“我造的东西对吗?”和“我做对了吗?”不是同一个问题和客户打交道时,后者通常是最重要的。

实施防御性设计

有 3 个主要阶段,设计者希望确保他们遵循一个可靠的防御设计框架:在客户讨论/需求阶段,在编码期间,以及在部署期间和之后。

需求阶段的防御性设计

需求,需求,以及更多的需求——这就是我们如何在设计阶段确保良好、干净的乐趣。“但是编程很好玩!”是的,凯伦,是的,但是浪费时间和金钱不是。

向客户展示一个工具,而不是一个有知觉的存在。提醒客户,机器学习很枯燥,旨在非常好地完成一个明确定义的流程的一个或多个步骤。

验证数据。客户是否拥有他们认为自己拥有的数据?原始数据本身干净吗?API 会偶尔改变格式吗?

然后再验证一遍。您能够重复访问工作数据集吗?它是否与您执行的第一次审计相符?

从小处着手,积累动力。限定最初承诺的范围。如果你能先解决一个简单的问题,你现在就能处理越来越多的业务流程。这也迫使客户端确保它们呈现给系统的数据是干净的。

(我们已经在各种项目中看到了很多成功,在项目开始时给整个项目泼了一盆冷水,这让每个人都清醒过来,并让一个清晰的业务案例浮出水面。在功能方面,除了厨房水槽,你的客户现场支持者很容易承诺所有东西。)

Agnes Skinner making her requirements known. From Tenor.

如果你想阅读更多关于需求工程的内容,我推荐的同名书籍,作者是伊丽莎白·赫尔和杰里米·迪克。

创世纪阶段的防御设计

现在,您开始在正确的用户界面或交互级别上编码并与客户一起工作,确保有明确定义的需求,可以测量、评估、测试和解释。

以用户为中心的设计。我们总是说让用户问正确的问题,而不是给用户一个准备好的答案。设计用户界面,让用户始终负责关键决策,系统应该作为助手部署——人在回路中有最后的发言权。

A screenshot of our AuditMap.ai tool. The Value

输入端的预处理/数据验证。这方面的一个例子是一个简单的分类器:在对所有语句进行排序之前,您可以预先放置一个“英语/非英语”过滤器,以确保您获得干净的数据,或者放置一个“看起来好/看起来不好”的过滤器,以确保过滤机制保护系统的其余部分。

多型号设计。它可以是一个紧密的整体,也可以只是不同的 API 调用,但是允许对每个模型的性能进行审查,就可以一直追溯到业务逻辑。

部署阶段的防御设计

恭喜你。你的人工智能部署好了,你的客户/老板高兴了,你去读了一会儿黑客新闻,现在你已经精力充沛地开始下一个项目了。然而,根据我们的经验,这是您需要投入最多精力的地方,至少在现场部署的前 6 个月

跟踪修正。系统部署后会犯哪些错误?如果你没有考虑纠正措施跟踪机制,那么你就不知道对数据集的长期修复是什么。(好处:这允许你的数据集有一个很好的增长,帮助它随着时间的推移而增长。丹的一篇文章中有一个更长的解释)

正在进行的客户对话。现在有了在设计工具时无法预见的用例。为确保您的客户拥有最佳体验,在移交后继续对话,以确保工具仍能按预期运行。(他们是不是因为一个诡异的内存泄露,在 50 次请求后就要重置服务器?如果是这样的话,不管你的准确率有多高,他们可能都不会给你打电话进行后续的约定。)

用户缓解。您的系统对错误的用户输入、文件类型和损坏的文件有弹性吗?多个用户一次上传多个文件怎么办?

中间文档。确保模块开发人员和集成商都理解设计决策背后的基本原理。你可以写自己的文档,或者让像 Swagger 这样的工具从(正确的)注释代码中管理文档。

负载均衡。您的系统对负载波动有弹性吗?在你的客户发布后(会议谈话和电视采访对此尤其不利。)我们喜欢很多数字海洋选项

永远不要忘记,用户会发明从未有人梦想过的用例。

We’re always impressed by unforeseen client use cases. From Imgur.

你的系统中最薄弱的部分很可能是人类。它们也是成功部署的最重要部分。

什么是防御设计,什么不是

防御型设计很无聊。这是系统化的,而且通常情况下,人们会问为什么有些结构和可交付物的构建超出了他们的基本需求。在几次险些出事之后,你的团队应该开始意识到做最坏打算的重要性。

然而,防御性设计不是一种保证或保险政策。仅仅因为你遵循了每一个可能的步骤,并不意味着你的系统是面向未来的,可以经受住技术飓风。

只要准备好“当”你的系统崩溃时,不要只考虑理论上的“如果”。通过这种方式,你可以确保人工智能做得很好,当它做不好时,将损害降到最低。

如果您在开始新的客户项目时,对本文或我们的设计方法有其他问题,请随时通过 LinkedIn 联系我们。

你可能喜欢的其他文章

我的首席技术官丹尼尔·夏皮罗(Daniel Shapiro)的其他文章您可能会喜欢:

高效实施脸书先知

原文:https://towardsdatascience.com/implementing-facebook-prophet-efficiently-c241305405a3?source=collection_archive---------1-----------------------

如果你曾经做过时间序列预测,我敢肯定你很清楚随之而来的压力和痛苦。一会儿你认为你已经破解了股市,一会儿你躺在浴缸里哭着诅咒你不准确的模型(我真的不建议你尝试和预测股市,你很可能不会收获你认为你会获得的收益)。我想说的是,时间序列预测是困难的,总是需要非常专业的数据科学家来实现。

Facebook Prophet’s logo

然而,我们的蓝色霸主,即脸书发布了一个惊人的模型称为脸书先知。Prophet 使几乎任何人都有可能预测时间序列值,即使你在这个领域没有什么经验。在大多数情况下,它开箱即可正常工作,您的数据分析师将能够通过输出讲述相当准确的故事。但是,当您想要开始在生产中使用该模型时,您必须开始更深入地理解正在发生的事情,并且知道哪些参数需要调整以及为什么。

为了向您展示如何调整参数以及为什么应该调整参数,我们将使用一个简单的 y 和 ds 数据框架(Prophet 使用的格式)进行实验。数据超过 2 年,每小时一次,这已经需要一些额外的调整。

Our time series we want to predict

Zooming in on our time series

在我们开始之前,假设你对脸书先知有一个相对较好的了解。如果你不知道,我强烈建议你点击下面的链接进入先知快速入门。如果你不这样做,一些代码将没有意义,因为我不会解释如何导入或适合先知的数据,只对如何优化它。

先知快速入门

在我们开始有趣的部分之前,博客的目标是我只想展示哪些超参数值得关注,并给出一些我学到的技巧。无论我说什么都不是法律,我邀请你分享对我工作的意见和建议。

我们如何衡量模型的性能?

许多隐藏的秘密中有一个在第一次使用 Prophet 时并不那么明显,那就是它内置了交叉验证功能。此函数将获取您的数据,并在您指定的时间段内训练模型。然后,它将预测您指定的时间段。Prophet 将在更长的时间内训练你的数据,然后再次预测,这将重复进行,直到到达终点。

作为一个例子,让我们以上面显示的数据为例,用现成的 Prophet 模型来拟合它。在示例中,我编写了自己的平均绝对百分比误差(MAPE)函数,并将其应用于测试结果,以获得用一个数字表示的模型性能。

从上面的代码中可以看出,我们从 Prophet 导入了交叉验证函数,并将其应用于我们的数据。这将返回所有预测点的预测值和真实值的数据帧,然后可以用它来计算误差。

所以在运行上面的代码后,我们得到了 15.32%的 MAPE。这表明在所有预测的点上,我们与真实值平均相差 15.32%。

在博客的其余部分,我将讨论每个超参数,以及在决定它们的值时应该注意什么。

优化模型

不要盲目地做任何事情

优化模型的第一个技巧是不要疯狂地改变值,创建巨大的 for 循环,或者将模型放入 gridsearch 来优化 hyper 参数。当观察时间序列模型时尤其如此,因为超参数对预测有很大影响,但是这些参数的值不必是完美的。相反,让他们进入正确的区域会带来最大的回报。您可以通过查看数据并了解当您更改每个参数时模型将如何处理这些数据来实现这一点。

增长

这个参数是最容易理解和实现的,因为你只需要绘制你的数据就知道它应该是什么。如果您绘制您的数据,并且您看到一个趋势继续增长,而(或者如果您的领域专家告诉您不需要担心饱和)没有真正的饱和洞察力,您将把这个参数设置为“ 线性 ”。

如果您绘制它并看到一条显示饱和前景的曲线(或者如果您正在处理您知道必须饱和的值,例如 CPU 使用率),那么您将把它设置为“”。**

当您选择逻辑增长时,此参数的难点就来了,因为您必须提供预测的上限(数据将达到的最大值)和下限(数据将达到的最小值)以及历史数据。这些上限和下限值可以随着时间的推移而改变,也可以是您永久输入的设定值。

在这种情况下,与领域专家交流对您帮助最大。他们对下一年的预期和一段时间内的不可能值有很好的了解。与他们交谈后,你可以提供更准确的上限和下限。然而,如果你附近没有领域专家,我发现你的第一个值的 65%对于底价很有效。然后你可以设定一个相对较高的限额,但要在常识范围内。因此,如果你预测一个网站的访问量,而目前它的访问量是 100,00 0,那么不要把你的访问量限制在 200,00 0,00 0,因为你很可能在你预测的时间内达不到这个上限。更好的办法是让它变得更合理,比如 50 万英镑,让上限随着时间慢慢增长。

假日

假期是一段时间,在这段时间里,每一天都有同样的效果。例如,如果您想要对一个人们在节日期间迁移的城市中的订户数量进行建模,您可以使用 holidays 参数在您的模型中输入节日期间的日期。

当你对非日常数据建模时,棘手的部分就来了。我犯的一个错误是,当我试图对每小时的数据建模时,把我的假期作为每天的数据。这导致我的模型性能更差,因为它很难将假期数据调整为正确的形式。确保假期数据与目标数据具有相同的形式是很重要的。您还应该能够提供您预测的假期日期。这意味着假期只能是你事先知道的时间/日期/日子。

另一个处理节假日的参数是holidays _ prior _ scale。此参数决定了假期对预测的影响程度。例如,当你在处理人口预测时,你知道假期会有很大的影响,尝试大的值。通常值在 20 到 40 之间就可以了,否则默认值 10 通常就很好了。作为最后手段,你可以降低它来看看效果,但我从来没有发现,以增加我的 MAPE。

变革点

变点是数据中趋势发生突然变化的点。一个例子是,如果你有一个活动,突然你的网站有了 50 000 多个固定访问者。变化点将是发生这种巨大变化的时间段。

变点有四个超参数:变点n _ 变点变点 _ 范围变点 _ 先验 _ 标度

当您提供变点日期而不是让 Prophet 确定日期时,将使用 变点 参数。一旦您提供了自己的变点,Prophet 将不会估计更多的变点。因此,重要的是你知道你在做什么。从我的经验来看,我发现让 Prophet 自己发现它们和我改变改变点的数量(用 n_changepoints )会得到最好的结果。就应该选择多少个变点而言,我建议如果你有每小时的数据,那么一个月至少一个变点会产生好的结果。然而,它会根据每个用例而变化,但这可能是一个好的开始。

change point _ range通常对性能没有太大影响。我通过保持默认值得到了最好的结果,但是如果有人发现从 0,8 改变它时有不同的情况,我会很乐意在评论中听到。另一个参数,change point _ prior _ scale,** 用于指示允许的可变点的灵活程度。换句话说,变点能在多大程度上符合数据。如果你把它做得很高,它会更灵活,但是你可能会适得其反。我发现 10 到 30 之间的值对我有用,这取决于数据的波动性。**

季节性

这些参数是 Prophet 的亮点,因为您只需更改几个值就可以做出重大改进并获得深刻见解。

第一个大参数是 季节性 _ 模式 。此参数指示季节性因素应如何与预测相结合。这里的默认值是 加法 ,另一个选项是 乘法 。起初我对这个参数很纠结,但是在使用了一段时间后,它开始对我有意义了。当你的季节性趋势在整个期间应该是“恒定”的时候,你将使用添加剂。例如,当您希望您的年度趋势增长影响与 2010 年和 2018 年相同时。这适用于趋势变化似乎保持不变的数据,例如居住在小城镇的人数。这是因为我们不期望增长突然以百万计,因为没有基础设施。

另一方面,当我们想要预测居住在一个发展中城市的人口数量时,年度趋势数字在最后几年可能更重要,因为基础设施已经存在。那时人口增长率可能会比早些年快得多。在这种情况下,您将使用来增加季节性随时间变化的重要性。

和各地的情况一样,还有一个 季节性 _ 先验 _ 规模 参数。这个参数将再次允许你的季节性更加灵活。我发现 10 到 25 之间的值在这里工作得很好,这取决于你在组件图中注意到的季节性程度。

我发现最适合我的一个技巧(我愿意讨论这个问题)是将yearly _ 季节性weekly _ 季节性*、daily _ 季节性*、都设置为 false ,然后添加我自己的季节性,如下面的代码片段所示。

Adding your own seasonalities

通过这样做,你可以获得更多的权力和对季节性的控制。您可以指定每个季节的确切时间,这意味着您可以创建“新的”季节。例如,通过将周期设为 93.3125,您可以将季度季节性添加到模型中。您还可以为每个季节性添加先前的比例,而不是共享一个比例。现在,我希望我能告诉你应该添加什么季节,应该是什么时间段,但是每个用例完全不同,应该联系领域专家以获得建议和见解。

为了清楚起见,如果周期被设置为 35,那么你告诉模型在某一点发生的事情很可能在 35 天内再次发生。

使用这种技术可以调整的另一个参数是组成每个季节性的傅立叶分量的数量(Fourier _ order)。对于那些懂一点数学的人来说,任何信号都可以用正弦波和余弦波之和来表示。这是 Prophet 生成季节性信号的固有方式。这样,您可以更改开始表示曲线的精确度,或者曲线中可以出现多少条曲线。下面显示的是一些数据的每日季节性,分别使用傅立叶级数 5 和 20。

Fourier_order = 5

Fourier_order = 20

正如你所看到的,曲线轮廓在两个趋势中保持不变,但是在有 20 个分量的趋势中有更多的起伏。这些颠簸可能是拾取噪声,也可能是更精确的值。这应该归结为你自己的解释和领域专家的意见。我发现较高的值确实会给出更好的结果,我强烈建议调查使用较高值的效果。您可以尝试范围从 10 到 25 的值。

MCMC 样本

这是一个棘手的问题。此参数确定模型是使用最大后验概率(MAP)估计,还是使用指定数量的马尔可夫链蒙特卡罗 (MCMC)样本进行训练和预测的完全贝叶斯推断。

因此,如果您使 MCMC 为零,它将进行 MAP 估计,否则您需要指定 MCMC 使用的样本数。我将诚实地说,我从来没有发现贝叶斯推理更好地工作,我总是使用地图估计。贝叶斯推理也需要非常长的时间来运行,因为你需要使用至少 1000 个样本来获得令人满意的结果。这是我总是留给基线值的一个参数。

作为保持 mcmc_samples 0 的结果,我还没有机会探究interval _ width,因为它是在使用 MAP 估计时自动生成的。

不确定样本

这是另一个对结果没有太大影响的参数,应该针对每个用例进行探究。

从一开始就改进我们的原始模型

那么,如果我们更多地考虑我们的参数并专注于上述参数,MAPE 会增加多少呢?下面显示的是最终模型。

Final Prophet model

如果我们看看我的最终模型,我们看到我选择了线性。这是因为我和与我一起工作的领域专家谈过,她提到我们在这里预测的没有限制。你也可以看到它增长很快,但也不是指数增长。出于这个原因,我不必担心我的预测会拾取一些导致值呈指数增长的东西。

我的季节性变成了倍增性,因为我发现模型很难预测时间序列后半部分的更高值。这表明这一趋势在后期可能更为重要。

您还可以看到,我添加了月度和季度趋势,因为我在对我的数据进行 ed a 时注意到了这些趋势(在构建模型之前始终进行 EDA 非常重要)。

通过所有这些改变,我设法把我的 MAPE 降到了 6.35%,基准模型的 MAPE 为 15.32%。

Predicted (blue) vs real values (black dots)

这只是表明 Prophet 开箱即用的效果令人惊讶,如果您对您的模型稍加注意,您可以大幅提高性能!

感谢您的阅读,我期待着关于您如何实施和优化 Prophet 的讨论。

在数据科学中实现 Git

原文:https://towardsdatascience.com/implementing-git-in-data-science-11528f0fb4a7?source=collection_archive---------7-----------------------

本文原载于【blog.zakjost.com】

介绍

我希望第 1 部分让您明白了版本控制是管理数据科学实验的重要工具。但是魔鬼在细节中,所以我们来谈谈如何在一个数据科学项目中实现版本控制。

有几种使用 git 的范例,但是为了数据科学实验的目的,我基本上采用了“特性分支”。简而言之,特性分支意味着有一个“主”分支,您可以将其用作基线,通过从“主”分支,进行实现该特性所需的所有更改,然后在成功后将新分支合并回主分支,可以将新特性添加到代码库中。

实施策略

在我的例子中,我为一个新的实验或者一个我想尝试的新的建模想法创建一个新的分支。在这一点上,你需要有意识地做出决定:你是修改代码,使它只在这个实验中有效,还是希望以一种既能在这个实验中又能在之前的实验中有效的方式来修改它?这个问题的另一种表述方式是:你是想替换你已经做的,还是想增加?答案将决定你能否将新分支合并回 master,或者它是否会永远保持自己的东西。

我的建议是额外努力将关键组件提取到一个库中,然后在多个实验中重复使用。这比拥有相同(或者更糟,稍微不同)代码的多个副本要好得多,这些副本需要单独维护。这种代码差异很可能是错误的来源。俗话说:最好的代码就是没有代码。通过将关键组件提取到共享库中,您可以进行增量改进,并最终得到一个内聚的代码库,该代码库可以重复运行一系列实验。如果您继续引入向后不兼容的变更,您会发现自己经常在分支之间跳跃,复制/粘贴有用的代码部分,但是随后需要进行修改,因为组件不是为协同工作而设计的。对于大型实验,这可能会变得难以处理。

特性分支方法的优点是,您可以将您的实验分支合并回 master,然后运行任何实验。这样做的代价是,当您对核心库进行更改时,您可能还需要更改其他实验的实现。所以,像所有事情一样,这是一个权衡的决定。以我的经验来看,它是有机发展的,每当我想复制和粘贴时,我就会想到提取公共代码。

示例实现

我发现一个有用的目录结构示例如下:

*|-- core/
    |-- tests/
        |-- test_pull_data.py
        |-- test_prepare_data.py
        |-- test_model.py
        |-- test_deploy.py
        |-- test_utils.py
    |-- pull_data.py
    |-- prepare_data.py
    |-- model.py
    |-- deploy.py
    |-- utils.py
|-- experiment_1/
    |-- data/
        |-- training.csv
        |-- validation.csv
        |-- test.csv
    |-- output/
        |-- results.json
        |-- models/
            |-- model1
            |-- model2
    |-- job_config.py
    |-- build_data.py
    |-- train.py
    |-- evaluate.py
    |-- prod.py
|-- experiment_2/
    |-- data/
        |-- training.csv
        |-- validation.csv
        |-- test.csv
    |-- output/
        |-- results.json
        |-- models/
            |-- model1
            |-- model2
    |-- job_config.py
    |-- build_data.py
    |-- train.py
    |-- evaluate.py
    |-- prod.py*

在这种情况下,主逻辑在core/目录中。然后,实验被组织在目录中,目录包含执行实验的核心逻辑的代码和运行它所产生的输入/输出资产。实现代码应该非常简单,并且只做特定于这个特定实验的事情。例如,如果它比较方法 A 和 B,那么它将导入 A 和 B 的配置,从核心实例化相关代码,并为每个调用“run”。

请注意,这种结构为实现单元/功能/集成测试提供了一个自然的位置。此外,将通用组件提取到一个多用户库中的行为有助于提高代码的可测试性。因为这段代码可能是参数化的,而不是依赖于硬编码的实验细节,所以为测试创建玩具示例变得更加容易。未来的一篇文章将更深入地探讨为数据科学项目编写测试。

技巧

这里有一些我发现很有帮助的简单做法。

1..gitignore

这告诉 git 要忽略哪些文件。在一个新项目中,这应该是首要任务,因为一旦你犯了愚蠢的错误,除非你采取特别的行动,否则它将永远存在。

最重要的是排除敏感信息,如密码和 API 密钥。如果您很早就提交了包含敏感信息的文件,这很快就会变成一场噩梦。从当前快照中删除它是不够的——您需要从所有以前的提交中删除它。帮你自己一个忙,不要去学怎么做。

下一步是忽略非常大的数据文件和不需要跟踪的不重要的文件(即 ipython 笔记本检查点、来自 IDE 的设置文件、pycache,)。pyc 等)。在上面的例子中,所有的输入/输出工件也应该被忽略,因为它们完全由代码本身决定,并且如果需要的话可以重新生成。

2.频繁提交

如果你完成了一大块合理的工作,提交一份。没有必要吝啬,这可能会让你摆脱困境。

3.清除提交消息

如果你提交得足够频繁,那么你的大块工作可能会非常集中。这应该能够清除提交消息。没有什么比试图追溯一个不期望的变更并因为一个适当注释的提交历史而快速找到它更令人满意的了。如果对你所做的事情的描述是这样的:“实现了 3 个新特性,添加了 dropout,构建了一个交叉验证组件,重构了训练逻辑”,那么你没有足够频繁地提交。

你呢?

当我尝试不同的策略时,这些想法正在进行中。如果你已经开发了一种你认为有用的不同方法,我很乐意听听它!

**您可以在【blog.zakjost.com】找到我所有的内容并订阅

在 scikit-learn 中实现 K 近邻

原文:https://towardsdatascience.com/implementing-k-nearest-neighbors-with-scikit-learn-9e4858e231ea?source=collection_archive---------3-----------------------

scikit-learn 的 KNeighbors 分类器演练

我们将使用 iris 数据集,这里的来自 UCI 机器学习。这是一个很小的数据集,具有容易区分的聚类,对于像这样的演示非常有用。它包含了对鸢尾属植物三个物种的 150 次观察:刚毛鸢尾、杂色鸢尾和海滨鸢尾。任务是根据最近的邻居来识别每种植物的种类。

k-最近邻法是一种简单地查看与它试图预测的观测值最接近的观测值,并根据周围大多数的观测值对感兴趣点进行分类的方法。

我使用以下代码将数据加载到 pandas 数据帧中:

## load the iris data into a DataFrame
import pandas as pd
url = '[http://archive.ics.uci.edu/ml/machine-learning-databases/iris/iris.data'](http://archive.ics.uci.edu/ml/machine-learning-databases/iris/iris.data') 
## Specifying column names.
col_names = ['sepal_length', 'sepal_width', 'petal_length', 'petal_width', 'species']
iris = pd.read_csv(url, header=None, names=col_names)

下面是一些数据:

下面,我画出了花瓣的长度和宽度被类分开,这样你就可以看到类是如何分开的。

Nice colors!

现在,为了对数据建模,我运行了几个预处理步骤。首先,我将物种名称映射到一个数字上,这样我就可以用我的分类器对它进行分类。其代码如下:

## map each iris species to a number with a dictionary and list comprehension.
iris_class = {'Iris-setosa':0, 'Iris-versicolor':1, 'Iris-virginica':2}
iris['species_num'] = [iris_class[i] for i in iris.species]

将数据分成我们的建模和目标变量,我们的 X 和 y:

## Create an 'X' matrix by dropping the irrelevant columns.
X = iris.drop(['species', 'species_num'], axis=1)
y = iris.species_num

列车测试分离:

from sklearn.model_selection import train_test_split
## Split data into training and testing sets.
X_train, X_test, y_train, y_test = train_test_split(X, y, random_state=42)

我们已经准备好模型了。在下面的代码中,我们将导入分类器,实例化模型,使其适合训练数据,并根据测试数据对其进行评分。请注意,您可以更改用于对每个点进行分类的最近邻的数量。

## Import the Classifier.
from sklearn.neighbors import KNeighborsClassifier
## Instantiate the model with 5 neighbors. 
knn = KNeighborsClassifier(n_neighbors=5)
## Fit the model on the training data.
knn.fit(X_train, y_train)
## See how the model performs on the test data.
knn.score(X_test, y_test)

该模型实际上具有 100%的准确率,因为这是一个非常简单的数据集,具有明显可分离的类。但是现在你有了。这就是如何用 scikit-learn 实现 K 近邻。加载你最喜欢的数据集,试试吧!

使用交互代码实现 NVIDIA 用于自动驾驶汽车的神经网络[手动倒车 TF]

原文:https://towardsdatascience.com/implementing-neural-network-used-for-self-driving-cars-from-nvidia-with-interactive-code-manual-aa6780bc70f4?source=collection_archive---------5-----------------------

Gif from here

所以最近碰到这个 Quora 的问题,“用于自动驾驶汽车的神经网络有几层?”,很快我就发现,(通过 Prasoon Goyal 的回答)NVIDA 从 2016 年开始用的车型并没有那么复杂。

不相信我?请参见下面的网络架构。此外,这里是原始论文的链接,“自动驾驶汽车的端到端学习”。

最后,请注意两件事。
1。这种模型在 2016 年使用,当前的模型将更加复杂。
2。让我们在这个模型上使用扩张反向传播,看看我们能达到什么样的结果。

网络架构(图形形式)

就是这个,LOL 我也不敢相信。这是如此简单,但它似乎在学习如何真正驾驶汽车方面做了一项惊人的工作。让我们看看 NVIDIA 自己的模型视频。

实验设置/奇怪的观察结果

Image from this webpage

由于我没有可以训练 LOL 的汽车,所以我将使用著名的 CIFAR 10 数据集进行分类。

最奇怪的观察是在层中没有激活功能的事实!我甚至找不到任何提到 Relu()或 sigmoid()激活函数的痕迹。甚至在这个开发者博客里。但是,我决定包含卷积层的 Relu()激活和全连接层的 logistic_sigmoid()激活。这个决定是在进行了多次实验后做出的。

网络架构(OOP 形式)

红框 →网络架构
黄框 →原纸区别

我唯一需要改变的是第二层和第三层卷积运算的步距。由于输入图像大小,我不能对所有三个卷积层执行步长为 2 的卷积。

修改后的网络架构(OOP 形式)

红框 →神经元和通道数量大小增加
黄框 →卷积运算差异。

我现在可以告诉你,CIFAR 10 数据集上的性能在原始模型上很差。因此,我增加了卷积层的通道数和全连接层的神经元数,看看我能得到多少改善。也因为我想使用扩张反向传播

训练结果(原始模型)

左图 →随时间变化的列车图像精度
右图 →随时间变化的列车图像成本

左图 →随时间测试图像精度
右图 →随时间测试图像成本

如上所述,训练图像和测试图像的准确率都只有 19%左右。这是可怕的结果。

透明度

为了增加这个实验的透明度,我已经将培训过程中 cmd 上的所有输出上传到我的 git hub,请点击这里访问它们。

训练结果(修改模型)

左图 →随时间变化的列车图像精度
右图 →随时间变化的列车图像成本

左图 →随时间测试图像精度
右图 →随时间测试图像成本

如上所述,即使使用修改的体系结构,训练图像和测试图像的准确度也分别约为 60/30%。这一点都不好……

透明度

为了增加这个实验的透明度,我已经将培训过程中 cmd 上的所有输出上传到我的 git hub,请点击这里访问它们。

交互代码(谷歌 Colab、微软 Azure、Repl it)

对于谷歌 Colab,你需要一个谷歌帐户来查看代码,而且你不能在谷歌 Colab 中运行只读脚本,所以在你的操场上做一个副本。最后,我永远不会请求允许访问你在 Google Drive 上的文件,仅供参考。编码快乐!

要访问原始模型的代码,请点击您希望查看代码的平台, Google ColabMicrosoft AzureReplt

要访问原始模型的代码,请单击您希望查看代码的平台, Google ColabMicrosoft AzureReplt

注意需要 wget 权限的平台不会在您的浏览器上运行。你可以在 Google Colab 上运行它。

遗言

从这个实验中,我了解到一些模型可能在某项任务上做得非常好,而在其他几项任务上表现不佳。此外,我还了解到扩张反向传播也是一个正则化因素。

如果发现任何错误,请发电子邮件到 jae.duk.seo@gmail.com 给我,如果你想看我所有写作的列表,请在这里查看我的网站。

同时,在我的推特这里关注我,访问我的网站,或者我的 Youtube 频道了解更多内容。如果你感兴趣的话,我还做了解耦神经网络的比较。

参考

  1. [1]2018.【在线】。可用:https://www . quora . com/How-many-layers-do-neural-networks-used-for-driving-cars-have。【访问日期:2018 年 3 月 19 日】。
  2. Bojarski,m .、Del Testa,d .、Dworakowski,d .、Firner,b .、Flepp,b .、Goyal,p .、…、张,X. (2016)。自动驾驶汽车的端到端学习。 arXiv 预印本 arXiv:1604.07316
  3. 超越 Tensorflow 的默认自动微分优化器,具有交互式代码[手动…(2018).走向数据科学。检索于 2018 年 3 月 19 日,来自https://towards data science . com/outpering-tensor flows-default-auto-difference-optimizer-with-interactive-code-manual-e 587 a82d 340 ea
  4. Python?,H. (2018)。如何在 Python 中以列表形式返回字典键?。Stackoverflow.com。检索于 2018 年 3 月 19 日,来自https://stack overflow . com/questions/16819222/how-to-return-dictionary-keys-as-a-list-in-python
  5. Python,A. (2018)。在 Python 中访问字典中的任意元素。Stackoverflow.com。检索于 2018 年 3 月 19 日,来自https://stack overflow . com/questions/3097866/access-an-arbitrary-element-in-a-dictionary-in-python
  6. Python 中的 DICOM:用 PyDICOM 和 VTK 将医学图像数据导入 NumPy。(2014).PyScience。检索于 2018 年 3 月 19 日,来自https://py science . WordPress . com/2014/09/08/DICOM-in-python-importing-medical-image-data-into-numpy-with-pydicom-and-VTK/
  7. 博雅尔斯基,m .,菲尔纳,b .,弗莱普,b .,杰克尔,l .,穆勒,美国和齐巴,K. (2016)。自动驾驶汽车的端到端深度学习。NVIDIA 开发者博客。检索于 2018 年 3 月 19 日,来自https://dev blogs . NVIDIA . com/deep-learning-self-driving-cars/
  8. CIFAR-10 和 CIFAR-100 数据集。(2018).Cs.toronto.edu。检索于 2018 年 3 月 19 日,来自https://www.cs.toronto.edu/~kriz/cifar.html
  9. j . brown lee(2017 年)。如何在 Python 中对序列数据进行热编码-机器学习掌握?机器学习精通。检索于 2018 年 3 月 19 日,来自https://machine learning mastery . com/how-to-one-hot-encode-sequence-data-in-python/
  10. SciPy . sparse . CSR _ matrix—SciPy v 1 . 0 . 0 参考指南。(2018).Docs.scipy.org。检索于 2018 年 3 月 19 日,来自https://docs . scipy . org/doc/scipy/reference/generated/scipy . sparse . CSR _ matrix . html
  11. 超越 Tensorflow 的默认自动微分优化器,具有交互式代码[手动…(2018).走向数据科学。检索于 2018 年 3 月 20 日,来自https://towards data science . com/outpering-tensor flows-default-auto-difference-optimizer-with-interactive-code-manual-e587 a82d 340 e
  12. Google Colab 免费 GPU 教程—深度学习火鸡—中等。(2018).中等。检索于 2018 年 3 月 20 日,来自https://medium . com/deep-learning-turkey/Google-colab-free-GPU-tutorial-e 113627 b9f5d
  13. 文件?,W. (2018)。解压一个. tar.gz 文件需要什么命令?。Askubuntu.com。检索于 2018 年 3 月 20 日,来自https://askubuntu . com/questions/25347/what-command-do-I-need-to-unzip-extract-a-tar-gz-file
  14. 线?,H. (2018)。如何通过命令行重命名目录?。Askubuntu.com。检索于 2018 年 3 月 20 日,来自https://askubuntu . com/questions/56326/how-do-I-rename-a-directory-via-the-command-line

用 CNN 和 self attentions 实现问答网

原文:https://towardsdatascience.com/implementing-question-answering-networks-with-cnns-5ae5f08e312b?source=collection_archive---------2-----------------------

在本帖中,我们将解决自然语言处理中最具挑战性也最有趣的问题之一,也就是问答。我们将在 Tensorflow 中实现 Google 的 QANet 。就像它的机器翻译对手 Transformer network 一样,QANet 根本不使用 RNNs,这使得训练/测试更快。(这个实验的源代码可以在这里找到)

我假设您已经对 python 和 Tensorflow 有了一些了解。

问答是计算机科学中的一个领域,在过去的几年中取得了一些快速的进展。回答问题的一个经典例子是 IBM 的沃森参加著名的智力竞赛节目 Jeopardy!2011 年,击败传奇冠军布拉德·鲁特和肯·詹宁斯,获得冠军。

在本帖中,我们将关注开放式阅读理解,问题可以来自任何领域,从美国流行明星到抽象概念。阅读理解是一种回答问题的方式,给我们一段文字,然后从这段文字中选择一些问题来回答。

IBM Watson competing against Ken Jennings (left) and Brad Rutter (right) at Jeopardy! in 2011. Source: https://blog.ted.com/how-did-supercomputer-watson-beat-jeopardy-champion-ken-jennings-experts-discuss/

数据集(小队)

我们将在这篇文章中使用的数据集叫做斯坦福问答数据集(SQuAD) 。SQuAD 有一些问题,我们将回头讨论,它可能不是机器阅读理解的最佳数据集,但却是研究最广泛的数据集。如果你对用于阅读理解的不同数据集感到好奇,也可以看看这个令人敬畏的 NLP 数据集列表。

《小队》的一个与众不同的因素是,问题的答案就在段落本身。这里是一个班格式的例子。

An example of Stanford Question Answering Dataset. Source: https://rajpurkar.github.io/SQuAD-explorer/

从上面的例子我们可以看出,不管问题有多简单或多难,问题的答案总是在段落本身。

但是首先,让我们看看我们期望解决的问题和答案的种类。通常情况下,问题本身已经是段落片段的转述版本。举个例子,

p:“计算复杂性理论是理论计算机科学中计算理论的一个分支,它专注于根据计算问题的内在难度对其进行分类,并将这些类别相互联系起来。一个计算问题被理解为一个原则上服从于由计算机解决的任务,这相当于声明该问题可以通过数学步骤的机械应用来解决,例如算法

问:“通常由计算机来解决的任务的术语是什么?

答:“计算问题”

从黑体字中可以看出,这个问题是从这一段中引申出来的。这一特性使得团队问题本质上比开放域问答问题更容易。因为我们现在要做的就是从段落中找出一个与问题语义匹配的句子,从上下文中提取出共同的语义或句法因素。虽然我们还是要求解决语义和句法抽取,但这比从可能有上万个单词的字典中推导出答案要容易得多。

队伍的劣势

上面提到的属性让我们使用一些技巧来轻松预测给定段落的答案。但是,这也给用 SQuAD 训练的模型引入了一些问题。因为模型严重依赖于从段落中找到正确的句子,所以它们容易受到插入到段落中的敌对句子的影响,这些句子类似于问题,但旨在欺骗网络。这里有一个例子,

Adversarial example of SQuAD. Source: https://arxiv.org/pdf/1707.07328.pdf

用蓝色突出显示的句子是为了愚弄网络而插入的对抗性示例。对于人类读者来说,这不会改变“在第三十三届超级碗中 38 岁的四分卫叫什么名字?”因为反诘句说的是冠军碗三十四。然而,对网络来说,对抗性句子比基本事实句子更符合问题。

模型网络(QANet)

我们选择 QANet 模型的原因很简单。由于其简单的体系结构,它易于实现,并且比完成相同任务的大多数网络训练更快。QANet 架构从下图可以看出:

The network architecture overview. Source: https://openreview.net/pdf?id=B14TlG-RW

模型网络可以大致分为 3 个部分。

  1. 把...嵌入
  2. 编码器
  3. 注意力

嵌入是将文本输入(段落和问题)转换成密集低维向量形式的表示。这是通过类似于本文中的方法完成的。

Character aware language modelling. Source: https://arxiv.org/pdf/1508.06615.pdf

我们的方法非常相似。唯一的区别是我们对卷积滤波器使用固定的核大小 5。我们还将单词表示与最大合并字符表示连接起来,然后将它们放入高速公路网络。

编码器是模型的基本构件。从上图的右侧可以看到编码器模块的细节。编码器由位置编码、层归一化、深度方向可分离的一维卷积、自关注和前馈层组成。

最后,注意层是网络的核心构件,问题和段落在这里融合。QANet 使用了 BiDAF 论文中使用的三线性注意函数。

我们开始吧!

履行

为简单起见,我们跳过数据处理步骤,直接进入神经网络。

把...嵌入

首先,我们定义输入占位符。一旦我们定义了占位符,我们就用单词嵌入来嵌入单词输入,用字符嵌入来嵌入字符输入。

然后,我们让它们通过 1 层 1 维卷积神经网络、最大池、连接单词+字符表示,最后让它们通过 2 层高速公路网络。我们将“重用”参数放在“conv”和“公路”函数中的原因是,我们希望段落和问题使用同一个网络。“conv”和“高速公路”功能是我们对卷积网络和高速公路网络的 Tensorflow 实现。(源代码可以在这里找到【https://github.com/NLPLearn/QANet )

我们将嵌入层的输出放入编码器层,以生成相应的上下文和问题表示。“residual_block”实现位置编码-> layer _ normalization-> depth wise 可分离卷积-> self attention ->前馈网络。

现在我们有了上下文和问题的表示,我们使用一个叫做三线性注意力的注意力函数将它们融合在一起。融合的输出现在具有关于问题的上下文的丰富信息。同样,我们将上下文到问题和问题到上下文的信息与上下文连接起来,并作为下一个输入传递给编码器层。

最后,我们有输出层,它接收注意力输出,并将它们编码成一个密集向量。这就是班的属性派上用场的地方。因为我们知道答案就在段落中的某个地方,对于段落中的每个单词,我们只需要计算这个单词是否是答案的概率。实际上,我们计算两种概率。对应单词属于答案开始的概率和对应单词属于答案区间结束的概率。这样,我们就不需要从一大堆字典里找出答案可能是什么,高效地计算概率。

就是这样!

培训和演示

与其他基于 RNN 的模型相比,QANet 训练相对较快。与流行的 BiDAF 网络相比,QANet 训练速度快 5~6 倍,性能更好。我们在 GTX1080 GPU 中为 60,000 个全局步骤训练网络,大约需要 6 个小时。

Visualizing results in Tensorboard. The top plots are the devset results and the bottom are the training results. “em” is exact match, “f1” is F1 score.

这是非常简单的方法,但我希望它能帮助你理解用神经网络回答问题!如果你有关于它们的问题,请留下评论,我会尽力回答你的问题。

感谢阅读,并请在评论中留下问题或反馈!

使用深度学习创建 Snapchat 过滤器系统

原文:https://towardsdatascience.com/implementing-snapchat-like-filters-using-deep-learning-13551940b174?source=collection_archive---------6-----------------------

如果你们都不喜欢阅读

欢迎,所有可能在看到‘Snapchat’和‘深度学习’这两个词后打开这篇文章的千禧一代程序员。我向上帝发誓,这两个字像飞蛾扑火一样吸引着你们。我在骗谁,我也是它的受害者,这就是为什么我花了几个小时做这个项目。

在这篇文章中,如果你愿意这样称呼它,我将回顾标题中的过程和项目背后的一点理论。坦白地说,即使我在标题中使用术语“Snapchat”也可能有点 clickbaity,因为尽管这个项目的工作原理相同(使用面部关键点将对象映射到面部),但就复杂性和准确性而言,它甚至没有接近 Snapchat 的实现。说完这些,让我从介绍我使用的数据集开始。

数据集

我使用的数据集如下:https://www.kaggle.com/c/facial-keypoints-detection蒙特娄大学的 Yoshua Bengio 博士提供。

每个预测的关键点由像素索引空间中的(x,y)实值对指定。共有 15 个关键点,代表了面部的不同元素。输入图像在数据文件的最后一个字段中给出,由像素列表(按行排序)组成,整数为(0,255)。这些图像是 96x96 像素。

既然我们对正在处理的数据类型有了很好的了解,我们需要对它进行预处理,以便我们可以将它用作模型的输入。

步骤 1:数据预处理和其他诡计

上面的数据集有两个我们需要关注的文件——training . CSVtest.csv. 训练文件有 31 列:30 列为关键点坐标,最后一列包含字符串格式的图像数据。它包含 7049 个样本,然而,这些例子中的许多在一些关键点上有“NaN”值,这让我们很难处理。因此我们将只考虑没有任何 NaN 值的样本。下面的代码就是这样做的:(下面的代码也对图像和关键点数据进行规范化,这是一个非常常见的数据预处理步骤)

一切都好吗?不完全是,没有。似乎只有 2140 个样本不包含任何 NaN 值。训练一个通用和精确的模型,这些样本要少得多。因此,为了创建更多的数据,我们需要扩充我们当前的数据

数据扩充是一种通过使用缩放、平移、旋转等技术从现有数据中生成更多数据的技术。在这种情况下,我镜像了每张图像及其对应的关键点,因为像缩放和旋转这样的技术可能会扭曲面部图像,从而破坏模型。最后,我将原始数据与新的扩充数据结合起来,得到总共 4280 个样本。

步骤 2:模型架构和培训

现在让我们进入项目的深度学习部分。我们的目标是预测一张看不见的脸的每个关键点的坐标值,,因此这是一个回归问题。由于我们正在处理图像,卷积神经网络是特征提取的一个非常明显的选择。这些提取的特征然后被传递到一个完全连接的神经网络,该网络输出坐标。最终的密集层需要 30 个神经元,因为我们需要 30 个值(15 对(x,y)坐标)。

  • “ReLu”激活在每个卷积和密集层之后使用,除了最后一个密集层,因为这些是我们需要作为输出的坐标值
  • 剔除调整用于防止过度拟合
  • 添加最大池是为了降维

模型能够达到最小损耗 ~0.0113 ,精度 ~80% ,我觉得已经足够体面了。以下是测试集上模型性能的一些结果:

Model performance on the Test set

我还需要检查模型在来自我的网络摄像头的图像上的表现,因为这是模型在过滤器实施期间将接收到的,下面是模型在我美丽的脸的图像上的表现:

Don’t be intimidated by this scary face. I don’t bite.

第三步:将模型付诸实施

我们已经让我们的模型工作了,所以我们现在要做的就是使用 OpenCV 来做以下事情:

  1. 从网络摄像头获取图像帧
  2. 检测每个图像帧中的面部区域,因为图像的其他部分对模型没有用(我使用了正面面部哈尔级联来裁剪面部区域)
  3. 通过转换为灰度、规格化和整形来预处理该裁剪区域
  4. 将预处理后的图像作为输入传递给模型
  5. 获得对关键点的预测,并使用它们在面部定位不同的过滤器

当我开始测试的时候,我脑子里没有任何特定的过滤器。我在 2018 年 12 月 22 日左右产生了这个项目的想法,作为一个像其他普通人一样的超级圣诞粉丝,我决定采用以下过滤器:

Filters

我使用了特定的关键点来缩放和定位上述每个过滤器:

  • 眼镜滤镜:左眼左关键点和右眼右关键点之间的距离用于缩放。眉毛关键点和左眼左关键点用于眼镜的定位
  • 胡须过滤器:左嘴唇关键点和右嘴唇关键点之间的距离用于缩放。上唇关键点和左唇关键点用于胡须的定位
  • 帽子滤镜:脸部的宽度用于缩放。眉毛关键点和左眼左关键点用于帽子的定位

执行上述所有操作的代码如下:

结果

上面,你可以看到项目的最终输出,其中包含一个在我脸上使用滤镜的实时视频和另一个标绘了关键点的实时视频。

项目的局限性

虽然这个项目运行得很好,但我确实发现了一些不足之处,使它有点不完美:

  • 不是最准确的模型。虽然在我看来 80%已经相当不错了,但还是有很大的提升空间。
  • 这个当前的实现只适用于选定的一组过滤器,因为我不得不做一些手动调整,以获得更精确的定位和缩放。
  • 将滤镜应用到图像的过程在计算上是相当低效的,因为要覆盖。png 过滤器图像到基于 alpha 通道的网络摄像头图像上,我必须在 alpha 不等于 0 的地方逐个像素地应用过滤器。这有时会导致程序在检测到图像中不止一张人脸时崩溃。

该项目的完整代码在我的 Github 上:https://Github . com/agr awal-rohit/Santa-filter-face-key point-regression

如果你想改进这个项目,或者你对我解决上述问题有任何建议,请务必在下面留下回复,并在 Github repo 上生成一个 pull 请求。谢谢你的来访,希望你喜欢这本书。

再见。

在 Tensorflow 中实现空间批量/实例/图层归一化[TF 中的手动反推]

原文:https://towardsdatascience.com/implementing-spatial-batch-instance-layer-normalization-in-tensorflow-manual-back-prop-in-tf-77faa8d2c362?source=collection_archive---------5-----------------------

Photo by Daniel van den Berg on Unsplash

这篇文章是对实现不同规范化层的简单回顾。

请注意,这篇帖子是给未来的自己看的,回顾这篇帖子里呈现的材料。

简介

Image from this website

今天我想写一篇关于实现不同类型的标准化层的短文。如上所述,批次/层/实例甚至组规范化方法都是相互关联的。唯一的区别是他们取均值和方差(一阶和二阶矩)的维度。

算出导数

计算每个归一化方案的导数也很容易。唯一的区别是,1)我们求导的维数,2)求导时需要除以的数。

上面的 DIM 变量显示了每个归一化方案之间的差异。假设我们有代表(B,H,W,C)的 4D 张量,它代表图像的批次、高度、宽度和通道。

批次定额 →对通道(1,1,1,c)取均值和方差
层定额 →对批次(b,1,1,1)
实例定额 →对批次/通道(b,1,1,c)取均值和方差

更新我重新阅读了最初的批量定额论文,作者没有包括 sigma 项。我也更新了代码。

批量归一化

使用我们能够从顶部驱动的派生,实现批量规范化层是非常容易的。

此外,我们可以确认,在该层之后,平均值为零(非常接近零),并且对于我们已经归一化的维度,标准偏差被设置为 1。

图层归一化

类似的故事层标准化,这一次我们将执行标准化方面的批量维度。

实例规范化

最后对于实例标准化,我们需要对批量维度和渠道维度进行标准化。

这篇短文的代码

要获取这篇博文的代码,请点击这里。

最后的话

实现这种标准化层总是好的做法,对于想要更多数学细节的人,请看这篇博文。

参考

  1. (2018).Arxiv.org。检索于 2018 年 11 月 18 日,来自https://arxiv.org/pdf/1803.08494.pdf
  2. 空间 Batchnorm Backprop 实施说明 Sam Kirkiles 博客 Medium。(2018).中等。2018 年 11 月 18 日检索,来自https://medium . com/samkirkiles/spatial-batch norm-back prop-implementation-notes-8 ccde 1 AC 62 a 2
  3. 推导批次标准化的后向传递的梯度。(2018).kevinzakka . github . io . 2018 年 11 月 18 日检索,来自https://kevinzakka . github . io/2016/09/14/batch _ normalization/
  4. thorey,C. (2016 年)。流过批量归一化的渐变是什么样子的?。Cthorey.github.io..检索于 2018 年 11 月 18 日,来自http://cthorey . github . io ./back propagation/

用 sk learn——线性回归实现监督学习算法

原文:https://towardsdatascience.com/implementing-supervised-learning-algorithm-by-sklearn-linear-regression-96ffbdb29961?source=collection_archive---------4-----------------------

在这篇博客中,我们将看到如何使用 Python 中的 SkLearn 库实现监督学习算法—线性回归。SkLearn 或 scikit-learn 是最广泛使用的机器学习和数据分析工具之一。它完成所有的计算,让您专注于提高效率,而不是算法的计算部分。

关于 scikit-learn 的更多细节,你可以从给定的链接中参考官方文档

[## sci kit-learn:Python 中的机器学习

编辑描述

scikit-learn.org](http://scikit-learn.org/stable/)

什么是监督学习算法?

机器学习大致包括两种方法,一种是有监督的,另一种是无监督的。在监督学习中,我们事先知道测试数据集的输出,而在无监督学习中,没有这样的数据集提供给我们。

要深入了解这个主题,请参考给定的链接。

[## 监督和非监督机器学习算法-机器学习掌握

什么是监督机器学习,它与无监督机器学习有什么关系?在这篇文章中,你将…

machinelearningmastery.com](http://machinelearningmastery.com/supervised-and-unsupervised-machine-learning-algorithms/)

现在到了有趣的部分——编码

我们将用 Python 编码,确保你已经在你的系统上安装了它。我将指导您安装所需的外部库。

import matplotlib.pyplot as pltimport numpy as npfrom sklearn import linear_model

让我快速地引导你到我们正在使用的库,如果你还没有它们,你可以使用 pip 安装它们。

  • Matplotlib:是一个用于绘制 2D 图形和图表的 python 库。我们将使用它来表示我们的模型。
  • Numpy :是 python 中用来进行科学计算的包。我们将使用它为我们的数据集制作数组和矩阵,并对它们进行基本计算。
  • Skle arn—Linear _ model:我们将使用 sklearn 的线性模型对给定的数据集进行线性回归。

出于教学目的,我们将使用小型硬编码数据集,否则您可以使用任何数据集。有像 熊猫 这样的库允许从外部源加载数据集。

比方说,现在我们想根据房子的大小来预测房子的价格。我们的测试数据集将是这样的。

DataSet Table

我们现在将使用 python 中的字典放置数据集(用于教程目的),并将使用 matplot 库绘制它们。

import matplotlib.pyplot as pltimport numpy as npfrom sklearn import datasets, linear_modelhouse_price = [245, 312, 279, 308, 199, 219, 405, 324, 319, 255]size = [1400, 1600, 1700, 1875, 1100, 1550, 2350, 2450, 1425, 1700]plt.scatter (size,house_price, color=’black’)plt.ylabel(‘house price’)plt.xlabel(‘size of house’)plt.show()

上面将给出以下输出。

现在,我们使用 scikit 的线性模型以如下方式训练我们的数据集。

import matplotlib.pyplot as pltimport numpy as npfrom sklearn import datasets, linear_modelhouse_price = [245, 312, 279, 308, 199, 219, 405, 324, 319, 255]size = [1400, 1600, 1700, 1875, 1100, 1550, 2350, 2450, 1425, 1700]size2 = np.array(size).reshape((-1, 1))#fitting into the modelregr = linear_model.LinearRegression()regr.fit(size2, house_price)print('Coefficients: \n', regr.coef_)print('intercept: \n', regr.intercept_)##############################formula obtained for the trained modeldef graph(formula, x_range): x = np.array(x_range) y = eval(formula) plt.plot(x, y)#plotting the prediction line graph('regr.coef_*x + regr.intercept_', range(1000, 2700))print regr.score(size2, house_price)#############################plt.scatter (size,house_price, color=’black’)plt.ylabel(‘house price’)plt.xlabel(‘size of house’)plt.show()

编译完上面的代码后,你会看到带有预测行的数据模型。

(‘Coefficients: \n’, array([ 0.10976774]))(‘intercept: \n’, 98.248329621380833)

这里,预测线的方程是“y = mx + c”的形式,上面计算了“m”和“c”的值。

给定房子的大小,要预测任何新的价格,我们可以通过以下方式使用线性模型提供的预测函数。

print regr.predict([2000])

预测产量为 317.78380528 千美元。

这就结束了线性压缩的教程。对于任何开始学习机器的人来说,我建议不要使用 scikit 库,先进行一次线性回归,只是为了更好地理解概念。尽量使用 梯度下降 等算法,使平方误差函数最小化。如果你不想用 python 编码,你可以使用 GNU-Octave 或 Matlab 等工具,它们非常适合原型和分析。此外,对矩阵和计算有很好的了解会对你有很大帮助。

快乐编码:)

感谢阅读这篇文章。如果你觉得这篇文章有帮助,一定要点击下面的❤来推荐它。这对我意义重大。

如果你想了解更多关于编程的知识,你可以关注我,这样我写新帖的时候你会收到通知。

还有,让我们在 TwitterLinkedinGithub脸书 上成为朋友吧。

在 Tensorflow 中实现 T-SNE[TF 中的手动回柱]

原文:https://towardsdatascience.com/implementing-t-sne-in-tensorflow-manual-back-prop-in-tf-b08c21ee8e06?source=collection_archive---------2-----------------------

GIF from this website

今天,我只是想研究一下 t 分布随机邻居嵌入(t-SNE),并想在 tensorflow 中实现它,同时创建一些可视化。下面是我们要比较的案例。

案例 A)纯 T-SNE 降维到 2D
案例 B)全连接网络作为 T-SNE 降维到 2D
案例 C)卷积神经网络作为 T-SNE 降维到 2D
案例 D)全连接网络作为 T-SNE 降维到 3D
案例 E)卷积神经网络作为 T-SNE 降维到 3D

请注意这篇帖子是为了我未来的自己,回顾如何在 tensorflow 中实现 T-SNE。

Original SNE paper from this website

TSNE paper from this website

如果有人感兴趣,T-SNE 最初是基于辛顿教授发明的随机邻居嵌入(SNE)。我链接了原始的 SNE 论文和 T-SNE 论文。

T-SNE 比 PCA 做得更好的案例

Image from this website and this website

已经有不同的方法来执行降维,但是传统方法存在局限性。例如,主成分分析(PCA)以线性方式降低维度,并且在一些情况下,更高维度的几何形状是以非线性方式。它没有捕捉到关键信息。更多更好更深入的解释请阅读这篇博文或观看下面的视频。

Video from GoogleTechTalks

一些有用的知识(我不得不学)

Image from this website

对我来说,在深入研究 T-SNE 之前,了解一些额外的东西是个好主意,比如指数归一化技巧,(或者稳定的 softmax 函数)或者对二分搜索法的回顾。

video from
Udacity

此外,它有助于审查二分搜索法,一般来说,它的运行时间为 O(登录),这是很好的。对于 T-SNE,它用于搜索最佳西格玛值,以匹配我们想要的困惑。

Image from this website

最后,来自 Distill 的一份出版物是一个令人惊奇的在线资源,可以让你更深入地了解 T-SNE 及其成功的原因。

张量流中的纯 T-SNE

遵循这里完成的 Numpy 实现并将其转换成 tensorflow 并不难。(liam schoneveld 也出色地解释了每个函数背后的数学原理。).此外,我们可以使纯 SNE 霸王龙成为 SNE 霸王龙层,如上图所示。并分配前馈操作以及反向传播。剩下要做的唯一的事情是连接到完全连接的层以及卷积层到这个 T-SNE 层。

这一点也不难,我们已经实现了全连接层/卷积层,我们可以做类似上面的事情来建立连接。

结果:案例 A)纯 T-SNE 退化为 2D

上面的 gif 显示了每个星团是如何通过历元数形成的。最终的聚类如下图所示。

如上所述,我们注意到算法很好地将数字分成不同的簇,但是,我们仍然可以注意到一些随机点属于不正确的点。

在红色区域,我们可以观察到一些 0/5 位于错误的位置。正如在天蓝色区域看到的一样,四和九之间没有明显的区别。

结果:情况 B)全连通网络为 T-SNE 简化为 2D

由于我们在最后一层使用 ELU()激活函数,我们可以注意到轴点是正数。此外,似乎大部分聚类都是在培训的开始阶段完成的。(具体来说,5000)。剩下的用于重新定位每个数据点。

首先,我们可以注意到,大多数的零都很好地聚集在一起。(与纯 SNE 霸王龙的情况相比,要好得多。).然而,四和九之间的区别仍然不是很清楚…

结果:情况 C)卷积神经网络为 T-SNE 简化为 2D

对于全连接网络的卷积神经网络,我们可以看到部分数据点粘在 Y 轴上。但我个人认为四九分开比其他任何情况都好。

以上是最终结果,在最右边的点,我们可以看到 4 和 9 之间的分离比其他的更好,因为 4 聚集在最右边。(但是需要分开得多。)

使用 Sklearn T-SNE 进行比较

我想将我的结果与 sklearn 的 TSNE 进行比较,如果我使用相同的学习速率和相同的超参数,我会得到上面的结果。

然而,通过一些超参数调整,我能够得到上述结果。四个和九个之间仍然存在着不清楚的分离,但是每个星团之间的距离却更远了。

结果:案例 D)全连通网络为 T-SNE 简化为 3D

上面的 gif 展示了 MNIST 数据集降维为 2 的聚类过程,总体来说做得不错。

上面的 gif 显示了最终的聚类。然而,与其他数字相比,4 和 9 之间的区别并不明显。

结果:情况 E)卷积神经网络为 T-SNE 简化为 3D

上面的 gif 显示了我在连接到 T-SNE 层之前使用 CNN 时的聚类进度。下面是最终得到的 gif。

我个人认为 CNN 在数据聚类方面做得更好,因为在处理图像时,空间信息更有用。

互动码

对于 Google Colab,您需要一个 Google 帐户来查看代码,而且您不能在 Google Colab 中运行只读脚本,所以请在您的操场上创建一个副本。最后,我永远不会请求允许访问你在 Google Drive 上的文件,仅供参考。编码快乐!

要访问案例 A)的代码,请点击此处。
要访问案例 B)的代码,请点击此处。
要访问案例 C)的代码,请点击此处。
要访问案例 D)的代码,请点击此处。
要访问案例 E)的代码,请点击此处。
要获取案例 Z 的代码,请点击此处。

奇怪的结果

最后,我只是觉得这是一个很酷的结果。显然聚类做得很糟糕,但还是有点酷,哈哈。

最后的话

由于 t-SNE 的操作方式,对新数据点进行降维非常困难,为了克服这个问题,原始论文的作者引入了参数 T-SNE。而论文可以在下面看到。

Paper from this website

接下来的事情是实施上述文件,这将是我的下一个任务。(以及均匀流形近似和投影(UMAP))

如果发现任何错误,请发电子邮件到 jae.duk.seo@gmail.com 给我,如果你想看我所有写作的列表,请点击这里查看我的网站。

同时,在我的推特这里关注我,访问我的网站,或者我的 Youtube 频道了解更多内容。我还实现了广残网,请点击这里查看博文 pos t。

参考

  1. Tensorflow?,C. (2018)。在 Tensorflow 中不复制张量的情况下批量计算成对距离?。堆栈溢出。检索于 2018 年 7 月 21 日,来自https://stack overflow . com/questions/37009647/compute-pairwise-distance-in-a-batch-without-replication-tensor-in-tensor flow
  2. NumPy . set _ print options—NumPy v 1.14 手册。(2018).Docs.scipy.org。检索于 2018 年 7 月 21 日,来自https://docs . scipy . org/doc/numpy-1 . 14 . 0/reference/generated/numpy . set _ print options . html
  3. tf.reduce_max | TensorFlow。(2018).张量流。检索于 2018 年 7 月 21 日,来自https://www.tensorflow.org/api_docs/python/tf/reduce_max
  4. tf.matrix_set_diag | TensorFlow(2018).张量流。检索于 2018 年 7 月 21 日,来自https://www . tensor flow . org/API _ docs/python/TF/matrix _ set _ diag
  5. tf.matrix_diag |张量流。(2018).张量流。检索于 2018 年 7 月 21 日,来自https://www.tensorflow.org/api_docs/python/tf/matrix_diag
  6. tf.matrix_set_diag | TensorFlow(2018).张量流。检索于 2018 年 7 月 21 日,来自https://www . tensor flow . org/API _ docs/python/TF/matrix _ set _ diag
  7. 学习?,H. (2018)。logit 最大值的减法如何提高学习?。交叉验证。检索于 2018 年 7 月 21 日,来自https://stats . stack exchange . com/questions/338285/how-the-subtraction-of-the-logit-maximum-improve-learning
  8. 使用 t-SNE 可视化数据。(2018).YouTube。检索于 2018 年 7 月 21 日,来自 https://www.youtube.com/watch?v=RJVL80Gg3lA
  9. Quora.com(2018)。t-SNE 算法相比 PCA 有什么优势?— Quora 。[在线]可从以下网址获取:https://www . quora . com/What-advantages-the-t-SNE 算法优于 PCA【2018 年 7 月 21 日获取】。
  10. Python 中的 lambda、map 和 filter—RUP esh mis HRA—Medium。(2017).中等。检索于 2018 年 7 月 21 日,来自https://medium . com/@ happymishra 66/lambda-map-and-filter-in-python-4935 f 248593
  11. 德斯莫斯图表。(2018).德斯莫斯图形计算器。检索于 2018 年 7 月 21 日,来自https://www.desmos.com/calculator
  12. 类,P. (2018)。Python 调用类中的函数。堆栈溢出。检索于 2018 年 7 月 23 日,来自https://stack overflow . com/questions/5615648/python-call-function-within-class
  13. 二分搜索法。(2018).YouTube。检索于 2018 年 7 月 23 日,来自https://www.youtube.com/watch?v=0VN5iwEyq4c
  14. (2018).Cs.nyu.edu。检索于 2018 年 7 月 23 日,来自https://cs.nyu.edu/~roweis/papers/sne_final.pdf
  15. (2018).Cs.toronto.edu。检索于 2018 年 7 月 23 日,来自http://www.cs.toronto.edu/~hinton/absps/tsne.pdf
  16. 用于视觉识别的 CS231n 卷积神经网络。(2018).cs 231n . github . io . 2018 年 7 月 23 日检索,来自http://cs231n.github.io/linear-classify/#softmax
  17. [副本],D. (2018)。双竖线。数学栈交换。检索于 2018 年 7 月 23 日,来自https://math . stack exchange . com/questions/1918 317/double-vertical-bars
  18. 只有 Numpy:(为什么我做手动反向传播)实现多通道/层卷积神经…(2018).中等。2018 年 7 月 23 日检索,来自https://medium . com/swlh/only-numpy-why-I-do-manual-back-propagation-implementing-multi-channel-layer-convolution-neural-7d 83242 FCC 24
  19. Schoneveld,L. (2017 年)。原始数字:t-SNE。nlml。检索于 2018 年 7 月 23 日,来自 https://nlml.github.io/in-raw-numpy/in-raw-numpy-t-sne/#eq1
  20. 奥雷利媒体/t-SNE-教程。(2018).GitHub。检索于 2018 年 7 月 23 日,来自https://github.com/oreillymedia/t-SNE-tutorial
  21. tf.clip_by_value |张量流。(2018).张量流。检索于 2018 年 7 月 23 日,来自https://www.tensorflow.org/api_docs/python/tf/clip_by_value
  22. tf.random_gamma |张量流。(2018).张量流。检索于 2018 年 7 月 23 日,来自https://www.tensorflow.org/api_docs/python/tf/random_gamma
  23. Matplotlib . py plot . text-Matplotlib 2 . 2 . 2 文档。(2018).Matplotlib.org。检索于 2018 年 7 月 23 日,来自https://matplotlib . org/API/_ as _ gen/matplotlib . py plot . text . html
  24. 变,m. (2018)。matplotlib 艺术家动画:标题或文本不变。堆栈溢出。检索于 2018 年 7 月 23 日,来自https://stack overflow . com/questions/47421486/matplotlib-artist-animation-title-or-text-not-changing
  25. matplotlib,3。(2018).使用 matplotlib 的 3D 动画。堆栈溢出。检索于 2018 年 7 月 23 日,来自https://stack overflow . com/questions/38118598/3d-animation-using-matplotlib
  26. Wattenberg,m .,Viégas,f .,& Johnson,I. (2016 年)。如何有效地使用 t-SNE?蒸馏,1(10)。doi:10.23915
  27. sk learn . manifold . tsne—sci kit-learn 0 . 19 . 2 文档。(2018).Scikit-learn.org。检索于 2018 年 7 月 23 日,来自http://sci kit-learn . org/stable/modules/generated/sk learn . manifold . tsne . html
  28. 动画示例代码:simple _ 3d anim . py—Matplotlib 2 . 0 . 2 文档。(2018).Matplotlib.org。检索于 2018 年 7 月 23 日,来自https://matplotlib . org/examples/animation/simple _ 3d anim . html
  29. 何时使用 cla(),c. (2018)。什么时候使用 cla()、clf()或 close()来清除 matplotlib 中的绘图?。堆栈溢出。2018 年 7 月 23 日检索,来自https://stack overflow . com/questions/8213522/when-to-use-cla-clf-or-close-for-clearing-a-plot-in-matplotlib
  30. 何时使用 cla(),c. (2018)。什么时候使用 cla()、clf()或 close()来清除 matplotlib 中的绘图?。堆栈溢出。检索于 2018 年 7 月 23 日,来自https://stack overflow . com/questions/8213522/when-to-use-cla-clf-or-close-for-clearing-a-plot-in-matplotlib

在 PyTorch 中实现 word2vec(跳格模型)

原文:https://towardsdatascience.com/implementing-word2vec-in-pytorch-skip-gram-model-e6bae040d2fb?source=collection_archive---------0-----------------------

你可能听说过 word2vec 嵌入。但是你真的了解它是如何工作的吗?我想我知道。但我没有,直到实现它。

这就是为什么我创建这个指南。

2021 年更新:更详细的文章见:https://neptune.ai/blog/word-embeddings-guide

先决条件

我假设你知道更多-更少 word2vec 是什么。

文集

为了能够跟踪每一步,我使用了以下 nano 语料库:

创造词汇

第一步是用 word2vec 创建词汇表。它必须从头开始构建,因为不支持扩展它。

词汇表基本上是一个带有指定索引的独特单词列表。

语料库非常简单和简短。在实际实现中,我们必须执行大小写规范化,删除一些标点符号等,但为了简单起见,让我们使用这些漂亮而干净的数据。无论如何,我们必须把它符号化:

这将为我们提供一个令牌列表:

[['he', 'is', 'a', 'king'],
 ['she', 'is', 'a', 'queen'],
 ['he', 'is', 'a', 'man'],
 ['she', 'is', 'a', 'woman'],
 ['warsaw', 'is', 'poland', 'capital'],
 ['berlin', 'is', 'germany', 'capital'],
 ['paris', 'is', 'france', 'capital']]

我们迭代语料库中的标记,并生成唯一单词(标记)的列表。接下来,我们创建两个字典,用于单词和索引之间的映射。

这给了我们:

 0: 'he',
 1: 'is',
 2: 'a',
 3: 'king',
 4: 'she',
 5: 'queen',
 6: 'man',
 7: 'woman',
 8: 'warsaw',
 9: 'poland',
 10: 'capital',
 11: 'berlin',
 12: 'germany',
 13: 'paris',
 14: 'france'

我们现在可以生成对center wordcontext word。让我们假设上下文窗口是对称的并且等于 2。

它为我们提供了一组centercontext指数:

array([[ 0,  1],
       [ 0,  2],
       ...

这很容易翻译成文字:

he is
he a
is he
is a
is king
a he
a is
a king

这很有道理。

定义目标

现在,我们正在讨论从第一个等式到工作实现的细节。

对于跳格,我们感兴趣的是预测上下文,给定中心词和一些参数化。这是我们单对的概率分布。

E.g.: P(king | is)

现在,我们想通过所有单词/上下文对来最大化它。

等等,为什么?

由于我们对预测给定中心词的上下文感兴趣,所以我们希望最大化每个contextcenter对的 P(上下文|中心)。由于概率总和为 1——对于所有不存在的contextcenter对,我们隐式地使 P(上下文|中心)接近于 0。通过将这些概率相乘,如果我们的模型是好的,我们使这个函数接近 1,如果是坏的,这个函数接近 0。当然我们追求的是一个好的——所以一开始就有 max 算子。

这个表达式不太适合计算。这就是为什么我们要执行一些非常常见的转换。

步骤 1——用负对数似然替换概率。

回想一下,神经网络是关于最小化损失函数的。我们可以简单地将 P 乘以-1,但是应用 log 可以给我们更好的计算特性。这不会改变函数极值的位置(因为 log 是一个严格单调的函数)。所以表达式改为:

步骤 2——用总和替换乘积

下一步是用总和代替乘积。我们能做到是因为:

步骤 3——转换成合适的损失函数

除以 par 数(T)后,我们得到最终的损失项:

定义 P

很好,但是我们如何定义 P(context|center) ?现在,让我们假设到达词实际上有两个向量。一个 if 作为中心词出现( v ),第二个 if 上下文( u )。假设 P 的定义如下:

太吓人了!

让我把它分解成更小的部分。请参见以下结构:

Softmax!

这只是一个 softmax 函数。现在仔细看看提名者

uv 都是矢量。这个表达式就是给定的centercontext对的标量积。更大,因为它们彼此更相似。

现在,分母:

我们正在遍历词汇表中的所有单词。

以及计算给定中心词和词汇中被视为上下文词的每个词的“相似度”。

总结一下:

对于语料库中每个现有的中心、上下文对,我们正在计算它们的“相似性得分”。然后除以每一个理论上可能的情境的总和——知道分数是相对高还是相对低。因为 softmax 保证取 0 和 1 之间的值,所以它定义了有效的概率分布。

太好了,现在我们来编码吧!

实现这一概念的神经网络包括三层:输入、隐藏和输出。

输入层

输入层只是以一键编码方式编码的中心字。它的尺寸是[1, vocabulary_size]

隐蔽层

隐藏层使我们的 v 向量。因此它必须有embedding_dims神经元。为了计算它的价值,我们必须定义W1权重矩阵。当然它必须是[embedding_dims, vocabulary_size].没有激活函数——只有简单的矩阵乘法。

重要的是——W1的每一列存储单个单词的 v 向量。为什么?因为 x 是一个热点,如果您将一个热点向量乘以矩阵,结果与从其中选择选择单列相同。用一张纸自己试试;)

输出层

最后一层必须有vocabulary_size神经元——因为它为每个单词生成概率。因此,就形状而言,W2就是[vocabulary_size, embedding_dims]

在此之上,我们必须使用 softmax 层。PyTorch 提供了这个的优化版本,结合了log——因为常规的 softmax 在数值上并不真正稳定:

log_softmax = F.log_softmax(a2, dim=0)

这相当于计算 softmax,然后应用 log。

现在我们可以计算损失。像往常一样,PyTorch 提供了我们需要的一切:

loss = F.nll_loss(log_softmax.view(1,-1), y_true)

nll_loss在 logsoftmax 上计算负对数似然。y_true是上下文单词——我们想让它尽可能高——因为对x, y_true来自训练数据——所以它们确实是上下文的中心。

反向投影

当我们钓到向前传球时,现在是时候表演向后传球了。简单来说:

loss.backward()

为了优化,使用了 SDG。它如此简单,以至于用手工编写比创建优化器对象更快:

W1.data -= 0.01 * W1.grad.data
W2.data -= 0.01 * W2.grad.data

最后一步是将梯度归零,以使下一步清晰:

W1.grad.data.zero_()
W2.grad.data.zero_()

训练循环

是时候把它编译成训练循环了。它可能看起来像:

一个潜在的棘手问题是y_true定义。我们并不显式地创建一个 hot,而是由nll_loss自己创建。

Loss at epo 0: 4.241989389487675
Loss at epo 10: 3.8398486052240646
Loss at epo 20: 3.5548086541039603
Loss at epo 30: 3.343840673991612
Loss at epo 40: 3.183084646293095
Loss at epo 50: 3.05673006943294
Loss at epo 60: 2.953996729850769
Loss at epo 70: 2.867735825266157
Loss at epo 80: 2.79331214427948
Loss at epo 90: 2.727727291413716
Loss at epo 100: 2.6690095041479385

提取向量

好了,我们已经训练好了网络。第一,最后一件事是提取单词的向量。有三种可能:

  • 使用 W1 中的矢量 v
  • 使用 W2 中的向量 u
  • 使用平均 v 和 u

试着自己思考什么时候用哪个;)

待续

我正在做这个的在线互动演示。应该很快就有了。敬请期待;)

你可以从这里下载代码。

Working on this!

使用自定义文本分类的隐式搜索功能

原文:https://towardsdatascience.com/implicit-search-functionality-using-custom-text-classification-58048a6815eb?source=collection_archive---------7-----------------------

文本分类是将任何文本语料库智能地分类到各种预定义的类别中,并且是结构化非结构化数据以对其进行分析的最常见方法之一。在我们之前的博客中,我们讨论了不同的机器学习技术来分类文本,包括我们最新的产品——定制分类器。在另一篇文章中,我们讨论了如何在没有任何训练数据的情况下,使用自定义分类器在自定义类别上构建自己的文本分类模型。在本文中,我们将看到自定义分类器如何用于显式和隐式文本分类。

显式文本分类

为了更好地理解我们所说的明确的文本分类是什么意思,考虑一个文本输入来为其分配一种情绪,“教练对球队的表现感到厌恶”,用以下类别将输入的文本分类为:厌恶、高兴、害怕、悲伤。你的大胆猜测是什么?没错,就是恶心。

这是一个显式文本分类的精确示例,其中输入文本要么携带分类,要么本身直接指向您必须分配给它的分类。让我们通过下面的例子来看看我们的自定义分类器在这种场景下的表现。

隐式文本分类

隐式文本分类可以被认为是将文本分类成类别,而不提及文本和所定义的类别之间的任何直接关系。例如,如果你想到莱昂内尔·梅西,我们脑海中会立即浮现什么?足球?。但是,当我们谈论一个没有梅西背景的自动文本分类模型时,它能够以类似的方式识别同一个例子吗?如果你说的是我们的定制分类器,那么答案是非常肯定的!

不相信我们?试试我们的演示!!

自定义分类器能够分类,莱昂内尔梅西不只是另一个名字,但也与足球有关。这是隐式文本分类的一个例子,其中输入文本没有直接指示它需要被分配到的类别。

还不信服?让我们看看最近关于阿莱克西斯·桑切斯转会曼联的新闻报道中的另一个很酷的例子。

这不是很好吗?我们的分类器甚至没有提到这项运动就选择了联盟!!

正如我们所见,这是迈向通用人工智能的第一步。我们没有提到任何与英超联赛或足球相关的东西,但我们的自定义分类器可以识别这种关系。在显式文本分类的基础上进行隐式文本分类的能力使得自定义分类器成为一个令人惊叹的有用工具。

直到最近,这还是一个牵强的概念。正如我们所知,使用机器学习和文本分类项目到目前为止面临的最大障碍是训练算法的注释数据集的可用性。但是随着 ParallelDots 的内部研究团队最近在定制分类器背后的零触发学习启发算法,我们真正实现了我们的愿景,即提供触手可及的人工智能。

这是什么意思?

这清楚地表明,在行动中,我们的自定义分类器脱颖而出!想象一下,现在你不需要数据科学家或者 ML 专家来为你做文本分类器。此外,正如您可以看到的,我们在执行分析时会给出由我们定义的类别,因此,执行文本分类不需要预先训练,因此您不需要为您的分类定制训练数据集。

这使您能够进行文本分类,而不必担心输入的种类或领域。所以你实际上可以用同一个工具对法律新闻和体育新闻进行分类。

为什么只是这样,这意味着不管任何类型的数据,无论是推文,facebook 评论,新闻或评论,你都可以执行你的文本分类任务,而不必担心任何其他事情。此外,能够进行显式和隐式分类,您可以为您的内容构建一个更智能的搜索引擎,或者使您的对话机器人更加智能。

现在想试试吗?注册一个免费的 ParallelDots AI APIs 账号开始使用。

结论

定制分类器是人工智能将如何塑造我们未来自然语言处理需求的主要例子。它不仅让您在自己的输入数据上定义自己的类别,从而使您比任何其他文本分类工具都有优势,而且还使您的文本分类考虑到与您定义的类别的任何隐含或间接关系。

同时执行显式和隐式文本分类的能力给了你在执行任何文本分类时无与伦比的优势。自定义分类器因此成为帮助您摆脱任何束缚的先锋,这些束缚使您无法使用文本分类的真正力量。

parallel dots AI API,是由 ParallelDots Inc 提供的深度学习支持的 web 服务,可以理解大量的非结构化文本和视觉内容,为您的产品提供支持。你可以查看我们的一些文本分析API并通过填写此处的表格联系我们或者给我们 apis@paralleldots.com 写信。

理解分析、分析和报告之间差异的重要性

原文:https://towardsdatascience.com/importance-of-understanding-the-differences-between-analytics-analysis-and-reporting-7f7306feadb?source=collection_archive---------7-----------------------

这听起来可能是一个老生常谈的话题,但不幸的是,这仍然是一个没有任何好转的大问题。我们需要了解我们与数据的关系,包括分析、分析和报告,以确保我们处于正确的轨道上。但是为了知道你的确切位置,你需要一张真实的地图。如果你认为你是在做分析,而你实际上是在报告阶段,你可能会认为你已经在隧道的尽头,没有其他机会让你看它。这篇文章旨在为您提供一张地图,以便您可以充分利用现有的数据。

数字时代为我们了解我们的客户、粉丝、订户和利益相关者如何与我们互动提供了新的可能性。例如,在数字时代之前,不可能知道一篇特定文章的浏览量或独特观众的数量。现在,如果你为一家在线报纸或内容网站工作,你就知道哪些内容和许多其他信息一起被消费得最多。这是我们可以通过谷歌分析等网络分析工具获得的最基本的信息。

由于 Google Analytics 从一开始就是免费的,所有的数字企业都开始只用一段代码来观察他们网站的表现。这种可能性使每个人都开始使用网络分析工具,但在此过程中术语被混淆和误用。

谷歌分析为你提供了基本的报告,让你了解你的数字资产的一些关键数字。

根据谷歌的说法,这就是它的分析工具所做的:“获取你需要的数据,以做出智能营销和商业决策”

没错。获取数据。那叫举报。

根据一本英语词典,“报告是对某人所观察、听到、做的或调查的事情的口头或书面描述”。这里真的没有太多的思考或分析,你只需点击你正在使用的工具,你找到数据的来源,并传递所观察到的,没有意见,评论或假设。

我遇到过自称为“分析顾问”的人或顾问,因为他们可以从谷歌或 Adobe Analytics 获取数据。

让我们通过一些例子来看看不同之处:

当您有以下演示时,您正在做报告:

  • 2016 年 7 月网站订单同比增长 20%。
  • 在过去的 7 天里,我们有 15000 次来自谷歌分析的访问
  • 我们今天访问量最大的页面是主页
  • 我们标志性的红色秋装这个月被浏览了 20,000 次。
  • 昨天有 155 人下载了我们的 IOS 应用

你看这里真的没有假设或评论。这些是简单的事实。报告为分析创造了基础。在报告阶段没有决策。

当我们到达分析阶段时,我们将对现有数据进行详细检查。我们可以尝试得出一些结论,或者我们可以尝试证明我们的假设,或者我们可以尝试理解数据。另一方面,分析是一个多学科领域,它与统计、数学和计算机科学等不同领域合作。

分析通常对当前数据感兴趣,而分析使用过去的数据来预测未来的数据。分析并不总是关于行动,但分析总是关于行动。分析可以为分析提供基础,而分析可以使用自己的科学工具做出决策。分析可以由人来完成,但分析通常需要不同种类的技术、方法和模型,这些只能由机器来执行。

如果你有以下陈述,你就是在做分析:

  • 2016 年 7 月销量增长的可能原因之一是新的电视宣传活动。
  • 在新订单中,50%可以归功于谷歌 AdWords,10%可以归功于重定向,其余可以归功于直接和自然搜索。

以上陈述对我们收到的报告做了一些评论。分析实际上是试图在数据中找到一个意义。当我们的订单增加时,我们试图了解增加的原因,但很多时候我们从来没有 100%的把握。是设计的改变吗?是因为新广告吗?这是经济复苏的反映吗?是因为我们的竞争吗?因此,在许多情况下,我们并不知道 100%,但我们可能有一些强有力的结论。

如果我们谈论的是分析,我们会将我们在报告和分析中看到的内容付诸行动。如果我们证明或否定了我们在分析阶段创建的一些假设,我们可以用这些事实来应用于其他情况。

例如:谁看了 X 品牌的衣服和 Y 品牌的鞋子,这之间真的有科学的关系吗?我们可以做统计和优化测试。基于这些测试,我们可以启动或优化我们的推荐引擎。我们开始从统计学上寻找关系和意义,我们可以在任何重要的地方使用结果:当我们瞄准一个广告时,当我们个性化网站时,或者当我们用电子邮件发送一些优惠时。

丢失了你在数据相关工作中的位置是很正常的。因为分析从来就不是一个如此流行的术语或领域。它一直被科学家使用,但现在每个营销人员也需要处理数据。使用地图并知道你在哪里会帮助你避免许多困惑。每一步都非常重要,不是每个人都适合每一步。对于一些人来说,报告可能听起来很无聊,但它是至关重要的,一些喜欢组织的人可能会非常喜欢它。分析是为喜欢哲学和喜欢将定性数据与定量数据联系起来的好奇者准备的。分析介于报告和分析之间,它不一定要用数字来完成,也可能包括灵感或“直觉”。所以这个领域更适合那些不想和技术打交道,但又有足够创造力去开发不同假设的人。最后,分析是为那些喜欢用科学技术解决问题的人准备的。

最初发布于:

http://www . webanalyticspower . com/2016/08/importance-of-understanding-the-differences-analytics-and-reporting/

重要的资源,如果你正在与神经风格转移或深层照片风格转移

原文:https://towardsdatascience.com/important-resources-if-you-are-working-with-neural-style-transfer-or-deep-photo-style-transfer-719593b3dbf1?source=collection_archive---------0-----------------------

The Starry Night by Vincent van Gogh

神经风格迁移和深度照片风格迁移是深度学习的有趣领域。他们的受欢迎程度已经上升到另一个水平。像 Prisma 和 Deepart.io 这样的应用加速了流行。如果你正在进行神经风格转换或深度照片风格转换,这些是非常重要的资源(论文、实现和教程)来帮助你。

研究论文

  • 艺术风格的神经算法

[## [1508.06576]艺术风格的神经算法

摘要:在美术中,尤其是绘画,人类已经掌握了通过绘画创造独特视觉体验的技巧

arxiv.org](https://arxiv.org/abs/1508.06576)

  • 神经类型转移——综述

[## [1705.04058]神经类型转移:综述

摘要:Gatys 等人最近的工作证明了卷积神经网络(CNN)在创建神经网络方面的能力

arxiv.org](https://arxiv.org/abs/1705.04058)

  • 深度照片风格转移

[## [1703.07511]深层照片风格转移

摘要:本文介绍了一种深度学习的摄影风格转换方法

arxiv.org](https://arxiv.org/abs/1703.07511)

  • 控制神经风格转移中的知觉因素

[## [1611.07865]控制神经类型转移中的感知因素

摘要:神经类型转移显示了非常令人兴奋的结果,使新形式的图像处理成为可能。在这里我们…

arxiv.org](https://arxiv.org/abs/1611.07865)

  • 实例规范化:快速风格化缺少的要素

[## [1607.08022]实例规范化:快速风格化缺少的要素

摘要:本文回顾了 Ulyanov 等人提出的快速风格化方法。艾尔。(2016).我们展示了如何…

arxiv.org](https://arxiv.org/abs/1607.08022)

实现

  • Torch 实现的神经风格转移

[## JC Johnson/神经型

神经式算法的神经式 Torch 实现

github.com](https://github.com/jcjohnson/neural-style)

  • 神经类型转换的 Tensorflow 实现

[## 阿尼沙塔利耶/神经类型

TensorFlow 中的神经式-神经式!:艺术:

github.com](https://github.com/anishathalye/neural-style) [## 一个人工智能可以模仿任何艺术家猫/变量/日志/生活

看看下面两张图。一幅是当代艺术家李奥尼德·阿夫列莫夫画的,另一幅是…

www.anishathalye.com](http://www.anishathalye.com/2015/12/19/an-ai-that-can-mimic-any-artist/) [## cy Smith/神经风格-tf

神经风格的实现

github.com](https://github.com/cysmith/neural-style-tf) [## log0/神经风格绘画

“艺术风格的神经算法”的实现

github.com](https://github.com/log0/neural-style-painting) [## 灯心草/神经艺术-tf

tensorflow 中的“艺术风格的神经算法”

github.com](https://github.com/woodrush/neural-art-tf)

  • 深度照片风格转移的火炬实现

[## 栾福军/深摄风格转移

深照片风格转移.纸张“深照片风格转移”的代码和数据:https://arxiv.org/abs/1703.07511

github.com](https://github.com/luanfujun/deep-photo-styletransfer)

  • 深度照片风格转移的 Tensorflow 实现

[## Louie yang/deep-photo-style transfer-TF

深度照片风格转换的 tf - Tensorflow (Python API)实现

github.com](https://github.com/LouieYang/deep-photo-styletransfer-tf)

  • Tensorflow 实现快速风格转换

[## lengstrom/快速式转移

快速风格转移- TensorFlow CNN 快速风格转移!⚡🖥🎨🖼

github.com](https://github.com/lengstrom/fast-style-transfer)

  • Torch7(Lua)实现神经风格转移

[## 凯胜泰/神经警报

neuralart -论文《艺术风格的神经算法》的实现。

github.com](https://github.com/kaishengtai/neuralart)

  • Keras 实现的神经风格转移

[## fchollet/keras

用于 Python 的深度学习库。在 TensorFlow、Theano 或 CNTK 上运行。

github.com](https://github.com/fchollet/keras/blob/master/examples/neural_style_transfer.py) [## titu 1994/神经类型转移

神经风格转换——Keras 实现了“艺术设计的神经算法”。

github.com](https://github.com/titu1994/Neural-Style-Transfer) [## kevinzakka/style_transfer

“艺术风格的神经算法”的 style_transfer - Keras 实现

github.com](https://github.com/kevinzakka/style_transfer)

  • 样式转换算法的 ano+Keras 实现

[## jayanthkoushik/神经类型

风格转换算法的实现。

github.com](https://github.com/jayanthkoushik/neural-style)

  • 神经艺术风格的深度实现

[## Anders bll/neural _ artistic _ style

Python 中的神经艺术风格

github.com](https://github.com/andersbll/neural_artistic_style)

  • pyCaffe 实现的神经艺术风格

[## fzliu/style-transfer

风格转移 L. Gatys,A. Ecker 和 M. Bethge 的“艺术风格的神经算法”的实现。http…

github.com](https://github.com/fzliu/style-transfer)

  • Caffe 实现的神经风格转移

[## ftokarev/caffe-神经型

caffe-neural-style - Caffe 实现了 Leon A. Gatys 的论文“艺术风格的神经算法”。

github.com](https://github.com/ftokarev/caffe-neural-style)

  • 神经类型转移的 MXNet 实现

[## Apache/孵化器-mxnet

孵化器-mxnet -轻量级,可移植,灵活的分布式/移动深度学习,具有动态,突变感知…

github.com](https://github.com/apache/incubator-mxnet/tree/master/example/neural-style)

  • 链器实现神经风格的传递

[## DSA no/chainer-神经类型

使用链接器实现神经样式

github.com](https://github.com/dsanno/chainer-neural-style)

  • 用于神经风格转移的 MXNet 预训练模型

https://github . com/dmlc/we B- data/raw/master/mxnet/art/model . zip

教程

[## 用于艺术风格转换的卷积神经网络

现在有一个很棒的应用程序叫做 Prisma,它可以把你的照片转换成艺术作品,使用…

harishnarayanan.org](https://harishnarayanan.org/writing/artistic-style-transfer/) [## 这些“神经网络风格转移”工具是如何工作的?

你好!上周我发表了一篇关于神奇的机器学习艺术工具的文章。这让我开始思考——其他人会怎么做……

jvns.ca](https://jvns.ca/blog/2017/02/12/neural-style/) [## PyTorch 神经传递- PyTorch 教程 0.2.0_2 文档

嗯,更进一步需要一些数学知识。设(C_{nn})是一个预先训练好的深度卷积神经网络,并且…

pytorch.org](http://pytorch.org/tutorials/advanced/neural_style_tutorial.html) [## 用卷积神经网络画梵高

为了从图像中提取内容,Gatys 等人使用卷积层 5_2。将图像输入到……

www.subsubroutine.com](http://www.subsubroutine.com/sub-subroutine/2016/11/12/painting-like-van-gogh-with-convolutional-neural-networks) [## 带有生成模型的端到端神经艺术

在这篇博客中,我们将描述我们如何设计一个端到端的神经星夜风格发生器:与传统的…

dmlc.ml](http://dmlc.ml/mxnet/2016/06/20/end-to-end-neural-style.html) [## “艺术风格的神经算法”的 TensorFlow 实现

Github 上有这个笔记本和代码。本笔记本演示了论文“A…

www.chioka.in](http://www.chioka.in/tensorflow-implementation-neural-algorithm-of-artistic-style) [## 在 Mac 上安装 Neural-Style

想让你的电脑为你制作艺术品吗?看看神经类型的。它可以做一些非常不可思议的事情,但是天哪…

medium.com](https://medium.com/@eterps/installing-neural-style-on-a-mac-baf695d7256b) [## Gruff 的技术提示

我在绘画方面很垃圾,但是当你可以自己创造人工智能的时候,谁还需要艺术手指呢…

blog.gruffdavies.com](https://blog.gruffdavies.com/tag/neural-style/)

视频教程

文章

[## 深度神经网络现在可以将一张照片的风格转移到另一张照片上

你可能听说过一种被称为“风格转移”的人工智能技术——或者,如果你没听说过,你见过它…

www.theverge.com](https://www.theverge.com/2017/3/30/15124466/ai-photo-style-transfer-deep-neural-nets-adobe) [## 深度神经网络现在可以将一张照片的风格转移到另一张照片上

你可能听说过一种被称为“风格转移”的人工智能技术——或者,如果你没听说过,你见过它…

www.theverge.com](https://www.theverge.com/2017/3/30/15124466/ai-photo-style-transfer-deep-neural-nets-adobe) [## 使用 DeepStyle & Ubuntu 创建自己的“神经绘画”

神经网络可以做很多事情。它们可以解读图像,理解我们的声音,翻译对话…

www.makeuseof.com](http://www.makeuseof.com/tag/create-neural-paintings-deepstyle-ubuntu/) [## 风格转移实验

风格转换是以其他图像的风格重新组合图像的技术。这些大多是使用…

genekogan.com](http://genekogan.com/works/style-transfer/) [## 神经类型解释

本文提出了一种艺术风格的神经算法,详细介绍了如何从给定的图像中提取两组特征

kvfrans.com](http://kvfrans.com/neural-style-explained/) [## 神经风格转移-新媒体新技术 2017

莱顿媒体技术硕士 2017 春季学期新媒体新技术课程学生的网站…

sites.google.com](https://sites.google.com/site/newmedianewtechnology2017/portfolios/anna/neural-style-transfer) [## 极端风格机器:使用随机神经网络生成纹理

等等,什么!基于完全随机神经网络生成高质量图像?这就是不合理的…

nucl.ai](https://nucl.ai/blog/extreme-style-machines/) [## 使用神经算法添加或删除画家的风格

伦敦的新媒体艺术家凯尔·麦克唐纳告诉创造者项目,他是如何劫持“深度梦”式的网络来…

creators.vice.com](https://creators.vice.com/en_us/article/nz44gm/add-or-delete-a-painters-style-using-neural-algorithms)

使用神经风格转移/深度照片风格转移的公司

[## 成为一名数字艺术家

人工智能把你的照片变成艺术

deepart.io](https://deepart.io/) [## 神经风格|艺术风格的神经算法

用艺术风格的神经算法生成艺术品

neuralstyle.com](http://neuralstyle.com/) [## 皮卡佐——创造艺术

创造源源不断的生产质量的艺术。把照片变成画,或创造全新类型的图像…

www.pikazoapp.com](http://www.pikazoapp.com/) [## Instapainting

免费使用在线神经网络照片绘画生成器。

www.instapainting.com](https://www.instapainting.com/ai-painter) [## 神经泰勒

将您的视频/照片/GIF 变成艺术

neuralstyler.com](http://neuralstyler.com/)

JC Johnson 神经式代码的 Docker 实现

https://hub.docker.com/r/ffedoroff/neural-style/

音频纹理合成和风格转换

[## 音频纹理合成和风格转换

通过 Dmitry Ulyanov 和 Vadim Lebedev,我们提出了一种扩展的纹理合成和风格转换方法。

dmitryulyanov.github.io](https://dmitryulyanov.github.io/audio-texture-synthesis-and-style-transfer/) [## DmitryUlyanov/神经风格音频 tf

用于音频神经类型的神经类型音频 tf 张量流实现。

github.com](https://github.com/DmitryUlyanov/neural-style-audio-tf) [## DmitryUlyanov/神经风格音频火炬

神经风格音频火炬火炬实现音频神经风格。

github.com](https://github.com/DmitryUlyanov/neural-style-audio-torch) [## vadim-v-lebe dev/audio _ style _ transfer

在 GitHub 上创建一个帐户,为 audio _ style _ tranfer 开发做出贡献。

github.com](https://github.com/vadim-v-lebedev/audio_style_tranfer)

Reddit 线程

Mathematica(堆栈交换)

[## 如何实现神经风格转移?

在《艺术风格的神经算法》一文中。描述提取内容的过程…

mathematica.stackexchange.com](https://mathematica.stackexchange.com/questions/136704/how-to-implement-neural-style-transfer)

感谢您的阅读。

如果你想取得联系,你可以通过ahikailash1@gmail.com联系我

关于我:

我是 MateLabs 的联合创始人,我们在那里建立了 Mateverse ,这是一个 ML 平台,使每个人都可以轻松地建立和训练机器学习模型,而无需编写一行代码。

:最近,我出版了一本关于 GAN 的书,名为《生成性对抗网络项目》,书中涵盖了大部分广泛流行的 GAN 架构及其实现。DCGAN、StackGAN、CycleGAN、Pix2pix、Age-cGAN 和 3D-GAN 已在实施层面详细介绍。每种架构都有专门的一章。我已经使用 Keras 框架和 Tensorflow 后端用非常简单的描述性语言解释了这些网络。如果你正在开发 GANs 或者打算使用 GANs,请阅读一下,并在ahikailash1@gmail.com与我分享你的宝贵反馈

[## 生成对抗网络项目:使用 TensorFlow 构建下一代生成模型…

探索使用 Python 生态系统的各种生成性对抗网络架构关键特性使用不同的…

www.amazon.com](https://www.amazon.com/Generative-Adversarial-Networks-Projects-next-generation/dp/1789136679)

你可以从http://www . Amazon . com/Generative-Adversarial-Networks-Projects-next-generation/DP/1789136679https://www . Amazon . in/Generative-Adversarial-Networks-Projects-next-generation/DP/1789136679?FB clid = iwar 0 x2 pdk 4 ctxn 5 gqwmbbkigib 38 wmfx-sqcpbni 8k 9z 8 I-kcq 7 vwrpjxm 7 Ihttps://www . packtpub . com/big-data-and-business-intelligence/generative-adversarial-networks-projects?FB clid = iwar 2 otu 21 fam fpm 4 suh _ HJmy _ drqxovwjzb0k z3 zis bfb _ MW 7 inycqqv7 u 0 c

在 Python 备忘单中导入数据

原文:https://towardsdatascience.com/importing-data-in-python-cheat-sheet-712ba3638c78?source=collection_archive---------8-----------------------

有了这个 Python 备忘单,您将有一个方便的参考指南来导入您的数据,从平面文件到其他软件和关系数据库的本地文件。

在进行任何数据清理、争论、可视化之前,……您需要知道如何将数据放入 Python。如您所知,有许多方法可以将数据导入 Python,这也取决于您正在处理的文件。

然而,您将最经常使用 pandas 和 NumPy 库:pandas 库是数据科学家进行数据操作和分析的最受欢迎的工具之一,仅次于用于数据可视化的 matplotlib 和 NumPy,后者是构建 Pandas 的 Python 中科学计算的基础库。

在这份用 Python 导入数据的备忘单中,您会发现一些 NumPy 和 pandas 函数,以及用 Python 编程语言构建的函数,它们将帮助您快速获取 Python 中的数据!

本快速指南帮助您学习在 Python 中导入数据的基础知识,您将需要开始清理和整理您的数据!

找到小抄 这里

Python 备忘单中的导入数据将指导您完成在工作空间中获取数据的基本步骤:您不仅将学习如何导入文本文件等平面文件,还将了解如何从 Excel 电子表格、Stata、SAS 和 MATLAB 文件以及关系数据库等其他软件的本地文件中获取数据。除此之外,您将获得更多关于如何寻求帮助、如何导航文件系统以及如何开始探索数据的信息。

简而言之,用 Python 启动数据科学学习所需的一切!

你想了解更多吗?现在就开始免费学习 Python 课程中的导入数据,或者尝试我们的 Python Excel 教程

此外,不要错过我们针对数据科学的 Python 备忘单,或者我们社区中的许多其他内容!

最初发表于【www.datacamp.com】

在 Python 中导入数据

原文:https://towardsdatascience.com/importing-data-in-python-f6602add57b7?source=collection_archive---------15-----------------------

关于导入不同数据的不同方法的总结很少

最近,我在 DataCamp 完成了两门关于 Python 中数据导入的课程,我对可以用来获取数据的资源数量感到非常惊讶。在这里,我想总结所有这些方法,同时敏锐我的知识。我也认为对其他人来说这也是有用的。那么,我们开始吧。

有各种各样的文件可以用作数据源:

  • 平面文件— csv、txt、tsv 等。
  • 腌制的文件
  • excel 电子表格
  • SAS 和 Stata 文件
  • HDF5
  • 矩阵实验室
  • SQL 数据库
  • 网页
  • 蜜蜂

平面文件

平面文件——txt、CSV——很容易,使用 numpy 或 pandas 导入它们的方法很少。

numpy.recfromcsv —加载存储在逗号分隔文件中的 ASCII 数据。返回的数组是记录数组(如果 usemask=False,请参见 recarray)或被屏蔽的记录数组(如果 usemask=True,请参见 ma.mrecords.MaskedRecords)。

data = np.recfromcsv(file)

numpy.loadtxt —该函数旨在成为简单格式文件的快速阅读器。 genfromtxt 函数提供了更复杂的处理,例如,具有缺失值的行。

data = np.loadtxt('file.csv', delimiter=',', skiprows=1, usecols=[0,2])

numpy.genfromtxt —从文本文件中加载数据,缺失值按指定处理。更复杂的函数,有许多参数来控制您的导入。

data = np.genfromtxt('titanic.csv', delimiter=',', names=True, dtype=None)

有了 pandas,这就更容易了——一行代码就可以把你的文件放在一个数据帧中。还支持可选的迭代或者将文件分成块。

data = pd.read_csv(file, nrows=5, header=None, sep='\t', comment='#', na_values='Nothing')

泡菜

泡菜是什么鬼东西?它用于序列化和反序列化 Python 对象结构。python 中的任何对象都可以被腌制,以便保存在磁盘上。pickle 所做的是在将对象写入文件之前先“序列化”对象。Pickling 是一种转换 python 对象(list、dict 等)的方法。)转换成字符流。这个想法是,这个字符流包含在另一个 python 脚本中重建对象所需的所有信息。下面的代码将打印一个在某处创建并存储在文件中的字典——很酷,不是吗?

import pickle 
with open('data.pkl', 'rb') as file: 
       d = pickle.load(file)print(d)

擅长

pandas.read_excel 将 excel 表格读入 pandas 数据框架,并有许多自定义数据导入功能,这是前所未有的愉悦(听起来像电视广告:D)。但这是真的——这个函数的文档非常清楚,您实际上可以对这个 Excel 文件做任何您想做的事情。

df = pd.read_excel('file.xlsx', sheet_name='sheet1')

SAS 和 Stata

SAS 代表统计分析软件。SAS 数据集包含组织为观察值(行)和变量(列)表的数据值。要打开这种类型的文件并从中导入数据,下面的代码示例会有所帮助:

from sas7bdat import SAS7BDAT
with SAS7BDAT('some_data.sas7bdat') as file: 
     df_sas = file.to_data_frame()

Stata 是一个强大的统计软件,使用户能够分析、管理和生成数据的图形可视化。它主要由经济学、生物医学和政治学领域的研究人员用来检查数据模式。数据存储在。dta 文件,最好的导入方式是 pandas.read_stata

df = pd.read_stata('file.dta')

HDF5

分层数据格式(HDF)是一组文件格式(HDF4、HDF5),旨在存储和组织大量数据。HDF5 是一种独特的技术套件,能够管理极其庞大和复杂的数据集合。HDF5 简化了文件结构,仅包含两种主要类型的对象:

  • 数据集,是同质类型的多维数组
  • 组,是可以容纳数据集和其他组的容器结构

这就产生了真正的分层的、类似文件系统的数据格式。事实上,甚至可以使用类似 POSIX 的语法 /path/to/resource 来访问 HDF5 文件中的资源。元数据以用户定义的命名属性的形式存储在组和数据集上。然后可以使用数据集、组和属性构建更复杂的表示图像和表格的存储 API。

为了导入 HDF5 文件,我们需要 h5py 库。下面的代码样本让一切变得更简单,对我来说完全可以理解。

import h5py # Load file: 
data = h5py.File('file.hdf5', 'r') # Print the keys of the file 
for key in data.keys(): 
    print(key)# Now when we know the keys we can get the HDF5 group
group = data['group_name'] # Going one level deeper, check out keys of group 
for key in group.keys(): 
    print(key)# And so on and so on

矩阵实验室

很多人用 MATLAB 工作并将数据存储在。mat 文件。那些文件是什么?这些文件包含 MATLAB 工作空间中分配给它们的变量和对象的列表。不足为奇的是,它在 Python 中作为字典导入,其中的键是 MATLAB 变量和值——分配给这些变量的对象。为了读写 MATLAB 文件使用了 scipy.io 包。

import scipy.io 
mat = scipy.io.loadmat('some_project.mat')
print(mat.keys())

关系数据库

使用驱动程序连接到数据库,我们可以直接从那里获取数据。通常它意味着:创建连接、连接、运行查询、获取数据、关闭连接。一步一步来做是可能的,但是在熊猫身上,我们有一个很棒的功能来为我们做这件事,所以为什么要自寻烦恼呢?它只需要一个可以用 sqlalchemy 包创建的连接。下面是连接到 sqlite 数据库引擎并从中获取数据的示例:

from sqlalchemy import create_engine 
import pandas as pd 
# Create engine 
engine = create_engine('sqlite:///localdb.sqlite')# Execute query and store records in DataFrame 
df = pd.read_sql_query("select * from table", engine)

来自网络的数据

应该就此写一篇单独的文章,但我将强调几件事,至少知道从哪里开始。首先,如果我们有一个文件的直接 url,我们可以使用标准的pandas . read _ CSV/pandas . read _ excel函数在参数“file=”中指定它

df = pd.read_csv('https://www.example.com/data.csv', sep=';')

除此之外,要从 web 获取数据,我们需要使用 HTTP 协议,尤其是 get 方法(有很多这样的方法,但是对于导入,我们不需要更多)。包请求在这方面做得非常出色。要从 requests.get 收到的响应中访问文本,我们只需使用 method .text。

import requests 
r = requests.get('http://www.example.com/some_html_page') print(r.text)

r.text 会给我们一个包含所有 html 标签的网页——不是很有用,不是吗?但是有趣的事情开始了。我们有一个 BeautifulSoup 包,它可以解析 HTML 并提取我们需要的信息,在本例中是所有超链接(继续前面的例子):

from bs4 import BeautifulSoup
html_doc = r.text # Create a BeautifulSoup object from the HTML 
soup = BeautifulSoup(html_doc)# Find all 'a' tags (which define hyperlinks) 
a_tags = soup.find_all('a') # Print the URLs to the shell 
for link in a_tags: 
    print(link.get('href'))

应用程序接口

在计算机编程中,应用编程接口(API)是一组子例程定义、通信协议和用于构建软件的工具。一般来说,它是各种组件之间的一组明确定义的通信方法。有许多不同的 API,首先要做的是检查文档,但事实是几乎所有的 API 都以 JSON 格式返回数据。我们必须能够捕捉到结果。并且再次打包的请求会帮我们处理。(我们必须发送 HTTP GET 请求来从 API 获取数据)。

import requests 
r = requests.get('https://www.example.com/some_endpoint') # Decode the JSON data into a dictionary: 
json_data = r.json()# Print each key-value pair in json_data 
for k in json_data.keys(): 
    print(k + ': ', json_data[k])

正如我们所见,数据无处不在,我们必须知道获取数据的所有方法。至此,我的简短总结到此结束。希望它不仅对我有用。

将数据导入 R:数据科学项目的第一步

原文:https://towardsdatascience.com/importing-data-to-r-the-first-step-towards-your-data-science-project-a499c1dd0948?source=collection_archive---------12-----------------------

本文的目的是为您迈向数据科学项目的第一步提供快速查阅指南

在导入数据之前,数据科学家需要确定手头问题所需的相关数据源。数据收集和数据管理是任何数据相关项目成功的基石。每个企业都有一个专门的数据管理团队,他们不断努力识别不同的数据源,并提取、转换和加载数据(也称为 ETL)到一个名为数据仓库的中央存储库。

这个主题非常庞大,因此超出了本文的范围,但在我看来,这是一个非常重要的概念,任何有抱负的数据科学家都应该理解。

一旦确定了数据源,就可以将它导入到 R 中进行进一步的分析。R 中有多个函数专门针对您的数据文件类型(例如 CSV、TXT、HTML、XLSX 等)。)

将 TXT/CSV 文件导入到 R

使用基本函数

下表根据文件格式总结了将数据导入 R 的基本功能(即不需要额外安装软件包)。

上表中的每个函数都有一组默认参数,这使得它们与其他函数不同。这些论点是:

  • 表头:逻辑值。如果为 TRUE,该函数假定您的文件有一个标题行。如果不是这样,您可以添加参数 header = FALSE。
  • 填充:逻辑值。如果为 TRUE,长度不等的行将隐式添加空白字段。
  • sep: 字段分隔符。例如,“\t”用于制表符分隔的文件。
  • dec: 文件中用于小数点的字符。
  • stringsAsFactor 是另一个重要的参数,如果您不希望您的文本数据被转换为因子,应该将其设置为 FALSE。

小心!如果不显式设置上述参数,函数将采用默认的参数值。

在上述每个函数中,您还需要指定文件名(如果它在您的本地机器上)或 URL (如果文件位于 web 上)。

读取本地文件

要在您的计算机上查找文件,您可以遵循以下方法之一:

  • 使用命令setwd(" "将您的工作目录设置为指向包含您的文件的文件夹,然后在函数中提供文件名。
  • 使用导入功能内的 file.choose() 。这使您可以从您的机器上交互式地选择文件。

提示: read.table() 是一个通用函数,可以用来读取任何表格格式的文件,只要你按照自己的要求设置参数。数据将作为数据框导入。例如,如果您有一个包含由“|”分隔的数据字段的文本文件,您可以使用下面的命令:

使用 readr 软件包

这个包中的函数的使用方式与基本函数类似。 readr比基本函数快得多(超过 10 倍),因此,对于大型 TXT 或 CSV 文件非常有用。

  • delim :数据文件中分隔数值的字符。
  • col_names :可以是 TRUE(默认值)、FALSE 或指定列名的字符向量。如果为 TRUE,输入的第一行将用作列名。

与基本函数类似,在上述每个函数中,您还需要指定文件名(如果它在您的本地机器上,或者使用 file.choose()) 或 URL (如果文件位于 web 上)。

摘要

在本文中,我们了解了根据数据量、文件位置和数据分隔符将 TXT/CSV 文件导入 R 的不同方法。对于基本函数,不需要安装额外的包,而对于高级函数,您首先需要安装包(例如,在我们的例子中是 readr ),然后调用库来使用这些函数。

(首发@www.datacritics.com)

2018 年奥莱利 AI Conf 的印象和教训

原文:https://towardsdatascience.com/impressions-and-lessons-from-the-oreilly-ai-conf-2018-51f006be623a?source=collection_archive---------16-----------------------

AI superstar and the author’s personal hero, Peter Norvig, giving his keynote a the AI Conf 2018

我最近参加了奥莱利人工智能大会 2018 。我写这篇文章是为了分享我的经历,以及我从朋友和同事那里学到的一些东西。我评论了我认为是会议的主要主题:人工智能用于客户支持,人类在循环中以及人工智能在劳动力中的影响,深度学习(DL)和强化学习(RL),部署人工智能和自动机器学习(Auto-ML)的云。最后,我从演讲者那里收集了一些发人深省的话。

还有,这里是许多演示的幻灯片

会议的主题

人工智能客户支持

很大一部分实际上使用人工智能或人工智能将数据投入工作的公司都是在客户支持和定制或用户体验领域这样做的。这方面值得注意的例子有:

  • 优步,他利用深度学习开发了自然语言处理模型来分类和建议对客户门票的回应,这体现在他们的客户痴迷门票助手( COTA-v2 )中。
  • 美国电话电报公司,他开发了一个 LSTM 网络(一种递归神经网络)来产生一个模型,该模型描述了客户在与公司互动时将遵循的接触点(渠道)序列,以及这些互动的结果(他们是否购买了产品或服务,以及通过什么渠道购买的)。
  • 加州蓝盾公司,他们将他们部署的聊天机器人视为其全渠道客户服务战略不可或缺的一部分。然而,他们强调,最成功的聊天机器人不会自己工作。它们总是建立在良好的数据基础设施之上,包括开发良好的 API 和微服务。

https://www.theinquirer.net/inquirer/news/3032927/microsofts-xiaoice-bot-can-fool-humans-into-thinking-theyre-talking-to-a-person

人在回路中以及人工智能对劳动力的影响

有很多人说人工智能不应该(完全)取代人类,而是让他们的工作更高效、更强大、更令人满意。此外,至少目前,人类仍然有助于开发人工智能解决方案,这是因为一个简单的事实,即大多数专家知识包含在人类专家的大脑中,他们是唯一能够准确地对训练 ML 算法所需的数千个数据点进行昂贵的标记的人。

The main two axes of human vs. AI replacement / collaboration / augmentation.

还有中间的方法,比如主动学习,基于半监督方式的人与机器协作的思想。也就是说,让机器处理简单的例行案件,而将困难/边缘案件交给人类专家。当然,这在一些应用中是可行的,在这些应用中,不服从于自动决策的困难情况很容易识别,并且在所有情况中占少数。

深度学习和强化学习风靡一时

对于大多数读者来说,深度学习将自己定位为 ML 模型的事实上的架构可能不是什么新闻。也许是因为会议在加州举行,而且谷歌是会议赞助商之一,所以有大量关于 TensorFlow 的演示。顺便说一下,会后我和我的一些好朋友聊过,他们实际上是 DL 研究者,他们非常肯定 PyTorch 是运行 DL 实验的一个更好的框架。

Peter Norvig 做了一个精彩的主题演讲,讲述了近年来非数字逻辑专家在科学问题上的惊人应用。从天文学应用(引力透镜系外行星探测),到医学应用(用 CV 、评估心血管风险因素、高中生识别癌症、用基于 DL 的应用追踪奶牛、),一直到农业应用(识别生病的木薯植物)。

两位年轻的微软研究人员(Danielle Dean 和 Wee Hyong Tok)就深度学习中的“最佳秘密”进行了一次非常精彩的演讲。简而言之,迁移学习是一种利用深度网络中编码的知识来解决不同问题的技术,这些知识是由专家在大型数据集上精心训练的。举例来说,被训练来解决对象分类任务的深度网络可以用相对较少的工作来翻新,以解决另一个计算机视觉任务,例如纹理分类。这是通过将网络用作特征并仅在可能很小的数据集上重新训练最后一层来实现的。

The texture classification problem trained on a rather small dataset, but solvable via transfer learning!

云(几乎)是部署 AI/ML 解决方案的唯一地方

考虑到最先进的 ML 和 AI 解决方案所需的复杂硬件和软件配置,基于云的基础设施占优势就不足为奇了。在这方面最好的贡献之一是来自谷歌的 Levent Besik 的主题演讲,他在演讲中概述了该公司“使人工智能民主化,并使其对所有开发人员&用户变得容易和有用”的努力,无论他们在人工智能的技术或科学方面的专业知识程度如何。谷歌的产品包括三个抽象层次。在最底层,人们可以找到平台( ml-engine数据流dataproc 云服务)和库(TensorFlow、Keras、Spark)层,供想要“从零开始”创建解决方案的开发人员使用接下来是 AI 构建模块,它们本质上是成熟的 API,用于解决定义明确的问题,如语言翻译、语音转录或图像识别。在最高级别,我们可以找到模板解决方案,如产品推荐引擎或客户联络中心。

Amazon Web Services (AWS) 提供了一套服务和平台,用于开发和部署 ML,遵循相同的一般原则。然而,我感觉 AWS 产品的一些组件,比如亚马逊 Sagemaker 比谷歌的同类产品更成熟、更完整、总体设计更好。

The AWS ML Stack. Image reproduced with permission from AWS.

自动毫升

如果你是一名数据科学家或人工智能解决方案开发人员,在不久的将来,你也有可能被一台机器取代。Auto-ML 技术承诺从数据预处理到超参数调整、模型选择和部署,对 ML 模型构建的最复杂方面进行端到端的抽象和自动化。简而言之,Auto-ML 服务将数据集(可能是脏的,甚至不需要包含标签)作为输入,并输出已经部署的 ML 模型,包括 REST-API 和一切!

Google Cloud’s AutoML solution to generate image classification.

H2O 是另一家展示了这方面有趣发展的公司。

考虑到我认为自己是一个 ML 实践者(我讨厌数据科学家这个术语),我仍然对 Auto-ML 技术持怀疑态度就不足为奇了。很难想象一个完全自动化的过程能够成功地执行 ML 模型创建中所有困难的基于经验和直觉的决策。例如,巧妙的特征工程是一件特别难自动化的事情。然而,最近在 Auto-ML 方面的进展,如谷歌所展示的,他们已经成功地开发了设计其他神经网络的神经网络,这让我怀疑自己。

行情

最后,我会给你留下一些我觉得有趣、有启发性或发人深省的引言:

“我们做的许多人工智能的东西除了营销之外没有商业价值。”——本·泰勒

“80%的 ML 工作负载运行在 AWS 上”——Hagay lupes go,AWS。

“[在]2000 万开发人员中,100 万是数据科学家,1000 名是深度学习研究人员”——Levent Besik,谷歌云。

“一些公司有许多‘好想法’(供 AI/ML 使用),但无法量化价值。如果这个想法是从“这不是很酷吗……”开始的,这可能是个坏主意。”——本·泰勒

“82%的组织正处于考虑采用人工智能的某个阶段。进行试点非常容易,但部署起来却非常困难……高管们正专注于客户保持率和满意度,以及客户获取成本的降低。”— 马尼什·戈亚尔,IBM

“实施人工智能的障碍:缺乏熟练的资源或技术专长,监管限制。关于数据和信息使用的法律、安全、隐私问题。”— 马尼什·戈亚尔,IBM

“在未来,你将会看到负担得起的、智能的、云驱动的、个性化的假肢设备”——约瑟夫·西罗什,微软

“我们正在进入一个机器和软件可以分析的世界(看到以前总是隐藏的模式);优化(告诉飞机每英里飞行的高度,以获得最佳的燃油效率);预言(告诉你你的电梯什么时候会坏,在它坏之前修好它);定制(为您量身定制任何产品或服务)并数字化和自动化任何工作。这正在改变每一个行业。”《地球是平的》的作者汤姆·弗里德曼,纽约时报

“ML 所做的只是提供推论。科学的商业方法。业务人员很容易联想到推理…数据科学不太适合敏捷方法”——AWS 的 Carlos Escapa

The fourth waves of AI — Image taken from Sinovation ventures presentation.

用元学习和无可能性推理改进你的科学模型

原文:https://towardsdatascience.com/improve-your-scientific-models-with-meta-learning-and-likelihood-free-inference-2f904d0bd7fa?source=collection_archive---------17-----------------------

CMS Particle Detector in the LHC accelerator at CERN. Comparison between reality and simulation (with Geant4)

无似然推理的介绍和论文无似然推理的递归机器的提炼,发表于 NeurIPS 2018 元学习研讨会

亚瑟·佩萨与 安托万·魏汉高 共同撰写的文章

动机

提出新的科学理论通常有两种方式:

  • 从基本原理出发,推导出相应的定律,并提出实验预测以验证理论
  • 从实验出发,推断出解释你的数据的最简单的规律。

统计学和机器学习在科学中的作用通常与第二种推断有关,也叫归纳

例如,想象一下,你想在一个环境中模拟两个种群(比如狐狸和兔子)的进化。一个简单的模型是 Lotka-Volterra 微分方程:你考虑一个事件发生的概率,比如“一只狐狸吃了一只兔子”、“一只兔子出生了”、“一只狐狸出生了”等等。在很短的时间间隔内发生,根据这些概率推导出一组微分方程,通过求解这些方程来预测两个动物种群的进化。通过将您的预测与真实群体的进化进行比较,您可以推断出该环境中的最佳模型参数(概率)。

现代理论需要模拟才能与观测联系起来。它可以是一个简单的微分方程解算器,如洛特卡-沃尔泰拉模型,也可以是一个复杂的蒙特卡罗模拟器,如他们在粒子物理学中使用的那样。

通过将模拟的结果(即模型的预测)与真实数据进行比较,就有可能知道模型的正确性并相应地进行调整。如果这种在模型和实验数据之间来回转换的过程通常是手动完成的,那么任何机器学习从业者都会问的问题是:我们可以自动完成吗?我们能否建造一台机器,将可调整的模拟器和真实数据作为输入,并返回最符合真实数据的模拟器版本?

这是我们最近工作的目标[1],我们训练了一个神经网络来提出模拟器调整的最佳序列,以便逼近实验数据,利用了无似然推理和元学习领域的最新进展。

无似然推断

让我们用更正式的方式重新表述我们的问题。我们可以通过一个随机函数来建模一个模拟器(也叫生成模型),这个随机函数取一些参数 θ ,返回从某个分布中抽取的样本 x (所谓的模型)。

这种形式主义适用于任何包含随机性的科学理论,因为这在现代科学中非常常见(粒子碰撞受本质上随机的量子物理定律支配,生物过程或化学反应经常发生在嘈杂的环境中,等等)。).

实验数据存在于与模拟器输出相同的空间中的一组点中。推理的目标是找到参数 θ ,使得模拟器生成尽可能接近真实数据的点。

使用这种模拟器的科学领域包括:

  • 群体遗传学。型号: 聚结理论观察:一个当前种群的 DNA。参数:共同祖先的 DNA。
  • 高能粒子物理学。模型:粒子物理的标准模型观察:碰撞时探测器的输出。参数:标准模型的耦合常数(像粒子的质量或者不同力的强度)。
  • 计算神经科学。模型:霍奇金-赫胥黎模型。观察:一个神经元激活后电压的演变。参数:神经元的生物物理参数。

那么,在给定一些真实观测值的情况下,我们如何预测模拟器的参数呢?让我们考虑一个简单的高斯模拟器的例子,它采用一个向量 θ= σ)作为参数,并返回来自高斯分布𝓝(μ σ)的样本。

推断这种模拟器参数的经典方法被称为最大似然估计。在由 θ 参数化的概率分布 P 下,真实数据点 X 的可能性(模拟器)定义为 P(X| θ )。这意味着,如果大多数数据点位于高密度区域,则可能性很高。因此,模型的最佳参数通常是最大化真实数据可能性的参数。如果您不熟悉基于可能性的推理,您可以阅读这一对主题的精彩介绍

如果您可以明确访问模拟器的基本概率分布以及该分布的梯度,例如,您可以在参数空间中执行梯度下降,以最大化可能性并推断模型的最佳参数。

然而,许多现实生活模拟器有一个难以处理的可能性,这意味着显式概率分布太难计算(无论是分析还是数值)。因此,我们必须找到新的方法来推断最佳参数,而不使用似然函数或其梯度。

总之,我们有一个黑盒随机模拟器,它可以获取参数并从未知的概率分布中生成样本,以及我们能够与生成的数据进行比较的真实数据。我们的目标是找到引导模拟器生成尽可能接近真实数据的参数。该设置称为无可能性推理

我们如何进行无可能性推断?

让我们试着逐步想出一个解决问题的方法。我们可以做的第一件事是从一个随机参数开始,并模拟相应的数据:

Representation of the two spaces of interest. The true parameter (that we wish to infer) is the red point on the left. The real data correspond to the red cloud of points on the right. We start by choosing a random parameter θ (in gray on the left) and simulating the corresponding data points (in gray on the right)

通过这样做,我们可以看到我们生成的数据离真实数据有多远,但是我们无法知道在参数空间中该往哪里走。相反,让我们模拟几个参数:

为此,我们考虑参数空间中的一种分布,称为建议分布,并注明 q(θ|ψ)。如果我们选择 q 为高斯分布,我们将得到ψ=(μ σ)。第一步是随机初始化ψ。在上图中,为了简单起见,我们考虑了ψ=μ。然后,我们可以执行以下步骤,直到收敛:

  • 从方案分布中抽取几个参数:图中ψ周围有 4 个参数。
  • 从它们生成数据:右边的 4 个点云。
  • 选择一个好的前进方向。

第三步是艰难的。直观地说,您希望将ψ移向橙色和绿色参数,因为相应的预测(点的橙色和绿色云)与实际数据最接近。一组称为自然进化策略【3】的方法允许您将每个θ的表现(就其预测和实际数据之间的相似性而言)与参数空间中的一个方向联系起来。最近的一篇论文[4]例如利用生成敌对网络(GAN)给出的相似性度量来寻找最佳方向。尽管这些算法在一般情况下表现良好,但人们可能想知道,对于给定的模拟器,是否不可能找到更好的算法来利用该模拟器的特定特性。这就是元学习发挥作用的地方!

优化的元学习

元学习背后的理念是学习如何学习,在我们的案例中是学习优化过程。本文介绍的通过梯度下降学习通过梯度下降学习【2】的主要思想是在每次迭代中使用递归神经网络(RNN)来寻找最佳下降方向。下面是由随机初始化的 RNN 产生的点序列的例子:

每个下降方向都是随机的,产生的最后一点离最小值很远。在训练过程中,它应该学会利用每个点上的梯度信息,以便向最小值移动,给出如下结果:

那么如何训练它呢?生成许多你知道其最小值的函数,并要求 RNN 函数最小化序列最后一点与实际最小值之间的距离。

学习学习科学模型

在无似然推理的情况下,给定实际观测值和每一步生成的点云,RNN 应返回一系列建议参数ψ。

现在,和学习通过梯度下降学习一样,我们如何训练 RNN?这里,技巧是生成许多随机参数θ,并假设每个参数都是“真实参数”。然后,我们可以模拟生成的每个θ,并获得一组“真实观察”。然后,可以通过向 RNN 传递这些真实的观察结果,查看其最终的方案分布,并将其与真实参数(我们知道是因为我们生成了它)进行比较,从而对其进行训练。

让我们通过一个例子来澄清这一切。在下图中,提案分布以颜色表示(红色=高密度)。开始时,RNN 是随机初始化的,我们用第一个生成的真实参数θ(红色)对其进行评估。

然后我们可以把损失转嫁到 RNN 身上。对 200 个不同的“真实参数”重复这个过程后,应该是这样的:

我们可以看到,它已经学会了利用观测空间的信息向好的参数移动。

结果

我们在不同的玩具模拟器上评估了我们的模型,有些我们知道可能性,有些不知道。

非似然问题:泊松模拟器

Example of Poisson distributions for various parameters. Source: Wikipedia

第一个模拟器采用参数λ,并从泊松分布 P(λ)中抽取样本。这个例子的目的是看我们是否获得与最大似然估计相当的性能。结果如下:

Comparison of ALFI (Automatic Likelihood-Free Inference, the name of our model), to a maximum likelihood estimator (MLE). Those box-plots represent the distribution of the mean-squared errors between the true parameters and the expected value of the final proposal distributions.

我们可以看到,性能是可比的,即使我们没有给我们的模型访问的可能性。

无可能性问题:粒子物理模拟器

为了评估我们的模型在一个真正的无可能性的设置,我们考虑了一个简化的粒子物理模型,模拟了一个电子和一个正电子碰撞变成一个μ子和一个反μ子。

Feynman diagram of the simulated process

模拟器的参数是入射粒子的能量和费米常数,输出是两个μ子之间的角度。

为了评估我们的方法,我们比较了真实的观察值和由最后一个发现的参数生成的观察值。结果如下:

Results of our method on a simple particle physics model. Comparison of the real observations (angles of the produced particles) with the ones generated by our predicted parameter.

讨论

我们看到了什么是无可能性推理,以及元学习如何通过学习模拟器调整的最佳序列来解决这个问题,以使模型符合现实。

与大多数元学习模型一样,它的一个局限是难以训练。我们很难将我们的方法扩展到更复杂的模拟器,因为元训练需要大量的模拟器调用,这在现实世界中可能非常慢。然而,随着元学习领域的进步,我们希望出现新的方法来缓解这个问题,并使其更具可扩展性。

参考

[1] A. Pesah,A. Wehenkel 和 G. Louppe,无似然推理的递归机器 (2018),NeurIPS 2018 元学习研讨会

[2] M. Andrychowicz,M. Denil,S. Gomez,M. W. Hoffman,d .普法乌,T. Schaul,B. Shillingford,N. de Freitas,通过梯度下降学习梯度下降 (2016),NIPS 2016

[3] D. Wierstra,T. Schaul,T. Glasmachers,Y. Sun,J. Peter,J. Schmidhuber,自然进化策略 (2014),机器学习研究杂志(JMLR)。

[4] G. Louppe,J. Hermans,K. Cranmer,不可微模拟器的对抗性变分优化 (2017),arXiv 电子版 1707.07113

图像来源

利用文本挖掘改进 Airbnb 收益预测

原文:https://towardsdatascience.com/improving-airbnb-yield-prediction-with-text-mining-9472c0181731?source=collection_archive---------3-----------------------

Stunning views from an Airbnb I stayed at in Tasmania. Because no one wants to start reading an article with a graph.

介绍

Airbnb 是一个受欢迎的家庭共享平台,让世界各地的人们分享他们独特的住宿。对于潜在的主人来说,这可能是一个有利可图的选择,因为他们有空的度假屋、多余的房间甚至是多余的床。然而,新主人很难知道他们能挣多少钱,特别是,与宜家的普通公寓相比,他们心爱的配有设计师家具的顶层公寓的真正价值是什么?

我在 Udacity 完成机器学习 Nanodegree 的同时,抓住机会解决了这个问题,并为 Airbnb 房源的潜在收益建立了一个预测模型。该模型考虑了文本描述,以捕捉单个列表的丰富的定性模型。我也住在伦敦,自然决定在这里为 Airbnb 房源建模,以利用我的领域知识。

完成这个项目带来了一些有趣的见解,并激励我与其他数据科学爱好者分享这些成果。在这篇文章中,我简要介绍了项目工作流程,并以一种更方便读者的方式讨论了其中的见解。对于技术头脑,整个项目和支持代码可以在我的公共 GitHub 上找到。

这篇文章的其余部分分为四个主题:

  • 数据探索和操作:对数据集和描述性见解的讨论。
  • 文本挖掘列表描述:用于分析语料库和执行主题建模的管道。
  • 训练机器学习模型:特征工程,模型选择和调优。
  • 结果和可视化:可视化文本数据和见解。

数据探索和操作

获取数据

为了建立这个模型,我使用了 Airbnb 内部的提供的数据集,在那里,关于一个城市的 Airbnb 房源的公开信息已经被搜集并发布,供独立的非商业用途使用。这包括详细的列表信息,如房间数量、位置、文本描述、价格和评论数量。

Sample of the dataset.

具体来说,我使用了 2016 年 10 月 3 日至 2017 年 3 月 4 日期间伦敦房源的详细信息。主动列表被定义为在此期间至少被审核过一次的资产。兼职列表、不完整列表和新列表也将被删除。数据清理后,数据集有 9722 行和 16 列。

我们如何衡量潜在收益?

为了建立这个模型,收益率的概念被用作潜在未来收益的代理。收益的定义是一项资产一年的收入。Airbnb“三藩市模式”中基于价格、平均停留时间和审核率的收益计算使用:

平均停留时间价格评论数/月评论率***

在伦敦,假设平均停留时间为 3 晚。相对保守的 50%的点评率用于将点评数量转换为预计预订量。这种占用模式是预算和立法分析师办公室与 Airbnb 自己的估计之间的中间地带。

Distribution of Price (£), Reviews/Month, and Annual Yield (£)

分析价格、评论和最终收益的分布,伦敦的大部分房源价格低于 100 英镑/晚,每月收到 1-4 个预订。这表明入住率为 10-50%(取决于所选的点评率),AirBnb 主机平均每年为每份房源赚取 15,739 英镑。对于上四分位数的上市公司,这一数字高达 21,480 英镑。从这些数字来看,伦敦市长办公室报告的伦敦市中心住宅租金中位数为 7800 英镑,这表明积极管理的房源有着健康的溢价。

文本挖掘列表描述

现在,我们已经有了一个经过处理的数据集,并了解了我们试图预测的内容,我专注于将描述文本转换为对机器学习模型有用的特征。

Sample of listings description field.

在自然语言处理(NLP)行话中,描述文本的集合(左边的摘录)被称为语料库。这被转换成文档术语矩阵,其中每个列表是包含术语矩阵的文档。NLTK 和 gensim 包被用来完成这个任务。

为了减少术语的数量并关注每个文档中最重要的术语,删除了非英语和停用词。单词也是词汇化的,正则表达式标记器用于忽略非字母数字字符串。剩余的单词然后被转换成文档术语矩阵的单词包表示(单词 id、单词频率二元组的列表)。

这样,我们可以使用潜在狄利克雷分配(LDA) 来发现语料库中固有的主题,根据学习到的主题对语料库进行分类,并将它们用作回归模型的特征。

LDA 是一种生成贝叶斯推理模型,它将每个文档与主题的概率分布相关联,其中主题是单词的概率分布。这是一种分析大量文本的有效方法,也是一种更加人性化的主题建模方法。

主题模型在下面的主题间距离图中可视化,使用了出色的 pyLDAvis 包。在这种可视化中,圆圈的面积代表每个主题的流行程度,而右边条的长度代表某个术语在特定主题中的成员资格。例如,下面的主题 1 是最普遍的,在主题 1 中,与整个语料库中术语的总术语频率(蓝色和红色区域)相比,术语“步行”具有最高的估计术语频率(红色区域)。

Visit https://cdn.rawgit.com/joaeechew/udacity_capstone/481e85b0/lda.html for an interactive version

我选择将文档术语分成 3 个主题,因为它允许非常不同的主题没有重叠,这使得对每个列表进行分类是一个明智的选择。根据每个主题中的热门术语,列表的主题可以描述为:

  • 话题 1 —位置:这主要是关于“位置”、“步行”、“车站”和“中心”等词语的位置。这可能会吸引那些看重便利和交通便利的游客,比如第一次来伦敦的游客,他们希望最大限度地利用时间,游览伦敦市中心的所有景点。
  • 话题 2——奢华:这似乎是针对现代公寓,突出了“厨房”、“现代”、“私人”和“空间”等词。这可能会吸引预算较高的旅行者,他们希望住在一个舒适、有空间和隐私的地方(这在伦敦很贵!).
  • 主题 3——预算:这主要是关于更基本设施的词汇,如“床”、“房间”、“淋浴”和“清洁”。这可能会吸引那些不想花太多钱、正在寻找能保证基本便利设施的房源的预算旅行者。

然后,每个列表被分类到不同主题中的一个,该主题被用作训练模型的下一阶段的附加特征。

训练机器学习模型

在本节中,我们通过拟合处理过的数据集来训练机器学习算法。这是建立预测产量的最终模型的地方。

误差度量

在训练模型之前,我们首先要定义目标。这是将指导算法的内部权重的误差度量,允许模型通过寻找可能的最低误差来学习最佳预测函数。

在该模型中,均方误差(MSE)被用作精确度的度量。这测量实际产量和预测产量之间的误差平方的平均值。这个的数学公式是:

MSE 是回归模型的常用误差分数,允许直观地测量误差,即 10000 的 MSE 表示产量模型偏离 100(10000 的平方根)。它总是非负的,值越接近零越好。

型号选择

有了明确定义的误差度量,我们可以训练几个模型并选择性能最好的一个。在每个模型被训练和测试之后,结果被比较以检查更复杂的模型产生更好的分数。

这些模型遵循复杂的顺序:

  1. 线性回归:这是一种简单的线性方法,用于对数据集中的特征(如房间数量、入住客人数量)和目标“收益”变量之间的关系进行建模。
  2. 决策树:这是一个更复杂的基于树的模型,可以捕捉数据集中的非线性关系。这使用树表示,其中树的每个内部节点对应于数据集中的一个特征(例如房间数量),并且每个叶节点是一个类别标签(例如多于 2 个房间)。
  3. 随机 森林:这是从决策树集合中构建的最复杂的模型。这背后的原理是,一组弱学习者,即个体决策树,可以集合起来创建一个强学习者——随机森林。案例和要素的随机样本用于构建每棵单独的树,然后对组合预测进行平均,以返回森林的最终结果。

正如所料,随机森林模型产生了最好的分数。这表明数据集具有许多非线性关系,只能通过更复杂的模型来捕捉。

基于 LDA 主题模型的特征工程

虽然使用结构化数据构建预测模型是很好的第一步,但该项目的目标是确定文本挖掘是否可以用于提高产量预测。我处理这个问题的方法是通过比较不同模型在有和没有列出主题作为特征的情况下的得分。

在没有列出主题的情况下,报告的最佳结果是均方根误差为 14,579。在包含描述主题后,根 MSE 进一步降低到 14,560,从而提高了性能。在确认准确性增加后,使用 scikit-learn 的 GridSearchCV 调整最终参数,这进一步将均方根误差降低到 14,520。

虽然精度的提高看起来很小,但值得注意的是,随着精度的提高,挤出额外的几个点变得更加困难。

更重要的是,这验证了文本挖掘中存在有价值信息的假设,并证明了探索更多 NLP 技术来捕获这些信息的合理性。

使用基于树的模型的另一个优点是能够看到数据集中每个要素的重要性。这也揭示了使用列表主题的价值:

importance %                        feature
7      24.932740                       latitude
0      21.772927                   accommodates
8      19.621701                      longitude
6       7.702141                 minimum_nights
5       6.356207                   extra_people
1       4.105430                      bathrooms
4       3.769556                guests_included
2       2.893417                       bedrooms
13      2.039581      room_type_Entire home/apt
3       1.844825                           beds
**20      0.956488      topics_description_Luxury
19      0.914949    topics_description_Location
18      0.900623      topics_description_Budget**
12      0.477287            property_type_Other
11      0.442333            property_type_House
9       0.430975        property_type_Apartment
14      0.396504         room_type_Private room
10      0.152781  property_type_Bed & Breakfast
17      0.107925              bed_type_Real Bed
15      0.098952          room_type_Shared room

根据列表描述建模的主题具有 2.5%的综合重要性,这高于资产类型(1.3%)、床位数量(1.8%)或床位类型(0.11%)的重要性。这意味着非结构化描述文本包含比已经在关于 Airbnb 列表的结构化字段中捕获的更多的信息,并且这些信息可以用 NLP 技术来挖掘。

观想洞见

除了提高预测力度之外,还有从文本挖掘 Airbnb 房源描述中产生的进一步见解。通过绘制 3 个主题(位置、奢华、预算)的气泡图,可以将伦敦的 Airbnb 市场划分为不同类型的房源——每种房源都有不同的平均价格和预订率。

Each topic is plotted at the average of that segment while the size represents the number of listings.

就规模而言,“经济型”市场的房源数量最多,其次是“位置型”,而“豪华型”市场的房源数量最少。这是有道理的,人们会自然地期待有更多的“预算”类型的上市。

从平均价格来看,“地理位置”明显领先,排在第 162 位,其次是“豪华”,第 140 位,第 128 位。这表明位置仍然是房地产的王道,验证了古老的谚语“位置,位置,位置!”。

令人惊讶的是,尽管位置价格最高,但评论数量最多的却是“豪华”住宿。这是预订频率的一个代表,表明拥有一个“豪华”类型的列表甚至可能导致高于平均水平的收益。

Airbnb 用户通常是千禧一代,与其他年龄组相比,他们更愿意在旅行上花费,他们被住在别处没有的精品酒店的独特机会所吸引。这可以解释 Airbnb 上“奢华”住宿的流行。其他细分市场,如通常更关心“位置”的商务旅客,可能更喜欢住在酒店,而其他细分市场,如“经济型”旅客,则更喜欢有保证的设施和较低的价格的旅馆。

反思和下一步措施

这是一个具有挑战性和有趣的问题,在完成这个项目的过程中,我学到了很多东西。

NLP 很难,没有正确答案。处理文本数据带来了独特的挑战,这些挑战源于数据的定性性质。与结构化数据相比,它的形式更加自由,很少有“正确的答案”可供选择。例如,我决定选择相对较少的主题进行建模,这样可以保持主题的可管理性和独特性,足以形成不同的部分。然而,几乎每一个其他选择的背后都有一个合理的理由,这个理由会导致截然不同的结论。

可解释性很重要。在没有正确答案的情况下,能够以人性化的方式解释您的模型有助于建立对结果的信心。我选择使用 LDA 而不是其他主题建模算法(例如,非负矩阵分解)的原因之一是它提供了单词分布的可解释性。这有助于建立信心,我已经选择了合理数量的主题进行建模,并且最终的主题可以被赋予有洞察力的标签,提供有用的信息。

NLP 可以解锁非结构化文本中的信息。尽管无论哪种方式都会有有价值的学习,但证明文本挖掘可以用来提取有价值的信息尤其令人满意。由此产生的话题不仅改进了预测模型,还提供了对 Airbnb 市场不同细分市场的宝贵见解。

更多的非结构化数据?任何数据从业者可能都会同意,正确的数据很少以您想要的形式出现。能够从非结构化来源中提取信息为执行有用的分析打开了大门——即使数据可用性较低或者不是为您的预期目的收集的。展望未来,探索 Airbnb 中图像的使用以及深度学习算法是否可以从中提取有意义的信息将是一件有趣的事情。

Airbnb 团队已经分享了大量关于 Airbnb 数据的优秀作品,任何有兴趣阅读更多的人都应该阅读他们的一些帖子。希望通过分享我的作品,我能以我自己的一点点方式为之添砖加瓦。如前所述,没有正确的答案,我欢迎并鼓励下面评论中的任何反馈或想法!

我很幸运,在我感兴趣的领域找到了一个很棒的数据集。这个数据集是由 Airbnb 内部收集的,旨在回答 Airbnb 如何被用于并影响你所在的社区的问题。不管你的观点如何,这是一个重要的讨论,尤其是随着共享经济的兴起,我鼓励你通过访问他们的 网站 来加入这场对话。

报告全文及全部代码可在我的公众号GitHub上获得。

posted @ 2024-10-13 15:16  绝不原创的飞龙  阅读(7)  评论(0编辑  收藏  举报