TowardsDataScience 博客中文翻译 2016~2018(一百零三)

原文:TowardsDataScience Blog

协议:CC BY-NC-SA 4.0

通过构建推荐引擎提升星巴克的顾客体验——第 1 部分

原文:https://towardsdatascience.com/enhancing-starbucks-customer-experience-by-building-recommendation-engines-part-1-108ddd1d729?source=collection_archive---------20-----------------------

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

Photo by Hans Vivek on Unsplash

介绍

星巴克已经成为全球主要的咖啡公司,在全球拥有超过 15000 家门店,包括公司所有和特许经营的门店。这家公司能够实现这一壮举的主要原因之一是坚持不懈地关注客户体验。

给其客户最大的便利是星巴克卡的推出,后来扩展到星巴克 App。它支持无现金支付,因此根据观察,客户在支付过程中的等待时间可以显著减少。此外,星巴克应用程序使顾客能够收到促销优惠,这些优惠强调顾客在星巴克购买商品时的利益最大化。

向客户进行促销的挑战在于,每个客户对他们收到的优惠都有不同的偏好。如果他们收到他们不喜欢的报价,他们很可能不会尝试完成报价,尽管所有报价都对他们有利。随着人工智能(AI)和机器学习(ML)的进步,星巴克解决这个问题已经成为可能。

项目概述

推荐引擎是可以用机器学习来实现的系统之一。它能够预测顾客喜欢什么,不喜欢什么。因此,该系统将推荐更有可能被顾客购买的商品,并随后提高星巴克的商店业绩,例如销售额或顾客购买的商品数量。

在这个项目中,我基于 3 个数据集创建了两个推荐引擎,这些数据集是模拟星巴克奖励移动应用程序上的客户行为的模拟数据。第一个数据集(portfolio.json)包含向客户提供的促销。它包含 id、类型、持续时间、渠道和报价奖励。

第二个数据集(profile.json)是关于星巴克顾客的人口统计资料。它包含用户的年龄、性别、收入、id,以及这些用户何时成为星巴克应用程序的成员。第三个数据集(transcripts.json)包含第二个数据集中星巴克客户的交易记录。它有事件,告诉我们要约是否被接收、查看或完成,以及事件何时完成。它还有用户 id 和值,这是一个报价 id 或交易金额的字典,具体取决于记录。

问题陈述

这里的挑战是用这 3 个数据集创建一个推荐引擎。它必须考虑用户在接收报价时的偏好,以及用户是否喜欢被给予报价。我解决这个问题的方法是创建两个推荐引擎。第一种是基于聚类,第二种是基于用户相似度。

创建推荐引擎所涉及的任务有:
1 .清理给定的数据集,因为它包含许多 NaN 值和几个错误。
2。探索和可视化数据,以获得人口统计资料以及客户购买行为的良好画面。
3。用于创建推荐引擎的工程特征。生成的特征是出价-购买行为的比率数据。
4。基于特征创建客户细分。这是使用 KMeans 集群完成的。
5。创建基于聚类的推荐引擎。这需要一个用户 id,将用户 id 映射到该用户所属的集群,并推荐集群成员喜欢的前 3 个报价。
6。基于用户相似度创建推荐引擎。这需要一个用户 id,搜索与该 id 相似的 10 个用户,并推荐这 10 个用户最喜欢的 top 3。

如果你想看我用来创建这个推荐引擎的代码,点击这里的

韵律学

衡量一个推荐引擎的有效性并不容易。星巴克总是可以做一段时间的 A/B 测试。星巴克必须在应用程序中分配 cookies,将用户分为 2 组,控制组和实验组。对照组不会得到这个推荐引擎,实验组会得到。然后,星巴克需要观察不变指标和评估指标的差异。

不变度量
应该关注的不变度量有:
1。控制组和实验组的用户数量。这个至少应该差不多,接近五五开。
2。分配给每个组的 cookies 数量。

评价指标 应该关注的评价指标有:
1。平均交易金额。如果实验组有较高的平均交易量,推荐引擎可以被认为是有用的。
2。完成出价的百分比。如果实验组具有较高的完成要约百分比,则推荐引擎可以被认为是有用的。
3。来自要约的交易与收到要约的比率。对实验组来说越高越好。
4。非来自要约的交易与收到的要约的比率。实验组越低越好。

在评估推荐引擎的有效性时应该考虑的另一种方法是离线方法。这些方法应在将发动机部署到实验组的最初几个月后进行计算:

  1. 精准。这是一个衡量指标,表示在已经提供的促销中,用户喜欢的数量。
  2. 回忆一下。这是用户喜欢的推广优惠推荐给用户的比例。这两个指标应该最大化,因为它将告诉我们推荐引擎是否真正推荐了用户喜欢的项目,以及在推荐中,用户喜欢的促销报价的比例是多少。

数据探索

给出的 3 个数据集不干净。除了投资组合数据,在数据准备好用于创建推荐引擎之前,还有许多任务要做。

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

Fig 1. Portfolio Data

投资组合数据集非常简单。它包含促销渠道、难度、促销持续时间(天数)、优惠 id、优惠类型和完成促销的奖励。这里要打扫的东西不多,除了:
1。将渠道栏分为 4 个虚拟栏:网络、电子邮件、手机和社交。
2。创建一个字典,将 offer id 作为关键字和别名,以便简化以后 3 个数据集的合并。

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

Fig 2. Profile Data

要清理这个数据集,需要做几件事情。我检测到的是:
1。有一对夫妇已经 118 岁了
2。有几个人在性别和收入栏中缺少数据。这是一个问题,因为没有完整的数据,我不能创建一个良好的客户细分。我输入这个数据帧的方法是使用随机森林回归器和随机森林分类器创建机器学习模型。

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

Fig 3. Users with the Age of 118

从空值的数量和切片数据框的前几行判断,年龄为 118 岁的人没有记录性别和收入。这可能是因为注册问题或用户故意不填写栏。这使得为空值创建机器学习预测比我想象的要困难一些。

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

Fig 4. Transactions Data

交易数据在用于创建客户细分或推荐引擎之前也包含许多问题。事件列应该根据记录的事件进行分隔,包含优惠 id、奖励或交易金额的值列也应该进行分隔。

基于数据的最初外观,我决定在清理数据之前不创建数据可视化。主要原因是为了避免在问题仍然存在的情况下给读者错误的数据描述。

续第 2 部分

创建这一部分是为了让读者对数据有一个印象。第 2 部分将大量讨论这个项目的数据清理和特性工程阶段。如果有兴趣,请按照这个 链接

通过建立推荐引擎提升星巴克的顾客体验——第二部分

原文:https://towardsdatascience.com/enhancing-starbucks-customer-experience-by-building-recommendation-engines-part-2-7703cf332767?source=collection_archive---------25-----------------------

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

Photo by quan le on Unsplash

本系列的第二部分将关注项目的数据清理和特性工程方面。如果你还没有看过这个项目的介绍部分,我强烈建议你跟着这个 链接 读一读,让你对我在做的事情有一个更清晰的了解。

点击这里的,你可以看到我用来清理数据的代码。

数据清理

本项目中数据清理的目的是为数据探索和可视化提供更清晰的信息。它还使我能够为星巴克应用程序的用户创建客户细分,然后基于聚类构建推荐引擎。

我清理的第一个数据是投资组合数据,因为它是最快的。使用来自 pandas 的 get_dummies 和 stack 方法,我在数据框中添加了几列以使其更加清晰。我还通过将 duration 列乘以 24 来创建 duration hours 列,duration 列是特定报价的持续天数。生成的数据帧如下:

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

Fig 1. Cleaned Portfolio Data Frame

清理另外两个数据帧有点困难。我做的第一件事是合并个人资料和交易数据。然后,我为 event 列创建了 3 个虚拟变量,根据发生的事件,它们的值分别为 1 和 0。

接下来,我将 value 列分成 4 个新列。第一个是要约 id。这告诉我们用户在特定时间收到、查看或完成了哪个报价。当用户进行交易而不是接收、查看或完成要约时,该列的值为 NaN,而不是要约 id。第二栏是交易金额。当用户进行交易时,该列保存交易的金额。否则,它包含 NaN 的值。我创建的第三列是事务列。根据用户是否进行了交易,该列的二进制值为 1 或 0。最后一个是奖励成就栏。如果用户完成了交易,则该列保存通过完成报价获得的奖励金额。

在创建了这 4 列之后,我决定将 person 列映射到 user id,以便简化以后将 user id 输入到推荐引擎的过程。生成的数据帧的前几行如下:

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

Fig 2. Cleaned Combination of Profile and Transactions Data Frame

这些数据的一个主要问题是,它没有告诉我们交易是否是因为报价而发生的。如果是,哪一个报价导致了交易?为了回答这个问题,我创建了两个专栏。第一个是来自要约的交易,根据交易是由要约引起的(1)还是由要约引起的(0)来保存值 1 或 0。第二个是已查看的交易报价,其中包含导致交易的报价 id,或者如果在此期间没有交易或者交易不是由特定报价导致的,则为“无交易”。

我基于这些机制创建了这两个专栏:
1。如果发生交易,我会检查它是否是由报价引起的。
2。我假设,如果一个用户查看了一个优惠,然后做了一笔交易,甚至几笔交易(以实现促销目标),那么这些交易就是由该优惠引起的。
3。要检查交易是否是由查看的报价引起的,我需要检查报价是否在交易时间和报价的最大持续时间内被查看。然后,我查看第一次出现的报价,并将其指定为导致交易的报价。逻辑是,如果用户首先查看交易,如果报价仍在时限内,他们会尝试完成报价。尽管该用户可能会收到另一个报价,但他会尝试完成查看的第一个报价。
我还使用之前创建的字典将优惠 id 映射到优惠别名。生成的数据帧的前几行如下:

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

Fig 3. Data Frame with Transaction from Offer and Transaction Offer Viewed

完成此操作后,我将结果数据框与投资组合数据框合并,以创建一个主数据框。之后,我继续清理数据框,为没有输入性别、收入和正确年龄的用户创建年龄、性别和收入列的预测。

预测年龄、性别和收入

在预测这些列的值时,我做的第一步是将主数据帧分成两个数据帧。这很容易做到,因为填错年龄的用户也没有填写性别和收入栏。因此,很容易将数据框划分为用于创建模型的数据框和用于预测值的数据框。

接下来,我从预测年龄开始。我使用随机森林回归器创建了一个预测模型。预测变量(X)是模型创建数据框中的列,除了“性别”、“收入”、“时间”、“报价类型”、“报价 id”、“交易报价查看”、“年龄”、“报酬实现”。目标变量(Y)是“年龄”。我得到的结果是:

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

Fig 4. Random Forest Regression for Age Result

结果不太好。因此,我利用 scikit-learn 的网格搜索 CV 创建了一个更好的模型。结果如下:

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

Fig 5. Random Forest Regression with Grid Search CV for Age Result

我意识到模型改进了,虽然改进没那么多。我应该可以调整更多的超参数。然而,由于时间限制,我选择使用这个模型来预测用户的年龄。之后,我再次使用随机森林回归器创建了一个收入预测。结果是:

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

Fig 6. Random Forest Regression for Income Result

这个模型比年龄预测模型要好,尽管还远远不够。我决定也使用这个模型,并在未来对其进行微调,以创建更好的预测。预测的最后一栏是性别。我使用随机森林分类器来创建预测模型,平均 f1 值“微观”为 0.831。

我用这些模型来预测没有填写或填写错误的人的年龄、收入和性别。然而,我注意到一些预测是错误的。

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

Fig 7. Data Frame with Age, Gender, and Income Already Predicted

图 7 是用户 id 为 1 的数据帧的前几行。年龄、性别和收入是不同的,这意味着模型没有做出很好的预测。例如,用户 1 的年龄被预测为 61、44、45 或 46 岁。性别预测为 F 和 m。这是正常的,因为每个用户在查看、接收和完成要约以及进行交易时的列值是不同的。

为了解决这个问题,我创建了更多的计算:

  1. 平均年龄值,以获得每个用户的预测年龄
  2. 收入值的平均值,以获得每个用户的预测收入
  3. 性别值模式,以获得每个用户的预测性别

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

Fig 7. Data Frame for User ID 1 After Adjustment

从用户 1 的年龄、性别和收入都相同的意义上来说,生成的数据框看起来比前一个更好。

特征工程

酒店业的大多数企业依靠比率数据来评估他们的业绩。例如,餐馆更喜欢使用促销完成率和促销成本,而不是仅使用促销完成数。因此,我为数据框中的每个用户创建了这些比率数据。

然而,在设计这些特性之前,我注意到交易报价视图列有一些不正确的值。无论用户没有进行交易还是用户进行了非要约交易,值“无交易”都是相同的。因此,我决定更改值。如果事务列的值为 1,我将“无事务”更改为“事务 _ 非 _ 来自 _ 报价”。

在区分非要约交易和无交易后,我为“transaction_offer_viewed”列中的每个值创建了虚拟变量,根据用户执行的交易类型,这些变量的值为 1 或 0。使用这些专栏,我创建了一个用户人口统计和购买行为的数据框架。

该数据框架由 21 列组成,包含用户人口统计资料(年龄、收入、性别)和用户促销购买行为。例如,列“bogo1”是用户从星巴克应用程序查看“bogo1”促销后完成的交易数量。以下是数据框中的前几行和前几列:

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

Fig 8. User Demographic and Promotion Purchase Behavior Data Frame

使用这个数据框,我创建了 3 个比率数据作为特征。第一个是完成要约的百分比,即完成要约与收到要约的比率。第二个是来自出价比率的交易。这是来自要约的交易和收到的要约之间的比率。最后,我创造了交易,而不是从出价比率。顾名思义,这是不是来自要约的交易和收到的要约之间的比率。我决定使用收到的报价而不是查看的报价作为分母,因为发送报价的“成本”需要考虑,尽管它可能不是金钱的形式。可能是时间或带宽。因此,我认为使用收到的报价作为比率数据的分母是合适的。

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

Fig 9. The Snapshot of The Ratio Data Features

我做的最后一件事是用 0 填充数据帧中的 NaN 值,用 999 填充 inf 值。理由是,NaN 值源自比率数据,其分子值为 0,分母值为 0。例如,完成要约百分比的 NaN 值源自未完成要约且未收到要约的用户。因此,用 0 填充它是合适的。

至于 inf 值,它出现在交易中,而不是来自出价比率。例如,一个有 3 笔交易并收到 0 个报价的用户将产生 inf 值。因此,我分配了一个大值(999)来替换 inf 值。我相信这也是合适的,因为它代表了一个没有看到报价就进行交易的用户。

续第 3 部分

这一部分是为了让读者了解我是如何为这个项目进行数据清理的。下一部分将重点关注用户人口统计的数据可视化,并提供购买行为。如果你有兴趣,请跟随这个 链接

如果你有建议或批评,请不要犹豫,发表意见。我仍然是,并将永远是这个领域的学生。如果你有任何问题或想知道我对你的项目的看法,请随时联系我。

通过建立推荐引擎提升星巴克的顾客体验——第三部分

原文:https://towardsdatascience.com/enhancing-starbucks-customer-experience-by-building-recommendation-engines-part-3-45100f085daf?source=collection_archive---------26-----------------------

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

Photo by Omar Lopez on Unsplash

本系列的第三部分关注项目的数据可视化。如果你还没有看过这个项目的介绍部分,我强烈建议你跟着这个 链接 读一读,让你对我在做的事情有一个更清晰的认识。

点击这里 这个链接 可以看到我用来清理数据的代码。

数据可视化

在获得用户人口统计和购买行为数据框架后,我决定探索这些数据并创建可视化效果,以更清晰地了解星巴克应用程序用户的人口统计概况和购买行为。我创建了一个额外的列是“加入年”。这一栏是某个顾客成为星巴克 App 会员的那一年的数据。

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

Fig 1. Histogram of User Age

星巴克应用程序的大多数用户年龄在 40-80 岁之间。这个结果与分子网站的发现有些一致。然而,主要的区别是分子发现星巴克的大多数用户年龄在 25-34 岁之间。其余的水桶也差不多。

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

Fig 2. Histogram of User Income

大部分用户的收入在 50000–78000 之间。这是有道理的,因为根据维基百科的数据,美国很多人来自收入在 35000 到 75000 之间的中下阶层。这也告诉我们,星巴克的应用用户以中低阶层为主。这有点有趣,因为星巴克的商品价格并不便宜。与中下阶层相比,上层阶级的用户并不多。也许,这是因为星巴克应用程序中的大多数用户实际上是为了促销优惠。这就是为什么创建推广推荐引擎是星巴克的一个好策略。自从用户成为星巴克应用程序的成员后,看到每个用户的交易金额的分布对我来说也很有趣。

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

Fig 3. Histogram of User Transaction Amount

大多数用户的交易金额在 0-200 美元之间。这实际上有点令人担忧,因为从 2013 年开始就有用户成为星巴克应用程序的会员。这些用户可能选择不打开该应用程序,或者他们已经删除了该应用程序,或者他们可能对优惠不感兴趣。因此,看看更早加入的用户是否花费更多将是有趣的。

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

Fig 4. Bar Chart of Amount of Transaction based on User Join Year

从图 4 可以看出,2013 年加入的用户交易量最少,其次是 2014 年加入的用户。为了进一步调查,我创建了一个条形图,显示每年加入星巴克应用程序的会员数量。

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

Fig 5. Bar Chart of Number of Members per Year

在 2013 年和 2014 年,成员人数似乎仍然很低。这可以解释为什么交易量也很低。然而,他们也有更多的时间来积累交易。似乎这些用户停止了会员资格,或者他们对促销根本不感兴趣。这也是星巴克创建推荐引擎进行推广的一个很好的理由。现在,看看这些用户的平均支出也会很有趣。

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

Fig 6. Bar Chart of the Average Amount of Transaction Based on User Join Year

尽管所有在 2013 年加入的用户在星巴克购物花费最少,但每个用户的花费都比 2018 年加入的用户多得多。根据平均交易,2016 年加入的每个用户每次购买花费最多。这告诉我们那些较早加入的人的消费能力。虽然他们不在平均消费最高的前三名之列,但他们确实花了相当多的钱购买星巴克的产品。这也是创建推广推荐引擎的原因之一。接下来,我查看了用户的性别分布。

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

Fig 7. Bar Chart of Users’ Gender Distribution

星巴克的顾客大部分是男性,其次是女性顾客和其他。之后,看看哪种性别会受到晋升机会的影响会很有趣。

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

Fig 8. Bar Chart of Number of Transaction from Offer Viewed by Gender

令人惊讶的是,填写“其他”的人在看到报价后会做更多的交易。女性用户受他们所看的报价的影响最小。接下来,我将按性别查看完成的聘用百分比。然而,必须指出的是,差别并不大。

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

Fig 9. Bar Chart of Percentage of Offer Completed by Gender

同样,性别为“其他”的人完成了最多的提议。男性客户,虽然他们做更多的交易,但他们并不真正试图完成报价。看看哪个性别花钱最多会很有趣。

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

Fig 10. Bar Chart of the Amount of Transaction by Gender

不出所料,女性用户花费更多。因此,尽管他们的交易次数最少,但他们往往比男性用户花费更多的钱来完成更多的报价。似乎女性和其他人都比男性更喜欢升职。

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

Fig 11. Histogram of User Transaction from Offer Viewed

大多数用户在查看报价后有 0-7 次交易。这意味着,当他们看到一个报价时,他们之后会进行交易,甚至可能不止一次交易。这表明,大多数星巴克应用程序用户喜欢促销优惠,如果他们得到优惠,他们会采取行动。

结论

数据探索/可视化的结果非常有趣。此外,他们都表示,建立一个推荐系统的推广产品。

我发现有趣的几件事是:
1。尽管星巴克的商品并不便宜,但大多数应用程序用户来自中下阶层。
2。早些年加入的用户可能已经终止了他们的会员资格。
3。2016 年加入的用户平均交易金额最高
4。2017 年加入的用户交易量最大,尽管他们个人并不真的花很多钱。
5。女性用户倾向于花更多的钱来获得奖励。
6。大多数应用程序用户都是男性,但他们不会真的尝试去完成一个报价。

续第 4 部分

这一部分旨在让读者了解人口统计概况,并通过数据可视化展示星巴克应用用户的购买行为。下一部分将重点关注星巴克应用用户的细分以及基于聚类的推荐引擎和基于用户的推荐引擎的创建。有兴趣的话请关注这个 链接

如果您有建议或批评,请不吝赐教。我仍然是,并将永远是这个领域的学生。如果你有任何问题或想知道我对你的项目的看法,请随时联系我。

通过建立推荐引擎提升星巴克的顾客体验——第四部分

原文:https://towardsdatascience.com/enhancing-starbucks-customer-experience-by-building-recommendation-engines-part-4-f67b9a45fc19?source=collection_archive---------23-----------------------

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

Photo by Charles Koh on Unsplash

本系列的第四部分重点介绍该项目的机器学习部分,即聚类和构建推荐引擎。如果你还没有看过这个项目的介绍部分,我强烈建议你跟着这个 链接 读一读,让你对我在做的事情有一个更清晰的认识。

点击这里 这个链接 可以看到我用来清理数据的代码。

使聚集

在掌握了星巴克顾客的人口统计数据之后,我使用 KMeans 进行了聚类,将人口统计数据分成几个组。

方法论 在做聚类之前,我用标准的定标器来定标数据。这是必要的,因为有些列有很大的值,而有些列只有 0 和 1。换句话说,聚类中使用的每个特征的方差都有很大的差异。维护原始数据会导致方差较小的变量具有更大的权重。因此,产生的聚类将沿着具有更大方差的变量被分开。

实现
选择多少个簇(k)的方法我用的是肘法。我选择查看几个集群,从 1 到集群中使用的变量数量,并对每个数量执行 KMeans 集群。然后,我计算了每个 k 的误差平方和(SSE)分数,并将分数附加到一个列表中。后来,我创建了一个线图来查看肘部,并选择它作为进一步分析中使用的聚类数。

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

Fig 1. SSE vs K on KMeans Clustering

在 KMeans 的结果中没有明显的拐点,除了 SSE 从第 7 类到第 16 类稍微大幅度的减少。因此,我决定用 16 个聚类来拟合和预测哪个用户属于哪个聚类。我创建了一个可视化工具来绘制每个集群的用户数量,如下所示:

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

Fig 2. The Number of Users per Cluster

从图 2 中可以看出,每个集群的用户数量的分布变化很大。例如,属于集群 2 的用户超过 4000 个,属于集群 8 的用户不到 10 个。这可能影响推荐引擎的质量,因为大多数用户将被映射到集群 2、3、7 或 16。

接下来,我根据聚类对用户人口统计数据框进行分组。我最终得到了聚类数据框。这是数据框的前几行和前几列的快照。如果你想看完整的数据帧,请查看我的 github。

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

Fig 3. The Cluster Data Frame

描述第 3 集群 1。第一个群体是年龄在 49 岁左右、收入在 58052 美元左右的男性客户。比起其他类型的报价,他们更喜欢 bogo4。收到报价后,他们会进行大约 2-3 笔交易。他们也做适度交易,而不是从收到的报价开始,这表明他们确实喜欢在星巴克喝咖啡。
2。第二个群体也是年龄在 49 岁左右、收入在 56291 美元左右的男性客户。比起其他类型的优惠,他们更喜欢打折。收到报价后,他们只做 1 笔左右的交易。然而,他们确实在星巴克购物,尽管他们没有收到任何报价。我认为,这些客户并不真正忠诚。他们想什么时候买咖啡就什么时候买,而且他们更喜欢打折。
3。第三个群体是年龄在 60 岁左右、收入在 78141 美元左右的男性顾客。比起其他类型的报价,他们更倾向于 bogo1。收到报价后,他们会进行大约 2-3 次交易,尽管他们没有收到报价,他们也会购买咖啡。这个集群类似于第一个集群,只是他们的收入更高。

基于聚类的推荐引擎

在对客户进行细分后,我创建了第一个推荐引擎,它是基于集群的推荐引擎。本质上,该引擎将依赖于之前创建的集群,并且基于将被给予推荐的用户所属的集群中的用户的喜好来创建推荐。

方法论 在创建推荐引擎之前,我必须考虑几件事情,它们是:
1。哪些用户不喜欢被给予优惠。
2。创建集群促销矩阵。
3。检查用户属于哪个集群。
4。推荐该用户所属集群喜欢的前 3 个优惠,并获取这些优惠 id 的列表。
5。如果用户属于不喜欢被提升的用户群,我不会给任何推荐。
6。如果用户是新的,我会给所有用户最喜欢的前 3 名。

实现 我创建了一个数据帧,包含用户 id 和交易非来自报价比率,以找出哪些用户不喜欢被给予报价。如果比率大于所有比率的平均值,我会认为用户是不喜欢优惠或促销的用户。

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

Fig 4. The ‘Offer or Not’ Data Frame

之后,我创建了一个集群提升矩阵的数据框架。我使用的变量只有折扣和买一送一变量。我决定不包含信息变量,因为无论如何,信息应该提供给每个用户。生成的数据帧的前几行如下:

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

Fig 5. Cluster-promotion Matrix

我使用这个数据框架和“提供或不提供”数据框架来创建推荐引擎。我创建了一个函数,它执行以下操作:
1。获取用户 id
2 的输入。如果用户 id 在“提供或不提供”数据框中,不要推荐任何东西。
3。如果用户 id 不在“提供或不提供”数据框中,请检查该用户属于哪个集群。
4。使用集群促销矩阵,推荐集群中用户最喜欢的前 3 个产品。
5。将优惠别名转换为原始优惠 id。

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

Fig 6. Recommendation Result

推荐引擎设法推荐与用户 293 在同一集群中的用户喜欢的前 3 个提议。至于用户 20,由于该用户属于“提供或不提供”数据框,所以引擎不推荐任何东西。新用户将得到如图 6 所示的 3 个报价。

细化
总而言之,这个推荐引擎做了我想做的事情。然而,我确实有一个问题。如上所述,集群包含不同数量的用户。因此,大多数用户仅被放在 4 个集群中。这可能会导致推荐引擎给出不太个性化的报价。因此,我决定创建一个基于用户的推荐引擎。

基于用户的推荐引擎

我心目中的基于用户的推荐引擎更加个性化。基本上,该引擎依赖于在用户推广矩阵中找到相似的用户,并根据这些相似的用户最喜欢的优惠提供推荐。

方法论 创建基于用户的推荐引擎的方法论与基于聚类的推荐引擎非常相似。我不得不考虑几件事。哪些用户不喜欢被给予优惠。
2。创建用户推广矩阵。
3。检查与要推荐的用户 id 最相似的前 10 名用户。
4。推荐 10 个最相似的用户最喜欢的前 3 个优惠。
5。如果用户属于不喜欢被提升的用户列表,我不会给任何推荐。
6。如果用户是新的,我会给所有用户最喜欢的前 3 名。

实施 我仍然使用“提供或不提供”数据框架来找出哪些用户不喜欢被提供服务。因此,我没有为此创建新的数据框。我做的第一件事是创建用户推广矩阵。我使用了用户统计数据框架,以用户 id 作为索引,以折扣和买一送一作为变量。

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

Fig 7. User-promotion Matrix

我用这个来计算每个用户之间的相似度。我使用的方法是计算要给出推荐的用户 id 的相应行的转置矩阵和用户矩阵数据帧的转置矩阵之间的点积。通过对用户相似度列表+ 1 的负值执行 argsort 来获得最相似的用户。最后要做的事情是从列表中删除用户 id。

为了创建推荐引擎,我创建了一个函数,它执行以下操作:
1。获取用户 id
2 的输入。如果用户 id 在“提供或不提供”数据框中,不要推荐任何东西。
3。如果用户 id 不在“提供或不提供”数据框中,则查找与该用户 id 最相似的 10 个用户。
4。使用用户推广矩阵,推荐 10 个最相似的用户最喜欢的前 3 个产品。
5。将优惠别名转换为原始优惠 id。

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

Fig 8. User-based Recommendation Result

与之前的推荐引擎相比,基于用户的推荐引擎为用户 id 293 创建了略有不同的推荐。其中两项建议是相同的。对于用户 id 3,引擎不推荐任何内容,因为该用户属于“提供或不提供”数据框架。对于新用户,该算法产生的结果与它是同一算法产生的结果相同。

评估和验证

两个推荐引擎都成功地实现了我想要的结果:

  1. 它识别哪些用户不应该被给予优惠
  2. 它根据相似用户/集群的偏好推荐报价
  3. 它为新用户推荐最受欢迎的产品。

评估推荐引擎不是一件容易的事情。星巴克必须花费一定的时间对这些系统进行 A/B 测试。这些指标已经在本文的引言部分提到过了(第 1 部分)。然而,在组的数量上有微小的变化。星巴克应该有 3 组,1 个对照组和 2 个实验组来测试这些推荐引擎。

Justification 个人认为基于用户的推荐引擎比基于聚类的好。它更加个性化和多样化,因为我们可以决定我们想要使用多少类似的用户。此外,正如我在上面提到的,每个集群中的用户数量是相当不同的。最大数量在 4000 以上,最小数量只有 8 个。这将影响基于集群的推荐引擎,因为集群中的用户越多,偏好的方差就越高。

结论

反射
给定的数据集确实很难,从这个意义上说,数据集中只有基本的特征。大多数时候,酒店行业的企业倾向于依赖比率作为衡量标准,所以我必须用这些数据集创建这些比率数据。然而,这并不是最困难的部分。

这个项目最困难的部分是清理数据,特别是输入年龄、性别和收入。我可以使用统计数据估算这些变量,如年龄均值、性别模式和收入均值/中值。但是,结果会不太准确。当我决定为这个项目创建一个推荐引擎时,我意识到获得最准确的数据是至关重要的,尤其是对于集群部分。因此,我决定使用机器学习来估算缺失/错误的值。这对我来说并不容易,尤其是因为我必须确定插补的顺序。我决定先用 R2 分数高的那个。

输入数据后,创建推荐引擎的过程并不困难。然而,推荐引擎的问题是,它应该在现实生活中进行测试,看看它是否工作得很好。我将需要进一步学习,以深化我在机器学习和推荐引擎方面的知识,以确保我可以构建出色的性能模型。

改进
可以做几个改进来构建更好的推荐引擎。其中一些是:

  1. 建立一个更好的随机森林模型来预测年龄、性别和收入。R2 分数不够高,MSE 分数也不够低。如果我有更多的时间,我可以调整超参数,或者尝试使用其他算法,如 Ada Boost,甚至神经网络。
  2. 建立一个更好的推荐引擎,将促销信息分为明星、主力、谜题和狗。我会用菜单工程的概念,实施分类推广。明星促销将是那些低成本和高交易量产生。主力将是那些成本高、交易量大的公司。难题将是那些成本低,但产生的交易量低。狗将是那些具有高成本和低交易量的狗。通过这样做,我们可以一直推广明星或益智推广,调整主力推广以及摆脱狗推广。当然,我需要额外的数据来做到这一点。

如果您有建议或批评,请不吝赐教。我仍然是,并将永远是这个领域的学生。如果你有任何问题或想知道我对你的项目的看法,请随时联系我。

机器学习中的集成学习|入门

原文:https://towardsdatascience.com/ensemble-learning-in-machine-learning-getting-started-4ed85eb38e00?source=collection_archive---------2-----------------------

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

使用各种不同的模型比只使用一种模型要可靠得多。在单个集合上一起工作的几个模型的集合称为集合。这种方法被称为集成学习。

投票

您可以使用不同的算法训练您的模型,然后集成它们以预测最终输出。比方说,你使用随机森林分类器,SVM 分类器,线性回归等。;模型相互竞争,并通过使用来自sklearn.ensembleVotingClassifier类投票选出最佳性能。

硬投票是从集合中选择一个模型,通过简单多数投票进行最终预测,以确保准确性。

软投票只能在所有分类器都能计算出结果的概率时进行。软投票通过平均各个算法计算出的概率来达到最佳结果。

代码:

VotingClassifier的准确率一般高于个体分类器。确保包含不同的分类器,这样容易出现类似错误的模型不会聚集错误。

装袋和粘贴

您可以在数据集的各种随机子集上使用单个模型,而不是在单个数据集上运行各种模型。替换随机抽样称为装袋,简称自举汇总。如果很难在脑海中想象,就想象一下忽略数据集中的几个随机条目,用其余的条目建模。在粘贴的情况下,同样的过程适用,唯一的区别是粘贴不允许为相同的预测器多次采样训练实例。

代码:

bootstrap=True参数指定装袋的用途。对于粘贴,将参数更改为bootstrap=False

如果分类器可以计算其预测的概率,则 BaggingClassifier 会自动执行软投票。这可以通过检查你的分类器是否有一个predict_proba()方法来验证。

装袋通常比粘贴效果好得多。

袋外评估

当对训练集执行 Bagging 时,只有 63%的实例包括在模型中,这意味着有 37%的实例分类器以前没有见过。这些可以像交叉验证一样用于评估。

要使用这个功能,只需在前面示例中的BaggingClassifier类中添加一个oob_score = True参数。

密码

到目前为止,只对实例进行了采样。对于包含大量要素的数据集,还有其他方法。

随机补丁和随机子空间

随机补丁对训练实例和特征进行采样。

BaggingClassifier()中设置某些参数可以为我们实现这一点:

随机子空间保留除样本特征之外的所有实例。

这是通过以下方式实现的:

随机森林

决策树的集合是一个随机森林。Random Forests 在内部执行装袋。随机森林创建几棵树,有时是几千棵树,并为给定数据集计算最佳可能模型。随机森林算法不是在分割节点时考虑所有特征,而是从所有特征的子集中选择最佳特征。这用较高的偏差换取了较低的方差,从而产生了更好的模型。

代码:

参数:n_estimators是森林中树木的极限数量。max_leaf_nodes用于设置端节点的最大数量,这样算法就不会深入单个特征并过度拟合模型(阅读关于决策树的详细解释)。n_jobs指定您的计算机要使用的内核数量;-1值意味着所有最大可能的核心。

使用网格搜索可以通过改变参数值来改进模型。

adaboost 算法

虽然 AdaBoost 技术的函数数学相当令人生畏,但其原理相当简单。首先,您选择一个基础分类器,它对给定的集合进行预测。记下错误分类的实例。错误分类实例的权重增加。用更新的权重在训练集上训练第二分类器。

简单来说,运行分类器并进行预测。运行另一个分类器来拟合以前错误分类的实例并进行预测。重复进行,直到所有/大部分训练实例都适合为止。

AdaBoost 使用的不是决策树,而是一个决策树桩,它是一个带有max_depth = 1的决策树,即一个决策节点和两个叶节点的树。AdaBoost 中的n_estimators参数设置决策树桩的数量。

密码

Scikit-learn 使用 Adaboost 的多类版本 SAMME ( 使用多类指数损失函数的阶段式加法建模)。如果预测器可以计算概率(有predict_proba()方法),Scikit Learn 使用 SAMME。R ( R 代表实数)依赖于概率,不容易过度拟合。

在过度拟合的情况下,尝试调整你的基本估计量。

梯度推进

与 AdaBoost 类似,梯度提升也适用于添加到集成中的连续预测模型。梯度提升不是像 AdaBoost 那样更新训练实例的权重,而是使新模型适合残差。

简而言之,使模型适合给定的训练集。计算残差,该残差成为新的训练实例。一个新的模型在这些上面被训练等等。选择所有模型的总和来进行预测。

密码

学习率参数缩小了每棵树的贡献。在learning_raten_estimator s 之间有一个折衷。降低 learning_rate 的值会增加集合中的树的数量。这叫做收缩。将估计数增加到一个较大的值可能会使模型过拟合。见早停。必须仔细监控这种权衡。

XGBoost

XGBoost 是一种最新、最受欢迎且功能强大的梯度增强方法。XGBoost 没有在叶节点上做出艰难的是或否的决定,而是为做出的每个决定分配正值和负值。所有的树都是弱学习者,并且提供比随机猜测稍好的决策。但是总的来说,XGBoost 的表现非常好。

密码

XGBoost 可以处理树和线性模型。我建议阅读 XGBoost 文档,了解更多的参数调优选项。

XGBoost 最近获得了很大的人气,并被用在了最获胜的 Kaggle 竞赛模型中。这是您数据科学工具箱中的强大工具。

下次见。建议编辑和改进。保持(机器)学习。

本文的灵感来自 Aurélien Géron 的书《使用 Scikit-Learn 和 TensorFlow 进行机器学习:构建智能系统的概念、工具和技术》。我已经尽力把事情简单化了。希望有帮助。在这里得到这本书:http://shop.oreilly.com/product/0636920052289.do

使用 Scikit-learn 构建集成学习模型

原文:https://towardsdatascience.com/ensemble-learning-using-scikit-learn-85c4531ff86a?source=collection_archive---------3-----------------------

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

Ensemble Learning (image credit)

集成学习使用多个机器学习模型来尝试对数据集进行更好的预测。集成模型的工作原理是在数据集上训练不同的模型,并让每个模型单独进行预测。这些模型的预测然后在集合模型中组合,以做出最终预测。

每种模式都有其优点和缺点。集成模型可以通过组合单个模型来帮助隐藏单个模型的弱点。

在本教程中,我们将使用投票分类器,其中集成模型通过多数投票进行预测。例如,如果我们使用三个模型,并且它们预测目标变量为[1,0,1],集合模型做出的最终预测将是 1,因为三个模型中的两个预测为 1。

我们将使用三种不同的模型来输入我们的投票分类器:k-最近邻、随机森林和逻辑回归。我们将使用 Python 中的 Scikit-learn 库来实现这些方法,并在我们的示例中使用糖尿病数据集。

注:集合模型也可用于回归问题,其中集合模型将使用不同模型的平均输出或加权平均值进行最终预测。

读入训练数据

第一步是读入我们将用作输入的数据。对于这个例子,我们使用糖尿病数据集。首先,我们将使用 Pandas 库读入数据。

import pandas as pd#read in the dataset
df = pd.read_csv(‘data/diabetes_data.csv’)#take a look at the data
df.head()

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

接下来,我们来看看我们有多少数据。我们将在数据帧上调用“shape”函数,查看数据中有多少行和多少列。行表示患者的数量,列表示特征(年龄、体重等)的数量。)在每个患者的数据集中。

#check dataset size
df.shape

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

将数据集分成输入和目标

现在让我们把数据集分成输入(X)和目标(y)。我们的输入将是除“糖尿病”之外的每一列,因为“糖尿病”是我们将试图预测的。因此,“糖尿病”将是我们的目标。

我们将使用 pandas 的‘drop’函数从数据帧中删除列‘diabetes ’,并将其存储在变量‘X’中。

#split data into inputs and targets
X = df.drop(columns = [‘diabetes’])
y = df[‘diabetes’]

将数据集拆分为训练和测试数据

现在,我们将数据集分为训练数据和测试数据。训练数据是模型将从中学习的数据。测试数据是我们将用来查看模型在看不见的数据上表现如何的数据。

Scikit-learn 有一个我们可以使用的名为“train_test_split”的函数,它使我们可以很容易地将数据集分成训练和测试数据。

from sklearn.model_selection import train_test_split#split data into train and test sets
X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.3, stratify=y)

“train_test_split”接受 5 个参数。前两个参数是我们之前分开的输入和目标数据。接下来,我们将“测试大小”设置为 0.3。这意味着所有数据的 30%将用于测试,剩下 70%的数据作为模型学习的训练数据。

将“分层”设置为 y 会使我们的训练分割表示 y 变量中每个值的比例。例如,在我们的数据集中,如果 25%的患者患有糖尿病,75%的患者没有糖尿病,将“分层”设置为 y 将确保随机拆分有 25%的糖尿病患者和 75%的非糖尿病患者。

构建模型

接下来,我们必须建立我们的模型。我们建立的每个模型都有一组我们可以调整的超参数。调整参数是指通过一个过程来为您的模型找到最佳参数以提高准确性。我们将使用网格搜索来寻找每个模型的最佳超参数。

网格搜索通过在我们指定的参数范围内多次训练我们的模型来工作。这样,我们可以用每个超参数值测试我们的模型,并找出最佳值以获得最佳精度结果。

k-最近邻

我们将建立的第一个模型是 k-最近邻(k-NN)。k-NN 模型通过获取一个数据点并查看“k”个最接近的标记数据点来工作。然后,给数据点分配“k”个最接近点中大多数的标签。

例如,如果 k = 5,3 个点为“绿色”,2 个点为“红色”,那么所讨论的数据点将被标记为“绿色”,因为“绿色”占大多数(如上图所示)。

代码如下:

import numpy as np
from sklearn.model_selection import GridSearchCV
from sklearn.neighbors import KNeighborsClassifier#create new a knn model
knn = KNeighborsClassifier()#create a dictionary of all values we want to test for n_neighbors
params_knn = {‘n_neighbors’: np.arange(1, 25)}#use gridsearch to test all values for n_neighbors
knn_gs = GridSearchCV(knn, params_knn, cv=5)#fit model to training data
knn_gs.fit(X_train, y_train)

首先,我们将创建一个新的 k-NN 分类器。接下来,我们需要创建一个字典来存储我们将为‘n _ neighbors’测试的所有值,这是我们需要调优的超参数。我们将测试“n_neighbors”的 24 个不同值。然后,我们将创建我们的网格搜索,输入我们的 k-NN 分类器、我们的超参数集和我们的交叉验证值。

交叉验证是指数据集被随机分成“k”个组。其中一组用作测试集,其余的用作训练集。该模型在训练集上被训练,并在测试集上被评分。然后重复该过程,直到每个唯一的组都被用作测试集。

在我们的例子中,我们使用 5 重交叉验证。数据集被分成 5 组,模型被训练和测试 5 次,因此每组都有机会成为测试集。这就是我们将如何对使用每个超参数值运行的模型进行评分,以查看“n_neighbors”的哪个值给了我们最好的分数。

然后,我们将使用“适合”功能来运行网格搜索。

现在,我们将使用“best_estimator_”函数将最佳 k-NN 模型保存到“knn_best”中,并检查“n_neighbors”的最佳值。

#save best model
knn_best = knn_gs.best_estimator_#check best n_neigbors value
print(knn_gs.best_params_)

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

对于接下来的两个模型,我将不再赘述,因为有些部分重复了 k-NN 模型的构建。

随机森林

我们要建立的下一个模型是一个随机森林。随机森林本身被认为是一个集合模型,因为它是一组决策树的集合,这些决策树组合在一起形成一个更精确的模型。

代码如下:

from sklearn.ensemble import RandomForestClassifier#create a new random forest classifier
rf = RandomForestClassifier()#create a dictionary of all values we want to test for n_estimators
params_rf = {‘n_estimators’: [50, 100, 200]}#use gridsearch to test all values for n_estimators
rf_gs = GridSearchCV(rf, params_rf, cv=5)#fit model to training data
rf_gs.fit(X_train, y_train)

我们将创建一个新的随机森林分类器,并设置我们想要调整的超参数。“n_estimators”是我们的随机森林中的树的数量。然后,我们可以运行网格搜索来找到最佳数量的树。

就像之前一样,我们将保存我们的最佳模型并打印最佳的“n_estimators”值。

#save best model
rf_best = rf_gs.best_estimator_#check best n_estimators value
print(rf_gs.best_params_)

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

逻辑回归

我们的最后一个模型是逻辑回归。即使它的名字中有“回归”,逻辑回归也是一种分类方法。这个更简单,因为我们不会调优任何超参数。我们只需要创建和训练模型。

from sklearn.linear_model import LogisticRegression#create a new logistic regression model
log_reg = LogisticRegression()#fit the model to the training data
log_reg.fit(X_train, y_train)

现在,让我们检查所有三个模型在测试数据上的准确性分数。

#test the three models with the test data and print their accuracy scoresprint(‘knn: {}’.format(knn_best.score(X_test, y_test)))
print(‘rf: {}’.format(rf_best.score(X_test, y_test)))
print(‘log_reg: {}’.format(log_reg.score(X_test, y_test)))

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

从输出可以看出,逻辑回归是三者中最准确的。

投票分类器

现在我们已经建立了三个独立的模型,是时候建立我们的投票分类器了。

代码如下:

from sklearn.ensemble import VotingClassifier#create a dictionary of our models
estimators=[(‘knn’, knn_best), (‘rf’, rf_best), (‘log_reg’, log_reg)]#create our voting classifier, inputting our models
ensemble = VotingClassifier(estimators, voting=’hard’)

首先,让我们把我们的三个模型放在一个叫做“估值器”的数组中。接下来,我们将创建投票分类器。它需要两个输入。第一个是我们三个模型的估计数组。我们将投票参数设置为 hard,这告诉我们的分类器通过多数投票进行预测。

现在,我们可以将我们的集成模型拟合到我们的训练数据中,并根据我们的测试数据对其进行评分。

#fit model to training data
ensemble.fit(X_train, y_train)#test our model on the test data
ensemble.score(X_test, y_test)

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

厉害!我们的集成模型比单独的 k-NN、随机森林和逻辑回归模型表现得更好!

就是这样!您现在已经构建了一个集合模型来组合各个模型!

感谢阅读!本教程的 GitHub 库(jupyter 笔记本和数据集)可以在这里找到。

如果你想了解我的机器学习内容,请关注我:)

机器学习中的集成方法:它们是什么,为什么使用它们?

原文:https://towardsdatascience.com/ensemble-methods-in-machine-learning-what-are-they-and-why-use-them-68ec3f9fef5f?source=collection_archive---------0-----------------------

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

合奏方法,它们是什么?集成方法是一种机器学习技术,它结合了几个基本模型,以产生一个最佳预测模型。为了更好地理解这个定义,让我们回到机器学习和模型构建的最终目标。随着我深入到具体的例子和为什么使用系综方法,这将变得更有意义。

我将主要利用决策树来概述集成方法的定义和实用性(然而,重要的是要注意,集成方法不仅仅适用于决策树)。

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

决策树基于一系列问题和条件来确定预测值。例如,这个简单的决策树决定了一个人是否应该在户外活动。该树考虑了几个天气因素,给定每个因素要么做出决定,要么提出另一个问题。在这个例子里,每次阴天的时候,我们都会在外面玩。但是,如果下雨了,一定要问有没有风?如果刮风,我们就不玩了。但是如果没有风,把鞋带系紧,因为我们要出去玩。

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

决策树也可以用同样的格式解决定量问题。在左边的树中,我们想知道是否投资商业房地产。是写字楼吗?一个仓库?一栋公寓楼?经济条件好?经济条件差?一项投资会有多少回报?这些问题都是用这个决策树来回答和解决的。

当制作决策树时,有几个因素我们必须考虑:我们根据什么特征做决策?将每个问题分类为是或否答案的阈值是什么?在第一个决策树中,如果我们想问自己是否有朋友一起玩呢?如果我们有朋友,我们每次都会玩。如果不是,我们可能会继续问自己关于天气的问题。通过添加一个额外的问题,我们希望更好地定义是和否类。

这就是集合方法派上用场的地方!集成方法允许我们考虑决策树的样本,计算在每次分裂时要使用的特征或要问的问题,并基于样本决策树的聚合结果做出最终预测,而不是仅仅依赖于一个决策树并希望我们在每次分裂时做出正确的决策。

集合方法的类型

  1. ing,或BootstrapAGGregating。 BAGG ing 得名于它将BBt【17】ot【19】agregion 组合成一个系综模型。给定一个数据样本,抽取多个自举子样本。在每个自举子样本上形成决策树。在形成每个子样本决策树之后,使用算法在决策树上聚集以形成最有效的预测器。下图将有助于解释:**

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

Given a Dataset, bootstrapped subsamples are pulled. A Decision Tree is formed on each bootstrapped sample. The results of each tree are aggregated to yield the strongest, most accurate predictor.

2.随机森林模式。随机森林模型可以被认为是 BAGG 模型,只是有一点小小的改动。当决定在哪里拆分以及如何决策时,袋装决策树具有可供选择的全部处置特征。因此,尽管引导样本可能略有不同,但数据在很大程度上会在每个模型中的相同要素处中断。相反,随机森林模型根据随机选择的要素来决定在哪里进行分割。随机森林模型实现了一定程度的区分,而不是在每个节点的相似特征处进行分割,因为每棵树都将基于不同的特征进行分割。这种程度的差异提供了一个更大的集合,因此产生了一个更准确的预测。请参考图片,以便更好地理解。

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

与装袋类似,自举子样本是从更大的数据集中提取的。在每个子样本上形成决策树。然而,决策树在不同的特征上被分割(在该图中,特征由形状表示)。

概括起来

任何机器学习问题的目标都是找到一个能够最好地预测我们想要的结果的单一模型。集成方法不是制作一个模型并希望这个模型是我们能够制作的最好/最准确的预测器,而是考虑无数的模型,并对这些模型进行平均以产生一个最终模型。值得注意的是,决策树并不是集成方法的唯一形式,而是当今数据科学中最流行和最相关的形式。

使用 Keras 组装 ConvNets

原文:https://towardsdatascience.com/ensembling-convnets-using-keras-237d429157eb?source=collection_archive---------0-----------------------

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

编辑:2019 年 2 月

微小的代码更改。改进的体验篇Jupyter 笔记本版。

介绍

在统计学和机器学习中,集成方法使用多种学习算法来获得比单独从任何组成学习算法获得的性能更好的预测性能。与统计力学中的统计集成(通常是无限的)不同,机器学习集成仅由一组具体的有限备选模型组成,但通常允许在这些备选模型中存在更加灵活的结构。【1】

使用集成的主要动机是找到一个假设,该假设不一定包含在构建它的模型的假设空间内。从经验上看,当模型之间存在显著差异时,集成往往会产生更好的结果。【2】

动机

如果你看看一场大型机器学习比赛的结果,你很可能会发现,最好的结果是由一群模型而不是单个模型实现的。例如,ILSVRC2015 上得分最高的单一模型架构排在第 13 位。第 1-12 名由不同的组合占据。

我还没有看到关于如何在集成中使用多个神经网络的教程或文档,所以我决定就这个主题制作一个实用指南。

我将使用 Keras ,特别是它的功能 API ,重新创建三个小型 CNN(与 ResNet50、Inception 等相比)。)来自相对知名的论文。我将在 CIFAR-10 训练数据集上分别训练每个模型。【3】然后,将使用测试集对每个模型进行评估。之后,我会把这三个模型放在一个合奏中进行评估。预计集成在测试集上将比集成中单独的任何单个模型表现得更好。

有许多不同类型的合奏;堆叠就是其中之一。它是更一般的类型之一,理论上可以代表任何其他的系综技术。堆叠包括训练一个学习算法来组合其他几个学习算法的预测。【1】为了这个例子,我将使用一种最简单的叠加形式,它包括取集合中模型输出的平均值。由于平均不需要任何参数,所以不需要训练这个集合(只需要它的模型)。

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

This post’s ensemble in a nutshell

准备数据

首先,导入依赖项。

from keras.callbacks import History
from keras.callbacks import ModelCheckpoint, TensorBoard
from keras.datasets import cifar10
from keras.engine import training
from keras.layers import Conv2D, MaxPooling2D, GlobalAveragePooling2D, Dropout, Activation, Average
from keras.losses import categorical_crossentropy
from keras.models import Model, Input
from keras.optimizers import Adam
from keras.utils import to_categorical
from tensorflow.python.framework.ops import Tensor
from typing import Tuple, List
import glob
import numpy as np
import os

我使用 CIFAR-10,因为相对容易找到描述在这个数据集上运行良好的架构的论文。使用一个流行的数据集也使得这个例子很容易重现。

在这里,数据集被导入。训练和测试图像数据都被归一化。训练标签向量被转换成独热矩阵。不需要转换测试标签向量,因为它不会在训练中使用。

def load_data() -> Tuple [np.ndarray, np.ndarray, 
                          np.ndarray, np.ndarray]:
    (x_train, y_train), (x_test, y_test) = cifar10.load_data()
    x_train = x_train / 255.
    x_test = x_test / 255.
    y_train = to_categorical(y_train, num_classes=10)
    return x_train, x_test, y_train, y_testx_train, x_test, y_train, y_test = load_data()

该数据集由来自 10 个类别的 60000 幅 32x32 RGB 图像组成。50000 幅图像用于训练/验证,另外 10000 幅用于测试。

print('x_train shape: {} | y_train shape: {}\nx_test shape : {} | y_test shape : {}'.format(x_train.shape, y_train.shape,                                                                                      x_test.shape, y_test.shape))

>>>x _ train shape:(50000,32,32,3) | y_train shape: (50000,10)

>>>x _ 测试形状:(10000,32,32,3)| y _ 测试形状:(10000,1)

由于所有三个模型都使用相同形状的数据,因此定义一个供每个模型使用的输入图层是有意义的。

input_shape = x_train[0,:,:,:].shape
model_input = Input(shape=input_shape)

第一个模型:ConvPool-CNN-C

我要训练的第一个模型是 ConvPool-CNN-C。

这个模型非常简单。它有一个共同的模式,即几个卷积层之后是一个池层。对于这个模型,有些人唯一不熟悉的是它的最后几层。不是使用几个完全连接的层,而是使用一个全局平均池层。

这里有一个全局池层如何工作的简要概述。最后一个卷积层Conv2D(10, (1, 1))输出对应十个输出类的 10 个特征图。然后,GlobalAveragePooling2D()层计算这 10 个特征地图的空间平均值,这意味着它的输出只是一个长度为 10 的矢量。之后,对该向量应用 softmax 激活。如您所见,这种方法在某种程度上类似于在模型顶部使用 FC 层。你可以在 Network paper 中阅读更多关于全球池层及其在 Network 中的优势。【5】

需要注意的重要一点是:没有激活函数应用于最后一个Conv2D(10, (1, 1))层的输出,因为这个层的输出必须首先通过GlobalAveragePooling2D()

def conv_pool_cnn(model_input: Tensor) -> training.Model:

    x = Conv2D(96, kernel_size=(3, 3), activation='relu', padding = 'same')(model_input)
    x = Conv2D(96, (3, 3), activation='relu', padding = 'same')(x)
    x = Conv2D(96, (3, 3), activation='relu', padding = 'same')(x)
    x = MaxPooling2D(pool_size=(3, 3), strides = 2)(x)
    x = Conv2D(192, (3, 3), activation='relu', padding = 'same')(x)
    x = Conv2D(192, (3, 3), activation='relu', padding = 'same')(x)
    x = Conv2D(192, (3, 3), activation='relu', padding = 'same')(x)
    x = MaxPooling2D(pool_size=(3, 3), strides = 2)(x)
    x = Conv2D(192, (3, 3), activation='relu', padding = 'same')(x)
    x = Conv2D(192, (1, 1), activation='relu')(x)
    x = Conv2D(10, (1, 1))(x)
    x = GlobalAveragePooling2D()(x)
    x = Activation(activation='softmax')(x)

    model = Model(model_input, x, name='conv_pool_cnn')

    return model

实例化模型。

conv_pool_cnn_model = conv_pool_cnn(model_input)

为了简单起见,每个模型都使用相同的参数进行编译和训练。使用 20 个时段,批次大小为 32(每个时段 1250 步),对于三个模型中的任何一个来说,似乎足以达到一些局部最小值。随机选择 20%的训练数据集用于验证。

NUM_EPOCHS = 20def compile_and_train(model: training.Model, num_epochs: int) -> Tuple [History, str]: 

    model.compile(loss=categorical_crossentropy, optimizer=Adam(), metrics=['acc']) 
    filepath = 'weights/' + model.name + '.{epoch:02d}-{loss:.2f}.hdf5'
    checkpoint = ModelCheckpoint(filepath, monitor='loss', verbose=0, save_weights_only=True,
                                                 save_best_only=True, mode='auto', period=1)
    tensor_board = TensorBoard(log_dir='logs/', histogram_freq=0, batch_size=32)
    history = model.fit(x=x_train, y=y_train, batch_size=32, 
                     epochs=num_epochs, verbose=1, callbacks=[checkpoint, tensor_board], validation_split=0.2)
    weight_files = glob.glob(os.path.join(os.getcwd(), 'weights/*'))
    weight_file = max(weight_files, key=os.path.getctime) # most recent file return history, weight_file

使用单个 Tesla K80 GPU 在一个时期内训练这个模型和下一个模型大约需要 1 分钟。如果您使用 CPU,训练可能需要一段时间。

_, conv_pool_cnn_weight_file = compile_and_train(conv_pool_cnn_model, NUM_EPOCHS)

该模型达到了约 79%的验证准确率。

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

ConvPool-CNN-C validation accuracy and loss

通过计算测试集的错误率来评估模型。

def evaluate_error(model: training.Model) -> np.float64: pred = model.predict(x_test, batch_size = 32)
    pred = np.argmax(pred, axis=1)
    pred = np.expand_dims(pred, axis=1) # make same shape as y_test
    error = np.sum(np.not_equal(pred, y_test)) / y_test.shape[0]   

    return errorevaluate_error(conv_pool_cnn_model)

> > > 0.2414

第二种模式:全 CNN-C

下一个 CNN,ALL-CNN-C,出自同一篇论文。【4】这款和上一款很像。实际上,唯一的区别是使用跨距为 2 的卷积层来代替最大池层。再次注意,在Conv2D(10, (1, 1))层之后没有立即使用激活功能。如果在该层之后立即使用 ReLU 激活,模型将无法训练。

def all_cnn(model_input: Tensor) -> training.Model:

    x = Conv2D(96, kernel_size=(3, 3), activation='relu', padding = 'same')(model_input)
    x = Conv2D(96, (3, 3), activation='relu', padding = 'same')(x)
    x = Conv2D(96, (3, 3), activation='relu', padding = 'same', strides = 2)(x)
    x = Conv2D(192, (3, 3), activation='relu', padding = 'same')(x)
    x = Conv2D(192, (3, 3), activation='relu', padding = 'same')(x)
    x = Conv2D(192, (3, 3), activation='relu', padding = 'same', strides = 2)(x)
    x = Conv2D(192, (3, 3), activation='relu', padding = 'same')(x)
    x = Conv2D(192, (1, 1), activation='relu')(x)
    x = Conv2D(10, (1, 1))(x)
    x = GlobalAveragePooling2D()(x)
    x = Activation(activation='softmax')(x)

    model = Model(model_input, x, name='all_cnn')

    return modelall_cnn_model = all_cnn(model_input)
_, all_cnn_weight_file = compile_and_train(all_cnn_model, NUM_EPOCHS)

该模型收敛到约 75%的验证准确性。

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

ALL-CNN-C validation accuracy and loss

由于两个模型非常相似,错误率不会相差太多。

evaluate_error(all_cnn_model)

>>>0.260900000000002

第三种模式:网络中的网络 CNN

第三个 CNN 是网络中的网络。【5】这是一篇 CNN 的文章,介绍了全局池层。它比前两个型号小,因此训练起来更快。最后卷积层后没有relu

我没有在 MLP 卷积层中使用多层感知器,而是使用了 1x1 内核的卷积层。这样,需要优化的参数更少,训练速度更快,我可以获得更好的结果(当使用 FC 层时,无法获得高于 50%的验证精度)。该论文指出,mlpconv 层所应用的功能相当于普通卷积层上的级联跨通道参数池,而普通卷积层又相当于具有 1×1 卷积核的卷积层。如果我对架构的解释不正确,请纠正我。

def nin_cnn(model_input: Tensor) -> training.Model:

    #mlpconv block 1
    x = Conv2D(32, (5, 5), activation='relu',padding='valid')(model_input)
    x = Conv2D(32, (1, 1), activation='relu')(x)
    x = Conv2D(32, (1, 1), activation='relu')(x)
    x = MaxPooling2D((2,2))(x)
    x = Dropout(0.5)(x)

    #mlpconv block2
    x = Conv2D(64, (3, 3), activation='relu',padding='valid')(x)
    x = Conv2D(64, (1, 1), activation='relu')(x)
    x = Conv2D(64, (1, 1), activation='relu')(x)
    x = MaxPooling2D((2,2))(x)
    x = Dropout(0.5)(x)

    #mlpconv block3
    x = Conv2D(128, (3, 3), activation='relu',padding='valid')(x)
    x = Conv2D(32, (1, 1), activation='relu')(x)
    x = Conv2D(10, (1, 1))(x)

    x = GlobalAveragePooling2D()(x)
    x = Activation(activation='softmax')(x)

    model = Model(model_input, x, name='nin_cnn')

    return modelnin_cnn_model = nin_cnn(model_input)

这个模型的训练速度要快得多——在我的机器上,每个时期 15 秒。

_, nin_cnn_weight_file = compile_and_train(nin_cnn_model, NUM_EPOCHS)

该模型实现了约 65%的验证准确率。

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

NIN-CNN validation accuracy and loss

这个模型比其他两个更简单,所以错误率有点高。

evaluate_error(nin_cnn_model)

> > > 0。0.3164000000000001

三模型集成

现在这三个模型将被组合成一个整体。

这里,所有三个模型都被重新实例化,并且加载了最佳保存的权重。

CONV_POOL_CNN_WEIGHT_FILE = os.path.join(os.getcwd(), 'weights', 'conv_pool_cnn_pretrained_weights.hdf5')
ALL_CNN_WEIGHT_FILE = os.path.join(os.getcwd(), 'weights', 'all_cnn_pretrained_weights.hdf5')
NIN_CNN_WEIGHT_FILE = os.path.join(os.getcwd(), 'weights', 'nin_cnn_pretrained_weights.hdf5') conv_pool_cnn_model = conv_pool_cnn(model_input)
all_cnn_model = all_cnn(model_input)
nin_cnn_model = nin_cnn(model_input)

conv_pool_cnn_model.load_weights(CONV_POOL_CNN_WEIGHT_FILE)
all_cnn_model.load_weights(ALL_CNN_WEIGHT_FILE)
nin_cnn_model.load_weights(NIN_CNN_WEIGHT_FILE)

models = [conv_pool_cnn_model, all_cnn_model, nin_cnn_model]

集合模型定义非常简单。它使用所有先前模型之间共享的相同输入层。在顶层,集成通过使用Average()合并层计算三个模型输出的平均值。

def ensemble(models: List [training.Model], model_input: Tensor) -> training.Model:

    outputs = [model.outputs[0] for model in models]
    y = Average()(outputs)

    model = Model(model_input, y, name='ensemble')

    return model

正如所料,集合的错误率比任何单一模型都低。

evaluate_error(ensemble_model)

> > > 0.2049

其他可能的合奏

为了完整起见,我们可以检查由两个模型组合组成的集合的性能。其中两个模型的错误率低于单一模型。

pair_A = [conv_pool_cnn_model, all_cnn_model]
pair_B = [conv_pool_cnn_model, nin_cnn_model]
pair_C = [all_cnn_model, nin_cnn_model]pair_A_ensemble_model = ensemble(pair_A, model_input)
evaluate_error(pair_A_ensemble_model)

>>>0.211999999999999

pair_B_ensemble_model = ensemble(pair_B, model_input)
evaluate_error(pair_B_ensemble_model)

>>>0.228199999999999

pair_C_ensemble_model = ensemble(pair_C, model_input)
evaluate_error(pair_C_ensemble_model)

> > > 0.2447

结论

重申一下引言中说过的话:每个模型都有自己的弱点。使用集成背后的原因是,通过堆叠表示关于数据的不同假设的不同模型,我们可以找到不在构建集成的模型的假设空间中的更好的假设。

通过使用非常基本的集合,与在大多数情况下使用单一模型相比,实现了更低的错误率。这证明了组合的有效性。

当然,当使用系综来完成机器学习任务时,有一些实际的考虑要记住。由于集成意味着将多个模型堆叠在一起,这也意味着每个模型的输入数据都需要向前传播。这增加了需要执行的计算量,从而增加了评估(预测)时间。如果你在研究或比赛中使用系综,增加评估时间并不重要。然而,在设计商业产品时,这是一个非常关键的因素。另一个考虑因素是最终模型尺寸的增加,这也可能是在商业产品中整体使用的限制因素。

你可以从我的 GitHub 获得 Jupyter 笔记本源代码。

参考

  1. 集成学习。(未注明)。在维基百科里。检索于 2017 年 12 月 12 日,来自https://en.wikipedia.org/wiki/Ensemble_learning
  2. D.Opitz 和 R. Maclin (1999 年)流行的集合方法:实证研究,第 11 卷,第 169-198 页(可在http://jair.org/papers/paper614.html获得)
  3. 从微小图像中学习多层特征 ,Alex Krizhevsky,2009。
  4. arXiv:1412.6806 v3【cs。LG]
  5. arXiv:1312.4400 v3【cs。NE]

熵是不确定性的度量

原文:https://towardsdatascience.com/entropy-is-a-measure-of-uncertainty-e2c000301c2c?source=collection_archive---------0-----------------------

八个性质,几个例子和一个定理

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

假设你正在医生办公室的候诊室里与三个病人交谈。他们三人都刚刚完成了一项医学测试,经过一些处理后,得出两种可能的结果之一:疾病要么存在,要么不存在。让我们假设我们正在与好奇和面向数据的个人打交道。他们已经提前研究了他们特定风险状况的概率,现在急于找出结果。

患者 A 知道,从统计学上来说,他有 95%的可能性患有所述疾病。对于患者 B 来说,被确诊患病的概率是 30%。相比之下,病人 C 面临着 50/50 的可能性。

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

Uncertainty in the waiting room

我想着重谈一个简单的问题。在其他条件相同的情况下,三个病人中哪一个面临最大程度的不确定性?

我认为答案是明确的:病人 c。他不仅正在经历“许多不确定性”。他正在经历的是在这种情况下最大程度的不确定性:一个戏剧性的医学版的掷硬币游戏。

与病人 a 相比,当然,整体情况看起来相当严峻,但至少这个病人对他的医疗前景没有多少不确定性。

从直觉上讲,我们能说病人 B 什么呢?也许她的情况属于“中间某处”?

这就是熵产生的原因。将一种情况描述为“中间的某个地方”对于候诊室的谈话来说可能已经足够好了,但是对于机器学习的目的来说,这种描述肯定太粗糙了。

测量不确定性

熵允许我们对生活中最紧迫的问题之一做出精确的陈述和进行计算:不知道事情会如何发展。

换句话说,熵是对不确定性的一种度量。

(它也是一种信息的度量,但是,我个人更倾向于不确定性的解释。可能只是我,但当我不再试图将我对信息的先入为主的观念强加于方程式时,事情似乎变得清晰多了。)

在某种程度上,说熵是“不确定性的度量”是一种轻描淡写。给定某些假设(并预示着下面提到的一个重要结果),熵是不确定性的度量。

顺便说一下,当我使用熵这个术语时,我指的是香农熵。还有很多其他熵,但我认为可以肯定的是,香农熵是自然语言处理和机器学习中使用最频繁的熵。

事不宜迟,这里是一个事件的熵公式 Xn 个可能的结果和概率 p_1,…,p_n :

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

Shannon entropy

基本属性

如果你像我第一次看到这个公式时一样,你可能会问自己这样的问题:为什么是对数?为什么这是一个很好的不确定性的衡量标准?当然,为什么是字母 H ?(显然,使用英文字母 H 是从希腊文大写字母 Eta 演变而来,尽管历史看起来相当复杂。)

随着时间的推移,我学到的一件事是,一个好的起点——在这里和许多其他情况下——是问两个问题:(1)我试图理解的数学构造具有哪些理想的属性?以及(2)它们是具有所有这些期望特性的竞争结构吗?

简而言之,作为不确定性度量的香农熵的答案是:(1)许多和(2)没有。

让我们从愿望清单开始。

基本性质 1:均匀分布具有最大的不确定性

如果你的目标是最小化不确定性,远离均匀概率分布。

快速提醒:概率分布是一个函数,它为每一个可能的结果分配一个概率,使得概率总和为 1。当所有结果具有相同的概率时,分布是均匀的。例如,公平硬币(50%的尾部,50%的尾部)和公平骰子(六个面中的每一个面的概率为 1/6)遵循均匀分布。

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

Uniform distributions have maximum entropy for a given number of outcomes.

对于均匀分布,不确定性的良好度量达到其最高值。熵满足标准。给定 n 种可能的结果,最大熵由等概率结果最大化:

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

Equiprobable outcomes

这是应用于伯努利试验的熵函数图(具有两种可能结果和概率的事件 p1-p ):

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

In the case of Bernoulli trials, entropy reaches its maximum value for p=0.5

基本性质 2:不确定性对于独立事件是可加的

AB 为独立事件。换句话说,知道事件 A 的结果并不能告诉我们任何关于事件 B 的结果。

与这两个事件相关的不确定性——这是我们愿望清单上的另一个项目——应该是各个不确定性的总和:

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

Uncertainty is additive for independent events.

让我们用抛两枚硬币的例子来更具体地说明这一点。我们可以同时掷两枚硬币,或者先掷一枚硬币,然后再掷另一枚。另一种思考方式是,我们可以同时或分别报告两次抛硬币的结果。这两种情况下的不确定性是一样的。

为了使这一点更加具体,考虑两个特殊的硬币。第一枚硬币正面朝上( H )的概率为 80%,反面朝上( T )的概率为 20%。另一枚硬币的概率是 60%和 40%。如果我们同时抛两枚硬币,有四种可能的结果: HHHTTHTT 。对应的概率由*【0.48,0.32,0.12,0.08】*给出。

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

The joint entropy (green) for the two independent events is equal to the sum of the individual events (red and blue).

将这些数字代入熵公式,我们看到:

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

就像承诺的那样。

基本属性 3:添加概率为零的结果没有效果

假设(A)每当结果#1 出现时你就赢了,并且(B)你可以在两个概率分布中选择, AB 。分配 A 有两种结果:比如说 80%和 20%。分布 B 有三种结果,概率分别为 80%、20%和 0%。

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

Adding a third outcome with zero probability doesn’t make a difference.

给选项 AB ,你会选哪个?此时一个合适的反应是耸耸肩或者翻白眼。包含第三种结果既不增加也不减少与游戏相关的不确定性。 A 还是 B ,谁在乎。没关系。

熵公式同意这种评估:

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

Adding a zero-probability outcome has not effect on entropy.

换句话说,添加一个概率为零的结果对不确定性的测量没有影响。

基本性质 4:不确定性的度量在其所有论证中是连续的

最后一个基本属性是连续性。

众所周知,对连续函数的直观解释是没有“间隙”或“洞”。更准确地说,输出中任意小的变化(在我们的例子中是不确定性)应该可以通过输入中足够小的变化(概率)来实现。

对数函数在为其定义的每一点上都是连续的。在子集上连续的有限个函数的和与积也是如此。由此可见,熵函数在其概率论证中是连续的。

唯一性定理

钦钦(1957) 表明,满足上述四个基本性质的唯一函数族具有以下形式:

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

Functions that satisfy the four basic properties

其中λ是正常数。钦钦将此称为唯一性定理。设λ = 1 并使用二进制对数,我们得到香农熵。

再次重申,使用熵是因为它具有令人满意的性质,并且是满足基本愿望清单(性质 1-4)上所有项目的家族函数中的自然选择。(以后我可能会在单独的文章中讨论这个证明。)

其他属性

除了钦钦唯一性定理中使用的四个基本性质之外,熵还有许多其他性质。让我在此仅提及其中一些。

性质 5:具有更多结果的均匀分布具有更多的不确定性

假设你可以在一枚漂亮的硬币和一个漂亮的骰子之间做出选择:

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

Fair coin or fair die?

假设硬币正面朝上或者骰子正面朝上,你就赢了。

这两个选项你会选哪个?如果你是利润最大化者,A 和 B 如果你喜欢更多的变化和不确定性。

随着等概率结果数量的增加,我们对不确定性的度量也应该增加。

而这正是熵的作用:H(1/6,1/6,1/6,1/6,1/6,1/6,1/6),H(0.5,0.5)。

一般来说,如果我们让 L(k) 是具有 k 个可能结果的均匀分布的熵,我们有

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

对于 m > n

属性 6:事件具有非负的不确定性

你知道什么是负面不确定性吗?我也不知道。

一个用户友好的不确定性度量应该总是返回一个非负的量,不管输入是什么。

这是熵满足的另一个标准。让我们再来看看这个公式:

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

Shannon entropy

根据定义,概率的范围在 0 和 1 之间,因此是非负的。概率的对数是非正的。概率的对数乘以一个概率不会改变符号。非正乘积之和为非正。最后,非正值的负值是非负值。因此,对于每个可能的输入,熵都不是负的。

特性 7:具有特定结果的事件没有不确定性

假设你拥有一枚神奇的硬币。不管你怎么抛硬币,它总是正面朝上。

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

A magical coin

你如何量化魔法或任何其他情况下某个结果肯定会发生的不确定性?嗯,没有。所以自然的答案——我想,你会同意——是 0。

熵是否认同这种直觉?当然了。

假设结果肯定会发生。由此得出 p_i ,结果 i 的概率等于 1。 *H(X),*由此,简化为:

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

The entropy for events with a certain outcome is zero.

属性 8:翻转参数没有效果

这是另一个明显可取的属性。考虑两种情况。第一种情况,正面和反面的概率分别是 80%和 20%。在第二种情况下,概率正好相反:正面 20%,反面 80%。

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

两次抛硬币的不确定性相同,熵相同: H(0.8,0.2) = H(0.2,0.8)

更一般地说,对于两种结果的情况,我们有:

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

Flipping arguments

这个事实适用于任何数量的结果。我们可以按照我们喜欢的任何顺序排列论点(即分布的概率)。熵函数的结果总是相同的。

摘要

概括地说,香农熵是不确定性的度量。

它被广泛使用是因为它满足某些标准(也因为生活充满了不确定性)。唯一性定理告诉我们,只有一个函数族具有我们提到的所有四个基本性质。香农熵是这个家族中的自然选择。

除了其他事实之外,熵对于均匀分布是最大的(属性#1),对于独立事件是可加的(#2),对于非零概率的结果数量增加(#3 和#5),连续的(#4),非负的(#6),对于某些结果为零(#7)和排列不变的(#8)。

感谢您的阅读!如果你喜欢这篇文章,请点击“鼓掌”按钮,跟随我了解更多关于自然语言处理和机器学习的知识。

此外,让我知道如果你有一个项目在这两个领域的交叉点,你想讨论。

使用 Conda 的 Python 环境管理(Python 2 + 3,使用多个版本的 Python)

原文:https://towardsdatascience.com/environment-management-with-conda-python-2-3-b9961a8a5097?source=collection_archive---------0-----------------------

Environment Management with Conda (Python + Configuring Ipython/Jupyter)

遇到类似下图中的 ImportError 可能会很烦人。

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

幸运的是,Anaconda 使得用 conda 的包管理器功能安装包变得很容易。如果您需要复习,软件包管理器是一个自动安装、更新和删除软件包的工具。虽然 conda 是一个包和环境管理器,但让我们首先回顾一下 Conda 的包管理器功能,然后重点介绍环境管理器功能。

安装包

打开命令提示符/anaconda 提示符(windows)或终端(mac/linux)并运行下面的命令。你可以用numpy替换任何你想安装的包。

conda install numpy

卸载软件包

运行以下命令卸载软件包。您可以用numpy替换您想要卸载的任何包。

conda uninstall numpy

更新包

运行下面的命令来更新包。你可以用scikit-learn替换任何你想更新的包。

conda update scikit-learn

康达 vs 皮普

Pip 是一个 Python 包管理器,代表“Pip 安装包”,通常与 virtualenv (一个用于创建隔离环境的工具)结合使用。

大多数时候(除了一些例外),通过 conda 或通过 pip 安装包没有太大的区别。这是因为 pip 包也可以安装到 Conda 环境中。

conda install numpy
pip install numpy

这不是一个关于 conda 与 pip 的讨论,因为 Jake VanderPlas 已经非常广泛地讨论了这个问题,而是为什么你可以通过 pip 或者 conda 来安装软件包。

为什么需要多个 Conda/Python 环境。

假设你有多个项目,它们都依赖于一个库(Pandas,Numpy 等)。如果您升级一个包,它可能会破坏依赖旧版本包的其他项目,因为旧项目的语法可能会被否决或过时。你该怎么办?建立一个虚拟环境。它允许你从一个项目到另一个项目中分离出将要使用的包、依赖项和版本。

对于 python 用户来说,虚拟环境的一个常见用途是拥有独立的 Python 2 和 3 环境。例如,我在加州大学圣地亚哥分校的几个同学最近开设了一门机器学习课,其中一位教授用 Python 3 来布置作业。不过另一个班有个教授在 Python 2 里布置作业。因此,他们不得不在不同的类项目中频繁地在 python 2 和 3 之间切换。至此,让我们进入 conda 环境命令。我建议您在单独的标签中打开视频,观看命令的运行。

创建新环境

下面的命令在 python 版中创建了一个名为subscribe的 conda 环境。您可以用subscribe来代替您想要命名的环境。

conda create --name subscribe python=3.6

请记住,一旦激活(进入)该环境,您将需要在该环境中安装额外的软件包。您在根环境中拥有的包不一定就是您将在新环境中拥有的包,除非您安装它们。

您还可以创建一个包含多个包的环境。这也让您可以选择在以后需要时安装额外的软件包。

conda create --name chooseAnotherName python=3.6 numpy pandas scipy

进入环境

如果您的环境名称不是subscribe,您将需要用subscribe替换您的环境名称。

窗口:

activate subscribe

Mac:

source activate subscribe

离开一个环境

如果您的环境名称不是subscribe,您将需要用subscribe替换您的环境名称。

窗口:

deactivate subscribe

Mac:

source deactivate subscribe

列出您的环境

这个命令向您展示了所有这是一个非常有用的命令,可以查看您有什么样的环境,也可以查看您处于什么样的 conda 环境中。

conda env list

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

移除一个环境

如果您想要删除的环境名称不是subscribe,您需要用subscribe替换您想要删除的环境名称。

conda env remove --name subscribe

如果你对这部分有疑问,请参考文档,留下评论或者参考上面的视频。

在 IPython 笔记本中同时使用 Python 2.x 和 Python 3.x 环境

虽然这篇文章的这一部分很大程度上是从 stackoverflow 中截取和改进的,但我觉得回顾一下人们遇到的一些技术问题是很重要的。主要思想是拥有多个 ipython 内核。包 nb_conda_kernels 会自动检测笔记本内核的不同 conda 环境,并自动注册。

  1. 确保您安装了 anaconda 4.1.0 或更高版本。打开一个新的终端,通过键入以下命令检查您的 conda 版本

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

checking conda version

如果你低于 anaconda 4.1.0,输入 conda update conda

2.接下来,我们通过键入以下命令来检查是否有库 nb_conda_kernels

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

Checking if we have nb_conda_kernels

3.如果没有看到 nb_conda_kernels 类型

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

Installing nb_conda_kernels

4.如果您正在使用 Python 2 并且想要一个单独的 Python 3 环境,请键入以下内容

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

py36 is the name of the environment. You could literally name it anything you want.

如果您正在使用 Python 3 并且想要一个单独的 Python 2 环境,您可以键入以下内容。

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

py27 is the name of the environment. It uses python 2.7.

5.关闭您的终端并打开一个新的终端。jupyter 型笔记本

6.单击 new,您将看到列出了您的虚拟环境。

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

如果你有任何问题,请在这里或者在 youtube 视频评论中告诉我!

纪元与批量大小与迭代次数

原文:https://towardsdatascience.com/epoch-vs-iterations-vs-batch-size-4dfb9c7ce9c9?source=collection_archive---------0-----------------------

了解您的代码…

你一定有过这样的时候,你看着屏幕,挠着头想知道“为什么我在代码中输入这三个术语,它们之间有什么区别”,因为它们看起来都很相似。

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

为了找出这些术语之间的区别,你需要知道一些机器学习术语,如梯度下降,以帮助你更好地理解。

这里有一个关于梯度下降的简短总结…

梯度下降

它是一种 迭代 优化算法,用于机器学习中寻找最佳结果(曲线的极小值)。

坡度是指斜坡倾斜或下倾的速率

下降表示下降的实例。

算法是迭代意味着我们需要多次得到结果才能得到最优结果。梯度下降的迭代质量有助于拟合不足的图形以最佳方式拟合数据。

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

Source

梯度下降有一个参数叫做学习率。正如你在上面(左图)看到的,最初步长越大,意味着学习率越高,随着点的下降,步长越小,学习率越小。还有,成本功能在降低或者成本在降低。有时候你可能会看到有人说损失功能在减少或者损失在减少,两个 成本 损失 代表的是同一个东西(顺便说一句,我们的损失/成本在减少是件好事)。

只有当数据太大时,我们才需要像纪元、批量大小、迭代这样的术语,这在机器学习中是经常发生的,我们不能一次将所有数据传递给计算机。因此,为了克服这个问题,我们需要将数据分成更小的尺寸,并将其一个接一个地提供给我们的计算机,并在每一步结束时更新神经网络的权重,以使其适应给定的数据。

纪元

一个时期是整个数据集仅通过神经网络向前和向后传递一次。

由于一个时期太大,不能一次输入计算机,我们把它分成几个小批。

为什么我们使用一个以上的纪元?

我知道这在一开始是没有意义的——通过神经网络传递整个数据集是不够的。我们需要将整个数据集多次传递给同一个神经网络。但是请记住,我们使用的是有限的数据集,为了优化学习和图表,我们使用了梯度下降,这是一个 迭代 过程。因此,用单遍或一个历元更新权重是不够的。

一个时期导致图中曲线的欠拟合(下图)。

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

随着时期数的增加,神经网络中改变权重的次数越多,曲线从欠拟合最优再到过拟合曲线。

那么,什么是时代的正确数字呢?

可惜这个问题没有正确答案。对于不同的数据集,答案是不同的,但是你可以说历元的数量与你的数据的多样性有关…举个例子-你的数据集中只有黑猫还是有更多的多样性?

批量

单个批次中存在的训练示例总数。

**注意:**批次大小和批次数量是两回事。

但是什么是批呢?

正如我所说的,你不能一次将整个数据集传递到神经网络中。因此,您将数据集分成若干批次、集合或部分。

就像你把一篇大文章分成多个集合/批次/部分一样,比如引言、梯度下降、纪元、批次大小和迭代,这使得读者很容易阅读整篇文章并理解它。😄

迭代次数

要得到迭代次数,你只需要知道乘法表或有一个计算器。😃

迭代是完成一个历元所需的批数。

**注:**批次数等于一个历元的迭代次数。

假设我们有 2000 个将要使用的训练示例。

我们可以将 2000 个例子的数据集分成 500 个一批,然后将需要 4 次迭代来完成 1 个时期。

其中批量大小为 500,迭代次数为 4,用于 1 个完整的历元。

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

关注我在媒体获得类似的职位。

脸书推特LinkedInGoogle+ 上联系我

如果你有任何意见或问题,请写在评论里。

鼓掌吧!分享一下!跟我来。

乐意帮忙。荣誉………

你会喜欢的以前的故事:

[## 蒙特卡罗树搜索

每个数据科学爱好者的 MCTS

towardsdatascience.com](/monte-carlo-tree-search-158a917a8baa) [## 强化学习中的政策网络与价值网络

在强化学习中,代理在他们的环境中采取随机决策,并学习选择正确的决策…

towardsdatascience.com](/policy-networks-vs-value-networks-in-reinforcement-learning-da2776056ad2) [## 神经网络中的激活函数及其类型

它是一条曲线(sigmoid,tanH,ReLU ),用于映射有界值之间的网络值。这就完成了…

theffork.com](https://theffork.com/activation-functions-in-neural-networks/) [## 如何使用 Python 发送电子邮件

使用 Flask 设计专业邮件!

medium.com](https://medium.com/@sagarsharma4244/how-to-send-emails-using-python-4293dacc57d9) [## TensorFlow 图像识别 Python API 教程

在带有 Inception-v3 的 CPU 上(以秒为单位)

towardsdatascience.com](/tensorflow-image-recognition-python-api-e35f7d412a70)

错误分析拯救你!

原文:https://towardsdatascience.com/error-analysis-to-your-rescue-773b401380ef?source=collection_archive---------3-----------------------

修复算法中的错误时应遵循的策略

欢迎来到 ML 第三章 Ng 的经验教训!是的,这是完全基于吴恩达最近在 Coursera 上的课程的系列的延续。虽然这个帖子可以是一个独立的学习,但阅读前面的两篇文章只会有助于更好地理解这一篇。这里是这个系列的第一篇第二篇的链接。我们开始吧!

当试图解决一个新的机器学习问题(已经没有太多在线资源可用的问题)时,吴恩达建议先快速构建一个系统,然后再迭代。建立一个模型,然后反复识别错误,并不断修正它们。如何发现错误以及如何修复它们?正当你这样想的时候,错误分析穿着一件巨大的长袍,长长的胡须插在腰带下,戴着半月形眼镜,说道——

“是误差,哈利,向我们展示了我们的模型到底是什么,远远超过了准确性”

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

Source

为什么要进行误差分析?

当建立一个新的机器学习模型时,你应该尝试并遵循以下步骤

**设置目标:**设置开发/测试集,并选择一个评估指标来衡量性能(参见第一篇文章)

快速建立初始模型: 1。使用训练集进行训练—调整参数
2。开发设置—调整参数
3。测试集—评估性能

区分后续步骤的优先顺序: 1。使用偏差和方差分析处理欠拟合和过拟合(参考第二篇文章)2。分析导致错误的原因并修复它们,直到您准备好所需的模型!

手动检查算法正在犯的错误可以让你了解下一步该做什么。这个过程叫做误差分析。举个例子,你建立了一个显示 10%测试误差的猫分类器,而你的一个同事指出你的算法把狗的图像误分类为猫。你应该试着让你的猫分类器在狗身上做得更好吗?

要修复哪个错误?

与其花上几个月的时间去做这件事,冒着最后发现它没什么用处的风险,这里有一个错误分析程序,可以让你很快判断出这是否值得你去努力。

  1. 获取大约 100 个标签错误的开发集示例
  2. 数数有多少只狗
  3. 如果你只有 5%的狗图片,而你完全解决了这个问题,你的误差只会从 10%下降到 9.5%,最多!
  4. 相比之下,如果你有 50%的狗图片,你可以更乐观地改善你的错误,并有希望将其从 10%减少到 5%

这就是你如何评价错误修复的单一想法。以类似的方式,您可以通过创建一个网格来评估多个想法,并选择最能提高性能的想法-

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

The ceiling of error correction for blurry images is pretty good and should be fixed first

这个过程的结论给你一个估计,在这些不同类别的错误上工作是多么值得。例如,这里很明显,我们犯的很多错误是在模糊的图像上,然后是很棒的猫图像。这给你一种追求最佳选择的感觉。

它还告诉你,无论你在狗狗图片或 Instagram 图片上做得有多好,你最多只能提高 8%或 20%的表现。因此,根据你有多少提高大猫或模糊图像性能的想法,你可以从这两个中选择一个,或者如果你的团队有足够的人员,也许你可以让两个不同的团队独立研究其中的每一个。

现在,如果在模型构建过程中,您发现您的数据中有一些标注不正确的数据点,您该怎么办?

标签不正确的数据

训练集校正

深度学习算法对训练集中的随机错误非常鲁棒。只要这些错误是无意的,并且是随机的,就不要花太多时间去修复它们。举个例子,在我们的猫分类器的训练集中有一些错误标记的狗图像。

然而!然而,深度学习算法对系统错误并不鲁棒,例如,如果你将所有白色狗图像标记为猫,你的分类器将学习这种模式。

开发/测试集校正

您还可以选择在开发/测试集上进行错误分析,以查看有多少百分比的错误标签,以及是否值得修复它们。如果您的开发集误差为 10%,并且由于错误标记的开发集图像而导致这里有 0.5%的误差,那么在这种情况下,尝试修复它们可能不是很好的利用时间。相反,如果有 2%的 dev 集误差,0.5%的误差是由于错误标记的 dev 集,那么在这种情况下,修复它们是明智的,因为它占总误差的 25%。

对于错误标记的图像,您可以选择只修复训练集,而不修复开发/测试集。在这种情况下,请记住,现在,您的训练集和开发/测试集都来自稍微不同的发行版。这没关系。让我们谈谈如何处理训练集和开发/测试集来自不同发行版的情况

不匹配的培训和开发/测试集

不同发行版的培训和测试

假设你正在构建一个应用程序,从用户点击的图片中对猫进行分类。你现在有两个来源的数据。首先是来自网络的 200,000 张高分辨率图片,其次是用户点击的应用程序上的 10,000 张不专业/模糊的图片。

现在,为了让培训和开发/测试集具有相同的分布,您可以将来自两个源的图像混洗,并在两个组之间随机分布。然而,在这种情况下,您的 dev set 在 2500 个图像池中只有大约 200 个来自移动用户的图像。这将优化你的算法,在网页图像上表现良好。但是,开发/测试集的理想选择是拥有它们,以便反映您期望在未来获得的数据,并认为做好这些数据是重要的。

我们在这里可以做的是,让开发/测试集中的所有图像都来自移动用户,并将来自移动用户的剩余图像与 web 图像一起放入训练集中。这将导致培训和开发/测试集中不一致的分布,但从长远来看,这将让您达到您想要的目标。

数据分布不匹配时的偏差和方差

当训练集与开发集和测试集来自不同的分布时,分析偏差和方差的方法会发生变化。由于显而易见的原因(它们已经来自不同的发行版),您不能再将 train 和 dev 之间的误差称为方差。在这里,您可以做的是定义一个训练开发集,它将与训练集具有相同的分布,但不会用于训练。然后你可以分析你的模型,如下图所示-

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

Data mismatch error will get added to the variance if Training-Dev set is not defined

结论

了解你的机器学习算法的应用,相应地收集数据,随机拆分训练/开发/测试集。想出一个单一的优化评估指标,并调整你的旋钮,以改善这一指标。使用偏差/方差分析来了解您的模型是过拟合还是欠拟合,或者在那里工作得很好。跳到错误分析,确定修复哪个最有帮助,最后,努力把你的模型设置正确!

这是这个系列的最后一篇文章。感谢阅读!希望它能帮助你更好地处理你的错误。

如果您有任何问题/建议,请随时在这里提出您的意见或通过 LinkedIn / Twitter 与我联系

选民价值观的错误和不确定性

原文:https://towardsdatascience.com/error-and-uncertainty-in-voters-values-f053b0bd931d?source=collection_archive---------15-----------------------

在过去的几个月里, Paula Surridge 写了两篇非常棒的博客 帖子探讨选民的价值观、他们在欧盟公投中的投票以及他们更普遍的投票模式之间的关系。Nick Barlow 有一篇关于中间派和自由民主党的类似文章,也很有趣。如果你还没有读过,它们非常值得你花时间去读。

我想谈谈 Paula 的一些观点,但更详细地谈谈我们如何衡量选民的价值观和态度。特别是,我想比较一下求和反应和项目反应理论(IRT) 方法。关于 IRT 是如何运作的,我就不多赘述了。如果你感兴趣,这本书提供了很好的介绍。

这两种方法都源于同一个问题:衡量态度真的很难。正如尼克所说,让受访者在左右、授权或其他尺度上自我认同充满了问题。更重要的是,它假设了一些人可能不具备的政治成熟度,并忽略了受访者更有可能选择中间或极端的价值观。

为了解决这个问题,调查设计者提出了一些问题,他们认为这些问题代表了他们要测量的东西。让我们以保拉讨论的威权-自由主义光谱为例。为了衡量这一点,BES 询问受访者对五种说法的认同程度,范围从*“1。强烈不同意"*对 *"5。非常同意”。*这些是:

  1. 今天的年轻人对传统的英国价值观不够尊重
  2. 对于某些罪行,死刑是最合适的判决
  3. 学校应该教孩子服从权威
  4. 对电影和杂志的审查是维护道德标准的必要手段
  5. 违法的人应该被判更严厉的刑罚

最常见的是,我们通过简单地将这些回答相加来得出总量表。虽然这很容易,并且经常提供足够好的结果,但是它有两个主要问题。首先,它只在回答者回答了所有问题的情况下有效。如果这样做需要政治上的老练,我们就冒着排除不太懂政治的受访者的风险。这反过来会使我们的结果产生偏差。第二,求和将有序分类变量视为度量变量,并假设所有项目提供相同数量的信息,以将受访者置于感兴趣的范围内。这种假设有时可能是正确的,但在问题的难度不同或回答模式有偏差的情况下就不太可能了。

IRT 采取了不同的方法。它使用了相当于豪华的逻辑回归来定位潜在规模的每个受访者。因此,IRT 没有很多与求和相关的问题。例如,它可以估计位置,即使回答者没有回答所有的问题。它还允许不同的项目在定位回答者时提供不同数量的信息。但在我看来,IRT 最好的一点是它是基于模型的。因此,它给出的估计是概率。这意味着我们不仅可以计算出我们认为某人坐在秤上的位置,还可以计算出我们对自己的计算有多确定。

一些实证结果

为了比较求和法和 IRT 法,我运行了三个逻辑回归来预测基于选民年龄、性别和授权位置的脱欧投票。模型 1 使用总和值,模型 2 使用分级反应模型(一种 IRT)的分数,模型 3 使用这些分数加上它们的测量误差。这些模型还不够强大,不足以出现在美国政治科学杂志上,但对我们的目的来说已经足够好了。

在这些模型中包括测量误差通常是困难的,如果不是不可能的话。幸运的是,R拥有优秀的brms包,让这一切成为可能(也很容易!).brms也有一个非常棒的功能,可以产生边际效应图,我已经在下面列出来了。为了便于比较,我对 auth-lib 总排名进行了 z 标准化。

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

Marginal effects of auth-lib scale placement on probability of voting Leave using Left — summed responses, Centre — factor scores from a graded response model, 3 — the same factor scores, plus measurement error.

从第一个和第二个图中可以看出,使用求和值和 IRT 分数的模型之间几乎没有区别。第一个模型中授权库位置的 1 个标准差变化导致离开投票的 1 个对数优势变化,相比之下,第二个模型中的 1.07 个对数优势变化。让我们暂时回到现实世界,这意味着这两个模型预测,auth-lib 值为 1 的人投票离开的可能性分别是得分为 0 的人的 2.7 倍和 2.9 倍。

然而,在模型中包含误差会导致不同的结果。不仅曲线更陡,而且我们的估计还包含更多的不确定性(如灰色置信带所示)。如你所料,更陡的曲线意味着更大的系数。在这种情况下,模型预测 auth-lib 位置中 1 个标准偏差的变化导致 1.51 个对数几率的变化。因此,我们应该预计 auth-lib 值为 1 的人投票脱离的可能性是 auth-lib 值为 0 的人的 4.5 倍。与之前模型的估计相比,这是一个很大的差异,并且表明 auth-lib 的放置比我们想象的更重要。

不仅影响更大,而且第三个模型的 R 值也更高,这表明它占了投票假期差异的更大部分。模型 3 解释了脱欧投票中约 25%的差异,而模型 1 和 2 分别为 21%和 20%。

“求和”完毕

我在这里的观点不是鼓吹测量。我确实认为它非常重要,但是,正如我前面所说的,总和值通常足够好,我不嫉妒任何人使用它们。然而,我确实希望这篇短文能激励研究人员对测量可能对他们获得的估计值的可靠性产生的影响保持谨慎。

这一点对于精确度尤为重要。例如,如果您的模型是一个政策决策的基础,您可能会考虑选择更接近模型 3 的模型,该模型利用了所有可用的信息。这可能很耗时,也更有技术含量,但可能会导致更可靠的估计。如果你有这样的倾向,这可能也值得考虑进行更多的一般性研究。你永远不知道,如果这种分析是可靠的话,这种影响可能比你最初想象的更重要!

每个 ML 工程师都需要知道的基本算法

原文:https://towardsdatascience.com/essential-algorithms-every-ml-engineer-needs-to-know-3167b1e940f?source=collection_archive---------2-----------------------

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

在深度神经网络接管场景之前,机器学习作为一个领域已经存在了很长时间。这里有一个你需要知道的算法列表,这样你就可以解决任何遇到的问题。这不是一个详尽的列表,但是你的基础将会被覆盖。

我还想宣布,我的媒体博客将从一般的机器学习焦点转变为深度学习焦点。我现在的大部分工作都涉及到创建新颖的深度学习系统,所以我想花更多的时间来写这方面的东西!

回归算法

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

回归算法模拟变量之间的关系。最初是一种来自统计学的技术,它们已经成为每个机器学习工程师工具箱中的重要工具。

常见回归算法

  • 最小二乘回归
  • 线性回归
  • 逻辑回归

约翰霍普金斯大学关于回归模型的 Coursera 课程

聚类算法

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

聚类算法可以将数据点分成具有相似属性的组。他们通过寻找数据中的内在结构来将数据组织到不同的组中。群体中的事物比其他群体中的事物相互之间的联系更紧密。

有两种类型的聚类算法。硬聚类是指数据点是否在一个组中。软聚类是指一个数据点可以不同程度地属于多个不同的组。

常见聚类算法

  • k 均值
  • 分层聚类

令人惊叹的集群介绍视频

降维算法

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

当特征的数量与数据点的数量相比非常大时。降维算法可以帮助您将特征的数量减少到手头问题所需的数量。它们可以删除多余或无用的功能,帮助您获得更好的结果。

降维算法有两种工作方式。第一种方法是通过特征选择,其中算法挑选可用特征的子集。第二种方法是特征提取,将高维空间中的数据降低到一个较低的维度。

常见的降维算法

  • 主成分分析
  • 低方差滤波器
  • 高相关滤波器
  • 随机森林
  • 反向特征消除/正向特征构建

这不是一个详尽的列表,只是我用过的一些。如果你想进一步了解这方面的内容,也想看看这些算法的投资回报率,请查看 KDnuggets 的博客文章

决策树算法

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

决策树根据数据中的值创建决策模型。在树结构中进行分叉,直到对每个数据点都有预测。与其他算法(深度学习)不同,他们的结果易于理解,并且易于在许多不同的数据类型上使用。

常见的决策树算法:

  • 分类和回归树
  • C4.5 和 C5.0
  • 随机森林
  • 卡方自动交互检测器

Analytics Vidhya 有一篇很棒的文章,深入探讨了决策树。列出不同的算法及其优缺点

深度学习

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

机器学习和“AI”背后的炒作是深度学习造成的。它们是人工神经网络的现代版本,利用廉价的计算来训练更大的神经网络。它们是强大的通用函数近似值,已经证明它们有能力解决一些最困难的问题。参见阿尔法围棋

通用深度学习人工智能

  • 堆叠式自动编码器
  • 卷积神经网络
  • 递归神经网络
  • 胶囊网络(更多信息在此)

查看这本书的片段。它介绍了深度学习的主要架构。

减去

如果你对机器学习很认真,你必须了解你可以使用的工具。对这些工具有一个很好的理解将会帮助你解决你遇到的任何问题。

基本数据技能——就业市场上的供给和需求

原文:https://towardsdatascience.com/essential-data-skills-supply-and-demand-on-the-job-market-4f7dffa23b70?source=collection_archive---------12-----------------------

深入了解 Kaggle 数据科学调查结果

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

The Data Science Community on Kaggle

Kaggle 数据科学调查

如果你错过了,不要担心,你可以明年加入我们。拥有超过 20,000 名受访者的 Kaggle ML & DS 2018 是迄今为止对数据科学界状况进行的最重要、最广泛的调查之一。该数据集包含超过 50 个问题的答案,其中许多是多项选择甚至是自由文本,因此对于数据爱好者来说有一个巨大的游乐场可以探索。这篇文章是我作为 Kaggle 调查 2018 年挑战的一部分所做的内核的抄本。

我们就业吧!

这项研究的主题是就业能力,所以我的大部分探索将集中在社区的一个相当大的子集:那些已经就业并目前活跃在数据科学领域主要角色之一的人。

就业能力 ,名词

拥有就业市场上急需的技能。

在第一部分,我将使用精选的调查数据回答如下问题:

  • 在数据科学领域,哪些是最重要的角色?
  • 这些角色的个性特征是什么?
  • 是什么让他们与众不同,与众不同?
  • 对他们中的每一个人来说,最需要的技术技能是什么?

我认为,这些问题的答案与学生、失业者以及任何计划职业转型或简单提升自己的人尤其相关。希望这个内核的读者不同意下面的观点:

“我是学生,请不要问这些问题”

27 号回应者以自由形式回应

在第二部分中,我将重点关注每个角色特定的技术堆栈,比较它们在就业市场上的供求,并确定最有用的技能。

选择正确的角色

如果你是一名学生或刚刚开始职业生涯,仍然不确定要瞄准的技术技能,或者如果你是一名经验丰富的数据科学家,正在寻找提高就业市场机会的方法,第一步是确定所有可能性,并探索它们之间的差异。

绘制社区地图

我通过输入缺失值、转换为虚拟变量和标准化数值来清理数据。然后,我使用 LDA 执行监督的降维并将结果特征向量映射到一个二维空间,同时马锡明聚类的分离。我在 LDA 中使用的特征集是基于我认为最能预测一个人日常工作活动的问题。

对产生的主成分的解释和轴的命名是高度主观的,因为它是多个特征的加权组合,并且可能太复杂而无法用简单的词语来描述。基于各个小组的最终位置,我喜欢将 **PC1(水平)视为业务(左)对代码(右)**轴,将 **PC2(垂直)视为工程(底部)对研究(顶部)**轴。

这些角色相对于彼此处于什么位置?

正如你可能注意到的第一张图片,集群明显重叠,这些角色的定义非常模糊。例如,数据分析师业务分析师角色拥有大部分相同的特征,但在应用分析得出的结论方面略有不同。尽管有重叠,星团质心的位置揭示了一些有趣的模式。气泡的大小代表了群体的大小。

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

观察结果:

  • 营销和业务角色在图表的中心左侧区域形成一个集群组,离密切相关的管理集群不远,这些集群使用数据分析师提供的报告和分析来做出数据驱动的业务决策。
  • 学术角色,即首席研究员研究研究员研究科学家在图表的顶部中间部分形成一个紧密的集群组。从技术角度来看,他们与数据科学家的角色最为相似。
  • 学生群体与其他学术角色关系密切,明显偏向于更实用的工程相关群体。
  • 数据库工程师比预期的距离数据工程师集群更远。原因可能是这些角色包括大量的查询、报告生成和数据维护,这与业务集群组的工作更密切相关。
  • 学生,以及首席执行官顾问数据科学社区中真正的多面手角色。我想象这些首席执行官作为前数据科学家现在领导一个人工智能大数据驱动的创业公司。

他们每天都在做什么?

让我们通过工作方法来探讨这些角色。对于前 5 个类别,我计算了认为某项活动重要的人的百分比。

哪些活动是你工作中的重要组成部分?

由于代码编写的重要性,答案以百分比给出,所以我直接使用它们。

Q23:你在工作或学校中大约有百分之多少的时间是花在主动编码上的?

彩色条表示与平均值的偏差,单位为百分点。方框旁边的小圆点表示该值是相关行中的最大值(蓝色)或最小值(红色)。

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

Main Activities

观察结果

  • 这两个问题完美地抓住了角色的本质。大多数角色都有一个优点,数据科学家是个例外。他们对每一项活动都给予了高于平均水平的重视,并且是构建和探索 ML 解决方案的明确领导者。这支持了数据科学家应该精通多个领域的先入之见。

数据管道

现在让我们看看数据管道的每一步花费了他们多少时间。

Q34 —在数据科学项目中,您大约有多少时间用于以下活动?

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

Working on the data pipeline

观察结果:

  • 数据清理是数据管道中最重要的部分。研究科学家软件工程师是幸运的人,他们的数据被端上了银盘。他们也是花最少时间分析它的人。

工具使用

他们使用什么样的工具和软件?

Q12 —您分析数据的主要工具是什么?

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

Tool Usage

观察结果

  • 统计学家在高级统计学领域遥遥领先。
  • 研究科学家是使用其他类型软件包的领导者,这些可能是他们用于生物信息学、物理学、数学的特定领域软件。

黑盒模型?

不要。你只是学习不够!

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

Black box models

观察结果

  • 统计学家是拥有最多万事通一无所知类型的领导者。
  • 几乎每个数据科学家都对 ML 模型有多不透明或多黑有自己的看法,有点令人惊讶的是,数据分析师对这个问题最不感兴趣。

我离成为数据科学家还有多远?

让我们以数据科学家角色为参考,探讨其他角色与之相关的方式。问题 26 的答案有助于我们评估每个人的自我评估:

Q26 —你认为自己是数据科学家吗?

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

Self assessment

观察结果:

  • 请注意,两个答案中的角色顺序完全相同。能够深刻理解机器学习模型是数据科学家的必备技能。
  • 0 轴左侧的数据科学家是自我怀疑者。他们第一次被问到的时候挑了数据科学家的头衔,但是第二次面对问题的时候开始质疑自己的真实身份:“真的?你呢。看看你自己!你认为自己是数据科学家?”

我们可以通过计算聚类质心之间的欧几里德距离,使用我们的 LDA 特征空间来估计每个角色与数据科学家角色的相似性。

现在,我们已经对每个角色需要什么有了一个大致的概念,并且已经看到了他们看待自己的方式,让我们彼此对照一下“自我评估”、感知的相似性以及每个角色与数据科学家角色之间的实际相似性。

气泡的大小代表团队的规模,X 轴代表团队到数据科学家角色的距离,通过自我评估(Q26 —你是数据科学家吗?),Y 轴代表小组到数据科学家角色的距离。

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

Self assessment vs. workflow similarity

观察结果:

  • 大多数统计学家似乎认为自己是数据科学家,尽管上面的图表强调了这些差异。
  • 另一方面,数据工程师似乎没有意识到他们的工作与 T42 的数据科学家有多么相似。

选择正确的技能

在接下来的几行中,我将深入挖掘关于数据科学就业市场的数据。我将 Kaggle 的调查数据与我目前正在处理的一个更大的数据集的一部分结合起来,这个数据集由 1500 多个与技术栈信息相关的数据职位组成。这些帖子是从过去两年的 StackOverflow 中搜集来的。我保留的唯一信息是标题和技术栈。将这组数据与调查结果进行比较,给了我一个绝佳的机会来探索社区如何满足数据工作市场的技能需求。

数据科学家的进化

数据科学是一个蓬勃发展、快速发展的领域,大多数相关技术和框架都是最近才出现的,尚未成熟。例如 Tensorflow ,符号数学和神经网络技术的领导者,仅在 3 年前发布。鉴于数据科学技术堆栈的极度动态性,我将只关注 10 年经验以下的开发人员。我认为,在这个水平之上,技术栈在就业能力中发挥的作用越来越小,对掌握一套特定语言和技术的期望让位于不太可测的技能,如架构、管理、特定领域的经验等等。

因此,让我们看一下数据科学家的技能堆栈如何随着时间的推移而发展。我假设从零技能的“空白页面”开始,但是很少出现这种情况。通常,在开始使用代码进行数据分析之前,人们已经熟悉了一些编程语言。

我根据个人经历创建了 5 个小组:

  • 实习生—不到 1 年
  • 初级——1-2 岁
  • 中级—3-5 年
  • 高年级—5-10 岁
  • 经验丰富—超过 10 年

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

Number of tech skills per experience level

观察结果

  • 学习曲线在开始时非常陡峭,但在高级阶段达到平稳。
  • 有趣的是,编程语言是知识不会随着年龄增长而减少的一个类别。数据科学中使用的大多数语言已经存在了很长时间。 SQL (1974) , [Python (1991)](https://en.wikipedia.org/wiki/Python_(programming_language) , [Java (1995)](https://en.wikipedia.org/wiki/Java_(programming_language) 。

他们需要的技能

为了了解故事的另一部分,我们来看看与数据相关的职位发布的要求。我使用的原始数据集包含 30,000 多个条目。选择与数据科学领域相关的数据并不是一个简单的过程。我试图将选择限制在那些包含机器学习数据科学大数据相关术语的范围内。过滤后的结果可以在我发布在 Kaggle 上的数据集里找到。以下是需求数量百分比的细分:

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

Number of skills required in job postings

观察结果:

  • 快速浏览一下数据就会发现,超过 88%的职位描述要求至少具备 3 种不同的技能。超过 60%的人提到了申请人应该熟悉的 5 个不同的术语。

时间是有限的,所以我们必须仔细决定在哪些技能上投资,以使我们在就业市场上的机会最大化。下一节将通过分析这些技能在数据集中的出现频率来帮助我们选择这些技能。

学习 Python。没有借口。

我按照熟悉相关技术的用户百分比(供应)和提及该技术的工作需求百分比(需求)来可视化前 50 项技术。出现在两个列表中的技术用灰色丝带连接。灰色的技能是供应或需求栏中缺少的技能。

我决定不包括一些我觉得过于笼统的术语,但尽管如此,这些概念仍然是雇主要求的 50 件最重要的事情之一。按重要性排序:Machine LearningBig DataCloudSys AdminAgileAlgorithmNoSQLDatabaseData ScienceRESTDeep LearningArtificial IntelligenceWeb-ServicesTestingComputer VisionQASecurityAutomationDesignMicroservicesDevOpsData WarehouseNLPStatisticsETLDataETLData

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

Supply and Demand of tech skills for data-related jobs

按角色划分的技能重要性

每项技能的重要性因角色而异,因此,尽管有一个概述很有用,但按职位细分供应和需求给了我们更有价值的洞察力:

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

Supply and Demand by role

观察结果:

  • 学习 Python 。没有借口。熊猫和 Numpy ,它最重要的数据争论库也出现在 50 强名单中。
  • 大多数 T42 IDE、笔记本和数据可视化库在工作要求中从未提及。
  • 另一方面, HadoopSparkElasticsearch 是就业市场上最受欢迎的技术,但在调查中没有提到。其他出现在前 50 名的大数据技术还有: HiveCassandraKubernetesKafka
  • Java 很重要,但是它在全球排名中的重要性可能被数据集中的大部分软件工程工作夸大了。同样的还有 JavascriptReactAngular 。之所以选择这些职位,是因为它们在某种程度上构成了数据管道的一部分,但它们往往夸大了一些技术在名单中的存在。
  • 没有对操作系统的使用情况进行调查,但是需要注意的是,在所有与数据相关的工作需求中,超过 5%的需求提到了 Linux。
  • Tableau 在数据可视化工具的调查中没有被提及,尽管基于 Google Trends它比最受欢迎的 Python dataviz 工具 Matplotlib 受欢迎程度高两倍多。它不受语言限制,用途广泛,易于学习,并且正在崛起。
  • Git 和 T42 Docker 在我看来是不可或缺的工具。尽管它们只出现在列表的下半部分,但它们应该是开发人员首先需要掌握的技能之一。

学习顺序

没有哪个头脑正常的人会通过使用 MapReduce 或 Hadoop 来开始学习编程。他们说,在开始写小说之前,你首先需要学习 ABC。那么,如果学习这些技能有一个自然的顺序,我们能从数据中揭示这种潜在的顺序吗?

关联规则可能会给我们一些答案。关联规则挖掘的目标是根据项目的单独出现概率和同时出现概率来识别项目之间的共现模式。例如,如果 RStudio 出现在几乎所有出现 R 的堆栈中,但反之则不成立,我们可以假设 RRStudio 的先决条件。这是一个在预定义的置信度阈值之上识别的关联的图表,边的权重表示置信度,节点的大小和垂直位置都表示特定技能的出现频率。

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

Tech skill learning order

观察结果

  • 大多数确定的关联似乎是有效的先决条件关系,例如 Seaborn 是作为对 Matplotlib API 的抽象构建的,没有 RStudio 就没有 Shiny 。其他的,例如张量流Caffe 是竞争关系,其中更受欢迎的选择(在这种情况下张量流)通常在学习不太受欢迎的之前已经被探索过。
  • Xgboostlightgbmcatboost 是先进的合奏工具,可以等到你觉得受到 ScikitLearn 提供的可能性的限制。

数据科学家技术堆栈

现在让我们来看看每个经验等级最有可能的筹码数量。我们将使用一个简单的指标来衡量这一堆人的就业机会:我们得到1 分了解需求集的第一个技能,2 分第二个,3 分第三个,依此类推。这样更深的堆栈将得到适当的推动。最终得分是候选人在每项工作要求中得到的所有分数的总和。

当然,对少数技术的深入了解总是胜过对几种技术的肤浅熟悉,但是深度比广度更难衡量,所以我将坚持根据符合要求的技能数量来比较堆栈。

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

观察结果:

  • 从初级到中级之间,最重要的改进是学习第二个数据库提供商。
  • 中级水平和高级水平之间,学习 R 开启了可能性。

现在让我们来看看数据分析师

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

观察结果:

  • 初级中级之间张量流给予最大的推动。
  • 中级高级等级之间,增加了 R 似乎是进步,分数上升到 1500 以上。

我们来玩个游戏吧!

让我们以一个技能数量适中的初级数据工程师的身份开始游戏。我们知道下一级(中级)人员的平均技术水平,所以让我们从每个类别中挑选相同数量的技能,并尝试最大化我们的就业能力。然后,我们会将我们选择的结果与下一个级别人员的平均分数进行比较。

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

观察结果

  • 一个中级数据工程师在 Kaggle 上的平均分是 2198 。另一方面,根据实际需求挑选的技能会得到 2304 的分数。
  • Java 显然是新堆栈中得分最高的技术。
  • 增加的PostgreSQLAWS 红移是一个数据工程师的绝佳选择。
  • D3 添加到堆栈中打开了数据可视化的可能性。
  • Keras 进行深度学习也是一项抢手的技能。

数据科学技术栈的皇家同花顺

如果我们从一张白纸开始,从零开始选择所有技能来填充高级数据科学家的堆栈,会发生什么?

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

观察结果:

  • 一个资深数据科学家在 Kaggle 上的平均分是 1735 。根据技能需求分数 2469 自由选择相同大小的筹码。
  • 栈的核心是 PythonJavaSQL 。这三项涵盖了所有工作要求的 50%以上。
  • 亚马逊网络服务也给了这个堆栈一个很好的提升。
  • D3MatplotlibShiny 涵盖了 JavascriptPythonR 中最重要的 dataviz 工具。
  • PostgreSQLMySQL 是最流行的开源数据库,它们最大化了我们在这个领域的机会。

结论

  • 选择合适的角色。如果你喜欢写代码,就成为软件工程师,如果你喜欢数学,就成为统计员,如果你是 DevOps 一类的人,就做数据工程,如果你喜欢数据可视化,做 EDA,就做数据分析师。如果这些你都想要,那就成为数据科学家
  • 选择合适的技能。 PythonJavaSQL 需求量大。 GitDockerLinux 必不可少。 ScikitLearnTensorflowKeras 是 ML 库的领导者。 HadoopAWSSpark 不容忽视。

数据科学的基本数学

原文:https://medium.com/s/story/essential-math-for-data-science-why-and-how-e88271367fbd?source=collection_archive---------0-----------------------

成为更好的数据科学家需要掌握的关键主题

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

Photo: Pekic/E+/Getty Images

数学是任何当代科学学科的基石。几乎所有现代数据科学的技术,包括机器学习,都有深厚的数学基础。

不用说,你绝对需要所有其他的知识——编程……

NLP 任务的基本文本更正过程

原文:https://towardsdatascience.com/essential-text-correction-process-for-nlp-tasks-f731a025fcc3?source=collection_archive---------3-----------------------

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

“person walking on sea near bridge during daytime” by frank mckenna on Unsplash

在之前的故事中,引入了 Norvig 的算法来纠正拼写错误。它使用了 4 种操作(即删除、转座、替换和插入)。在这个故事中,我想介绍另一种方法,只使用删除操作来找到潜在的正确单词。

在处理文本时,我们可能需要处理不正确的文本。尽管我们仍然可以使用字符嵌入单词嵌入来计算类似的向量。它对看不见的数据和词汇表之外的东西很有用(OOV)。不过如果能纠正错别字就更好了。

看完这篇帖子,你会明白:

  • 对称删除拼写纠正(SymSpell)
  • 履行
  • 拿走

对称删除拼写纠正(SymSpell)

Garbe 引入了对称删除拼写纠正(SymSpell)。这是一种简单但有用的纠正拼写错误的方法。

在离线训练期间,需要执行预先计算来建立语料库。用编辑距离生成 word(仅删除操作)并将它们与原始项目连接。换句话说,它使用额外的存储和内存资源来节省在线预测时间。如果匹配,新生成的单词将用于搜索并返回原始单词。在线预测时,输入单词经过同样的计算,然后从预先计算的结果中查找。你可以查看这个故事的细节。

速度方面的性能非常好,因为:

  • 预计算是离线完成的。
  • 在线预测只涉及删除操作和索引搜索(哈希表)

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

https://github.com/wolfgarbe/symspell

履行

为了方便拼写检查,需要语料库。为了便于演示,我简单地使用了 sklearn 库中的数据集,没有进行预处理。您应该使用特定领域的数据集来为您的数据构建更好的语料库。

建立语料库

from collections import Counter
from sklearn.datasets import fetch_20newsgroups
import recorpus = []
for line in fetch_20newsgroups().data:
    line = line.replace('\n', ' ').replace('\t', ' ').lower()
    line = re.sub('[^a-z ]', ' ', line)
    tokens = line.split(' ')
    tokens = [token for token in tokens if len(token) > 0]
    corpus.extend(tokens)corpus = Counter(corpus)corpus_dir = '../../data/'
corpus_file_name = 'spell_check_dictionary.txt'symspell = SymSpell(verbose=10)
symspell.build_vocab(
    dictionary=corpus, 
    file_dir=corpus_dir, file_name=corpus_file_name)symspell.load_vocab(corpus_file_path=corpus_dir+corpus_file_name)

修正

results = symspell.correction(word='edwarda')
print(results)

输出是它将“edward”和“edwarda”标识为 1 个距离,而“count”是指原始语料库的频率。

[{'distance': 1, 'word': 'edward', 'count': 154}, {'distance': 1, 'word': 'edwards', 'count': 50}]

除了单词校正,Symspell 还提供了一个复合词的距离计算。

results = symspell.corrections(sentence='Hello I am Edarda')
print(results)

与单字校正不同,复合函数支持拆分和分解操作。有关详细信息,您可以查看符号拼写 API

下面的输出计算与原始句子的总距离。给出“你好我是 Edarda”,它发现如果修正为“你好我是 ed 区”最短距离是 3。

[{'distance': 3, 'word': 'hello i am ed area'}]

拿走

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

  • 和拼写校正器一样,符号拼写不考虑上下文,而仅仅考虑拼写。
  • 由于方法简单,搜索时间复杂度为 O(1) 为常数时间。
  • 允许更大的编辑距离会引入更大的词汇,并导致更大的硬盘和内存消耗,但在当前的资源规模下应该没问题。

关于我

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

参考

C #中的符号拼写(原始)

python 中的符号拼写

通过抓取推文找到 2018 年 FIFA 世界杯最喜欢的球队

原文:https://towardsdatascience.com/estimate-the-favorite-scraping-tweets-using-python-863303384e29?source=collection_archive---------9-----------------------

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

source: blog.cpdfootball.de

足球运动员和数据科学家的工作展示了相同的工作-生活设置,即技能和意志的组合*。*

6 月 14 日前夕,一个备受赞誉的所有足球爱好者的宗教节日——2018 年 FIFA 世界杯在俄国拉开帷幕。这个月久负盛名的体育盛宴将在全球范围内庆祝,直到 7 月 15 日的大结局。

抓住这个机会,我测试了我新发现的技能,以判断在给定的比赛中两个竞争团队中谁将是最受欢迎的。

你将在这里学到的东西 :

  1. 如何从 Twitter 上抓取数据?
  2. 数据挖掘

先决条件:

  1. Tweepy 库应该安装在您的计算机上。

2.访问 Twitter。如果您还没有帐户,请创建一个帐户。

抓取文本数据是自然语言处理的一个组成部分。当手头的任务是分析情绪时,Twitter 是一个非常实用的平台。

思维过程:

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

source: www.nocodewebscraping.com

这就是我们的方法——首先,我们将生成所需的凭证以利用 Twitter API,然后我们将编写 python 代码来提取实时推文,最后我们将通过选择相关的关键字来分析推文。

让乐趣开始吧…

抓取推文的分步指南

A.为 Twitter API 生成凭据:

。访问 https://apps.twitter.com/T21,用你的 twitter 凭证登录。

二。点击创建新应用

。输入必要的详细信息,然后点击“创建您的 Twitter 应用程序

。在下一页,点击“ API 密钥选项卡,复制您的“API 密钥”和“ API 秘密”。(建议:务必在桌面上贴上这些凭证的便笺)

V 。向下滚动点击“创建我的访问令牌,复制你的“访问令牌”和“访问令牌秘密”。

B.通过 Python 代码连接到 Twitter API:

下面是您需要的代码,以便连接到 Twitter 上的实时推流,并将它们下载到您的机器上。

  • 注意:编码时使用 Python 2.7 版本。

一旦您在命令提示符下执行代码(对于 windows 用户),您将看到下面的数据流。

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

Live Streaming Tweets

C.分析数据:

在命令行下输入保存下载的推文。

python Twitter _ streaming . py > Twitter _ data . txt

为了理解锦标赛揭幕战的极性方向,我定期(在 6 月 13 日和 14 日)运行该程序两天,以获得相当大且有意义的数据样本。我可以在上面提到的时间段内抓取 79,359 条大小为 450 MB 的推文。

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

您可以根据业务案例的需要从原始文本中提取尽可能多的见解。比如说。这是写推特的一种语言。在底部找到这个练习的 Jupyter 笔记本。

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

由于第一场比赛是在东道主俄罗斯和对手沙特阿拉伯之间,我选择了以下关键词。

  • 国际足联,世界,世界杯,足球,国际足联世界杯,#FIFA2018
  • 世界杯,#WorldCup2018,#FifaWorldCup,
  • #FIFAWorldCup,RUSKSA,#RUSKSA,预测,赢,#FIFA。

为了估计这两个帖子中哪一个是最受欢迎的,用#RUS、#KSA 和#鲁斯卡作为目标推文,并分离结果。

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

Final Outcome

令人惊讶是,比赛结果也与公众情绪一致。当俄罗斯人痛击平庸的沙特人时!

俄罗斯 5 比 0 沙特阿拉伯

多么片面的事情啊!

你还在等什么,还有 63 场比赛要打。玩得开心!!下面是参加本届世界杯的球队的信息图。 在这里 你可以找到所有比赛的赛程。

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

FIFA WC 2018 Qualified Teams . source: www.Ivacy.com

朱庇特笔记本:

希望你喜欢这篇文章。所以,释放你的爱和情感吧,这将根据你点击拍手图标的次数来估算。# seeyou next time #直到那时***# KeepLearningNewThings*****

参考文献:

  1. 十二页文档
  2. Twitter 流媒体 API — Python &代码!

更多阅读:

如果你喜欢我的文章,那就花几分钟看看我的其他博客吧-

  1. 什么是探索性数据分析?
  2. K 表示聚类:在陌生人的世界里识别 F . r . I . e . n . d . s
  3. 决策树—数据科学家破解哈姆雷特困境的灵丹妙药

估计分布:非参数

原文:https://towardsdatascience.com/estimating-distributions-nonparametric-713ccf0647b?source=collection_archive---------14-----------------------

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

Taken from here

这篇文章是我深入研究如何优化投资组合配置的系列文章的一部分。本系列解释了我的开源投资组合优化库 OptimalPortfolio 背后的数学和设计原则。第一篇文章是关于寻找市场不变量的。这样做之后,我们现在必须估计市场不变量的分布,以便从中提取有用的信息。

估计数据的统计特性是一个深入研究的领域。困难出现在几个方面:

  1. 选择我们假设数据是从哪个分布产生的。
  2. 使得估计器稳健,使得它们对数据的变化不太敏感。
  3. 将数据拟合到所选择的分布,以有效地获得最佳估计。
  4. 确保估计值能很好地推广到总体,而不仅仅是样本数据。

在我们进一步讨论之前,我们需要对这里的一些术语进行形式化。

估计量

给定从具有固定参数的某个分布生成的数据样本,

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

为简单起见,我们假设分布可以完全由均值和方差(或标准差)来表征。现在,估计量实质上是使用样本数据计算的分布的均值和方差的估计。可以想象,这个问题与数据的结构、数据点的数量、数据点是如何生成的以及是否有任何缺失值紧密相关。

考虑到这些问题,有许多方法可以从数据中找到估计值。我将它们分为如下三类:

  1. 非参数—当有大量数据时,这种方法很有效。
  2. 最大似然-当数据集较小时,这比非参数更有效
  3. 收缩-这最适用于高维或非常小的数据集

因为在一篇文章中讨论这三种方法会使文章太长,所以在这篇文章中,我们探讨非参数估计量。在后续文章中,我将深入讨论另外两种估算方法。

非参数的

非参数估计量顾名思义。这些估计量并不局限于任何特定的参数化分布。相反,只考虑数据,并将分布建模为经验分布。经验分布本质上是在每个数据点都有一个核函数的分布。这个核函数被经典定义为狄拉克δ函数。然而,由于使用 Dirac delta 函数进行计算的困难,现代实现考虑高斯核。换句话说,经验分布是对于每个数据点

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

在我们的例子中,我们让核函数 K 是高斯函数,所以

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

其中参数γ被认为是平滑参数,它可以被认为是每个数据点处的高斯分布。很容易证明,这种经验分布将产生与样本均值和方差相等的均值和方差。因此,

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

经验分布似乎很简单,很容易理解。这可以实现为

def sample_mean(invariants, frequency=252):
    *"""
    Calculates sample mean.
    """
*    daily_mean = invariants.mean()
    return daily_mean*np.sqrt(frequency)

def sample_cov(invariants, frequency=252):
    *"""
    Calculates sample covariance
    """*
    daily_cov = invariants.cov()
    return daily_cov*frequency

当我们试图改进它以解决各种错误时,困难就来了。首先,让我们关注经验分布的局限性。

限制

非参数估计受到许多限制。首先,为了获得真实均值和方差的合理估计,我们需要大量的数据。对数据的大量需求是由于大数定律。该定律指出,随着数据点的数量趋于无穷大,样本均值和样本方差将趋于总体均值和总体方差(有些情况超出了本文的范围)。换句话说,如果我们有一个无限的数据集,那么非参数估计量将是估计总体统计量的最佳方法。然而,在现实生活中,数据并不总是足够的(也不是无限的)。这导致非参数估计失去准确性,成为一个坏的估计。

非参数估计的另一个限制是对数据的敏感性。考虑添加或更改单个数据点会如何影响平均值和方差的估计值。直觉上,一个数据点的微小变化不会显著改变总体的均值和方差。然而,非参数估计的情况并非如此。因为它们完全依赖于数据来导出均值和方差,所以数据点的微小变化会导致估计值的不小变化。这可以用估计量的崩溃点来形式化。估计量的崩溃点被定义为为了改变估计量的值而要改变的数据点的最小比例。这实质上衡量了我们刚才讨论的内容。非参数估计量的崩溃点显然是 1/n,这在稳健统计领域被认为是不好的。

改进非参数

使用非参数估计量的好处是对基础分布的性质没有任何假设。所以,在寻找估计量时,这将给我们最一般的结果。虽然它有局限性,但我们想看看我们是否能保持它的一般性质。

一个可能的扩展是给不同时期的数据一些权重的概念。换句话说,我们对不同时间点的数据有不同的评价。这方面的一个例子是指数加权协方差估计。我最近在这篇文章中读到了这一点,看起来很有希望。这个概念类似于pandas.ewm ,其中每个先前的时间步长被赋予一个较小的权重,通常是小于 1 的某个数的幂。

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

这可以如下实现

def exp_cov(invariants, span=180, frequency=252):
    *"""
    Calculates sample exponentially weighted covariance
    """*
    assets = invariants.columns
    daily_cov = invariants.ewm(span=span).cov().iloc[-len(assets):, -len(assets):]
    return pd.DataFrame(daily_cov*frequency)

注意,权重不需要总是指数的或有序的。考虑这样一种情况,您可能想要估计协方差矩阵,但是数据部分中存在一些波动性聚类。一种方法可能是对聚类内的值给予较大的权重,而对聚类外的值给予较小的权重。这种方法的局限性在于,它需要针对每个数据集进行调整,当数据集非常大时,这可能会变得计算量很大。

结论

总的来说,我们发现定义的估计量是生成数据的基础分布的参数的“估计”。然后,我们讨论了有三种类型的估计:非参数,极大似然和收缩估计。我们探讨了非参数估计量以及如何在 python 中实现它。考虑到它的一些局限性,我们从一篇文章中得到启发,提出了指数加权协方差的扩展,并实现了它。

展望未来,我们将探索最大似然估计量,它们如何优于非参数估计量,以及在什么情况下应该使用它们。

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

原文:https://towardsdatascience.com/estimating-optimal-learning-rate-for-a-deep-neural-network-ce32f2556ce0?source=collection_archive---------1-----------------------

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

在这篇文章中,我正在描述一个简单而强大的方法来找到一个合理的学习率,这是我从 fast.ai 深度学习课程中学到的。我正在三藩市大学亲自参加新版本的课程。它还没有对公众开放,但将于今年年底在 course.fast.ai (目前有去年的版本)上发布。

学习率如何影响培训?

深度学习模型通常由随机梯度下降优化器训练。随机梯度下降有很多变种:Adam,RMSProp,Adagrad 等。它们都可以让你设定学习速度。该参数告诉优化器在与小批量梯度相反的方向上移动权重的距离。

如果学习率低,那么训练更可靠,但是优化将花费大量时间,因为朝向损失函数的最小值的步骤很小。

如果学习率很高,那么训练可能不收敛,甚至发散。重量变化可能如此之大,以至于优化器超过了最小值,使损失更严重。

训练应该从相对较大的学习率开始,因为在开始时,随机权重远非最佳,然后学习率可以在训练期间降低,以允许更细粒度的权重更新。

有多种方法可以为学习速度选择一个好的起点。一个天真的方法是尝试几个不同的值,看看哪个给你最好的损失,而不牺牲训练速度。我们可以从一个像 0.1 这样的大值开始,然后尝试指数级的低值:0.01、0.001 等等。当我们以较大的学习率开始训练时,当我们运行训练的最初几次迭代时,损失不会改善,甚至可能增加。当以较小的学习速率训练时,在某个点,损失函数值在最初几次迭代中开始下降。这个学习率是我们可以使用的最大值,任何更高的值都不会让训练收敛。甚至这个值也太高了:它不足以训练多个时期,因为随着时间的推移,网络将需要更细粒度的权重更新。因此,开始训练的合理学习率可能会低 1-2 个数量级。

一定有更聪明的方法

Leslie N. Smith 在 2015 年的论文“训练神经网络的循环学习率”的第 3.3 节中描述了一种为神经网络选择学习率范围的强大技术。

诀窍是从低学习率开始训练网络,并为每一批以指数方式增加学习率。

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

Learning rate increases after each mini-batch

记录每批的学习率和培训损失。然后,画出损失和学习率。通常情况下,它看起来像这样:

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

The loss decreases in the beginning, then the training process starts diverging

首先,在低学习率的情况下,损失改善缓慢,然后训练加速,直到学习率变得太大,损失增加:训练过程出现偏差。

我们需要在图上选择一个损失减少最快的点。在这个例子中,当学习率在 0.001 和 0.01 之间时,损失函数快速减小。

查看这些数字的另一种方法是计算损失的变化率(损失函数相对于迭代次数的导数),然后在 y 轴上绘制变化率,在 x 轴上绘制学习率。

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

Rate of change of the loss

它看起来太吵了,让我们使用简单移动平均来平滑它。

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

Rate of change of the loss, simple moving average

这个看起来更好。在这张图上,我们需要找到最小值。接近 lr=0.01。

履行

杰瑞米·霍华德和他在 USF 数据研究所的团队开发了 fast.ai ,这是一个深度学习库,是 PyTorch 之上的高级抽象。这是一个易于使用但功能强大的工具集,用于训练最先进的深度学习模型。杰里米在深度学习课程的最新版本( fast.ai )中使用该库。

该库提供了学习率查找器的实现。您只需要两行代码来绘制您的模型在学习率上的损失:

该库没有绘制损失函数变化率的代码,但计算起来很简单:

请注意,在训练之前选择一次学习率是不够的。最佳学习率在训练时下降。您可以定期重新运行相同的学习率搜索过程,以便在培训过程的稍后时间找到学习率。

使用其他库实现方法

我还没有看到像 Keras 这样的其他库准备使用这种学习率搜索方法的实现,但是写起来应该很简单。只需多次运行培训,一次一个小批量。每次小批量后,通过乘以一个小常数来提高学习率。当损耗大大高于先前观察到的最佳值时(例如,当当前损耗>最佳损耗* 4 时),停止该程序。

事情还不止这些

选择学习率的起始值只是问题的一部分。另一个需要优化的是学习进度:如何在训练中改变学习率。传统观点认为,学习率应该随着时间的推移而降低,并且有多种方式来设置这一点:当损失停止改善时的逐步学习率退火、指数学习率衰减、余弦退火等。

我上面提到的论文描述了一种循环改变学习率的新方法。该方法提高了卷积神经网络在各种图像分类任务中的性能。

如果你知道训练深度神经网络的其他有趣的技巧和诀窍,请给我发消息。

另请参见:

[## Fast.ai:我从第 1-3 课中学到了什么

Fast.ai 是一个非常棒的深度学习课程,适合那些喜欢通过做来学习的人。与其他课程不同,在这里您将…

hackernoon.com](https://hackernoon.com/fast-ai-what-i-learned-from-lessons-1-3-b10f9958e3ff) [## 深度学习新闻的最佳来源

深度学习领域非常活跃,可以说每周都有一两个突破。研究论文…

medium.com](https://medium.com/@surmenok/best-sources-of-deep-learning-news-fbc98815bad3) [## 杰夫·迪恩关于大规模深度学习的演讲

杰夫·迪恩是谷歌高级研究员。他领导谷歌大脑项目。2017 年 8 月在 Y Combinator 演讲。的…

becominghuman.ai](https://becominghuman.ai/jeff-deans-talk-on-large-scale-deep-learning-171fb8c8ac57)

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值