TowardsDataScience 博客中文翻译 2021(一百八十六)

原文:TowardsDataScience Blog

协议:CC BY-NC-SA 4.0

DevOps 工程师的自白:冲刺

原文:https://towardsdatascience.com/confessions-of-a-devops-engineer-sprints-1b74631509a1?source=collection_archive---------55-----------------------

如何提高你的冲刺和避免常见的菜鸟错误

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

威廉·艾文在 Unsplash 上的照片

一个故事

在冲刺日,我们反思前两周的成就(或不足)。大约 20 分钟后,我们会跳到 zoom 上,分享我们的想法和反思。我看着我们的黑板。我过滤我的名字,我看到我两周前开始的任务都在进行中。

我可以很容易地解释为什么我不能完成冲刺任务。理由总是包括一些关于需求变化或一些不可预见的障碍或缺乏数据或一些其他“合理”的借口。我的任务和其他人做的完全不同,对吗?

事实是,我的任务和其他人的任务没什么不同。唯一不同的是我缺乏经验。有经验的工程师可以更准确地测量给定任务需要多长时间,然后相应地完成任务。

在这里,我将试着描述一些我犯的新手错误,以及一些在冲刺阶段创建任务的建议。

给出合理的时间估计

我犯的最大错误之一是估计完成一项任务需要多长时间。现在,我的估计如此不准确的原因之一是因为我缺乏经验,不知道完成一项任务需要多长时间。如果你从未攀登过珠穆朗玛峰,就很难确切知道要爬多长时间。

为了解决这个时间估计问题,我试着更细致地思考,并依靠我更有经验的队友来帮助我估计任务。当我说“考虑得更细”时,我并不是指考虑所需的每一行代码和测试,而是考虑完成任务所需的更大的步骤。一个很好的例子可能是部署一个新特性。这里,较大的步骤包括编写、审查、测试,然后部署代码。根据特性的性质,编写代码可能需要几个小时,审查和测试可能需要一天,部署代码可能需要一两天。因此,在这里,我们可以估计大约 4-5 天来开发这一新功能。比你最初想象的要长,对吗?

有时,当我们定义 sprint 任务时,队友和经理可能会质疑这些估计。他们可能会说“嘿,我不认为这需要 X 天;应该只需要一半的时间”。现在,如果你对完成任务需要做什么还没有一个坚实的理解,你可能很容易被说服同意。重要的是在下一个 sprint 计划之前花一些时间,定义必要的任务,并估计完成它们需要多长时间。

清除任务输入和输出

在创建新任务之前,清楚地定义什么是输入和输出是很重要的。输入包括您的时间、精力和其他材料,如设计文档。输出等于所需的东西,例如新产品功能。

这些输入和输出定义得越清楚,你的团队和管理层就越清楚你已经完成了什么或者你正在努力完成什么。

下面是一个错误任务定义的示例:

输入:3 天

输出:新功能

所以我们来解剖一下。输入是 3 天的工作,相当于大约 27 小时的专用时间(假设每天工作 9 小时)。输出是一个“新特征”。这个新功能到底是什么?完成这个模糊的目标不需要其他先决条件?您是否有访问代码库的权限?这个任务的完成意味着特性被部署到客户那里,还是仅仅意味着代码在本地工作?

好吧,让我们稍微改进一下我们的例子:

输入:3 天,bob 的设计文档

输出:改进控制台横幅

这是一个改进,因为我们现在引用的设计文档可能提供了方向。我们的输出包括一些关于开始构建的清晰性,但是定义的任务仍然非常模糊。3 天也是相当多的时间。通常,当分配给某个特定任务的时间超过 2 天时,这是一个危险信号,表明该任务可以被分解成更小的部分。

我将提供一个相当不错的任务定义的例子,而不是描述更多糟糕的例子:

输入:1 天

输出:设计文档,详细说明控制台横幅搜索索引到数据库的实施

输入:. 5 天,设计文档

输出:与团队一起评审设计文档

输入:0.5 天,Jim Henderson(开发)支持和实施

输出:为控制台横幅搜索添加索引

输入:. 5 天,马克·约翰逊(DevOps)支持与监测结果

输出:本地测试为控制台横幅搜索添加的索引

输入:. 5 天,测试结果,技术主管支持批准拉动式请求

输出:审查本地测试的代码和结果,提交并合并到开发环境中

输入:1 天,Jenn Smith (DevOps)支持部署

输出:向客户部署改进的控制台横幅搜索

希望你能明白。任务需要很长时间才能完成,并且不完全依赖于你的技能和专业知识。通常需要一个村庄来完成一项任务。任何失败都会产生重大后果。

反思和迭代

这听起来可能很明显,但重要的是反思你定义的目标,以及你是否能够及时完成这些目标。在本文的开头,我设置了一个场景,反思我和我的团队最近的冲刺。在那些场合的积极反思帮助我思考如何提高我的短跑。

我问自己“为什么我不能完成这个任务”,“我的任务定义太模糊了”或者“我给自己足够的时间了吗”?

我鼓励每个人花时间问自己这些难题,并跟踪进展。也许有过创建带有底层子任务的任务的经历。也许允许自己在编写初始代码后调整评估。测量初始时间估计和实际时间估计怎么样。也许早先我们的初始估计和实际估计相差很大,但正在慢慢地趋于一致。

置信区间与预测区间

原文:https://towardsdatascience.com/confidence-intervals-vs-prediction-intervals-7b296ae58745?source=collection_archive---------3-----------------------

混淆这两者可能代价高昂。了解它们的不同之处以及何时使用它们!

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

置信区间和预测区间都表示统计估计的不确定性。然而,每一个都与来自不同来源的不确定性有关。有时,人们可以用相同的数量来计算这两者,这导致了在解释统计模型时的混乱和潜在的严重错误。让我们看看它们有什么不同,它们表达了什么样的不确定性,以及何时使用它们。

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

回归模型中的不确定区间

让我们从实际出发,用一个简单的线性回归模型来拟合加州住房数据。我们将只使用前 200 条记录,并跳过第一条作为测试用例。该模型基于一个单一的预测值,即邻居的中值收入来预测房价。我们只使用了一个预测值,以便能够很容易地看到 2D 的回归线。

在模型总结中,我们看到了下表。

===========================================================
          coef  std err       t   P>|t   [0.025    0.975]
-----------------------------------------------------------
const   0.7548    0.078   9.633   0.000   0.600   0.909
MedInc  0.3813    0.021  18.160   0.000   0.340   0.423

邻里收入中位数的系数 MedInc 为 0.3813,其 95%的区间为 0.340 — 0.423。这是一个置信区间。置信区间与从多个值估计的统计量有关,在这种情况下是回归系数。它表达了**采样不确定性,**这是因为我们的数据只是我们试图建模的人口的随机样本。它可以解释如下:如果我们收集了许多其他关于加州房屋的数据集,并为每个数据集拟合了这样一个模型,在 95%的情况下,真实人口系数(如果我们有加州所有房屋的数据,我们就会知道这个系数)将落在置信区间内。

置信区间属于从多个值估计的统计量。它表示抽样不确定性。

现在,让我们使用该模型对我们在培训中忽略的第一个观察结果进行预测。代替predict()方法,我们将使用get_predict()结合summary_frame()来提取更多关于预测的信息。

我们得到以下数据帧:

 mean mean_se mean_ci_lower mean_ci_upper obs_ci_lower obs_ci_upper
3.9295  0.1174      3.697902      4.161218     2.711407     5.147713

这个房子的预测值是 3.9295。现在,mean_ci列包含本次预测的置信区间的下限和上限,而obs_ci列包含本次预测的预测区间的下限和上限。

您可以立即看到预测区间比置信区间宽得多。我们可以通过使用该模型来预测一系列不同邻里收入的房价,从而很好地可视化它,这样我们就可以看到回归线和预测值周围的区间。

现在,pred就像以前一样,只有 500 行,包含 0 到 15 之间 500 个不同收入值的预测和区间界限。我们现在可以用它来绘制回归线及其周围的区间。

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

周围有间隔的回归线。图片由作者提供。

这里有两个主要的东西要看。首先,收入中值在 2 到 5 之间时,置信区间较窄,在更极端的值时,置信区间较宽。这是因为,对于数据中的大多数记录,收入在 2 到 5 之间。在这种情况下,模型有更多的数据,因此抽样不确定性较小。

第二,预测区间比置信区间宽得多。这是因为表达了更多的不确定性。除了采样不确定性之外,预测区间还表示特定数据点的固有不确定性。

预测区间表达了采样不确定性之上的特定数据点的固有不确定性。因此它比置信区间更宽。

这种数据点级别的不确定性来自于这样一个事实,即在同一个邻域中可能有多个价值不同的房屋,因此在模型中具有相同的预测值。这在这个例子中很明显,但在其他情况下也是如此。非常相似或者甚至完全相同的多个特征向量与不同的目标值相关联。

让我们回顾一下:

  • 置信区间表示从许多数据点估计的数量的抽样不确定性。数据越多,采样不确定性越小,因此间隔越小。
  • 除了采样不确定性之外,预测区间也表示单个值周围的不确定性,这使得它们比置信区间更宽。

但是这些区间从何而来,它们又是如何包含这些不同的不确定性来源的呢?接下来我们就来看看吧!

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

音程从何而来

在传统的统计学中,人们会将预测 y-hat 周围的区间计算为

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

其中 t-crit 是 t 分布的临界值,SE 是预测的标准误差。对于置信区间和预测区间,右侧的两个数字将是不同的,并且是基于各种假设计算的。

然而,统计学中参数假设的时代幸运地即将结束。最近计算能力的提高允许使用简单的、一刀切的重采样方法来进行统计。因此,与其用推导和公式来烦你,不如让我向你展示如何通过重采样来构造这两种类型的区间。这种方法不仅适用于线性回归,而且基本上适用于你能想到的任何机器学习模型。此外,它将使人们瞬间清楚哪种不确定性被哪个区间所覆盖。

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

拔靴带

我们将使用的重采样技术是自举。归结起来就是从原始数据中抽取许多样本,比如说 10 000 个样本,然后替换掉。这些被称为引导样本,因为我们是用替换来绘制的,相同的观察结果可能在一个引导样本中出现多次。这样做的目的是从一个假设的总体中获得许多样本,以便我们可以观察抽样的不确定性。接下来,我们对每个 bootstrap 样本分别执行我们想要的任何分析或建模,并计算感兴趣的量,例如模型参数或单个预测。一旦我们有了这个量的 10 000 个自举值,我们就可以查看百分位数来得到区间。整个过程如下图所示。

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

改编自作者在 DataCamp 教授的 R 课程中的用插补处理缺失数据。

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

自举置信区间

让我们用 bootstrap 置信区间来预测一所房子的价值,该房子位于中值收入为 3 英镑的社区。我们采用 10 000 个 bootstrap 样本,对每个样本拟合一个回归模型,并预测 MedInc 等于 3。这样,我们得到了 10 000 个预测。我们可以打印它们的平均值,以及表示置信区间下限和上限的百分位数。

Mean pred: 1.9019164610645232
95% CI: [1.83355697 1.97350956]

这个 bootstrap 样本考虑了抽样的不确定性,所以我们得到的区间是一个置信区间。现在让我们看看如何引导一个预测区间。

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

引导预测区间

除了采样不确定性之外,预测间隔还应该考虑特定预测数据点的不确定性。为此,我们需要对代码做一个小小的改动。一旦我们从模型中获得预测,我们也从模型中提取随机残差,并将其添加到该预测中。通过这种方式,我们可以将个体预测的不确定性包含在 bootstrap 输出中。

Mean pred: 1.9014631013163406
95% PI: [1.07444778 2.72920388]

正如所料,预测区间明显比置信区间宽,即使平均预测是相同的。

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

感谢阅读!

如果你喜欢这篇文章,为什么不在我的新文章上 订阅电子邮件更新 ?通过 成为媒介会员 ,你可以支持我的写作,并无限制地访问其他作者和我自己的所有故事。

需要咨询?你可以问我任何事情,也可以在这里 预定我 1:1

你也可以试试我的其他文章。不能选择?从这些中选择一个:

</8-tips-for-object-oriented-programming-in-python-3e98b767ae79> </6-useful-probability-distributions-with-applications-to-data-science-problems-2c0bee7cef28>

Python 中的置信区间

原文:https://towardsdatascience.com/confidence-intervals-with-python-bfa28ebb81c?source=collection_archive---------6-----------------------

用 Python 实现大学统计

介绍

在一系列的每周文章中,我将会涉及一些重要的统计学主题。

目标是使用 Python 来帮助我们获得对复杂概念的直觉,从经验上测试理论证明,或者从零开始构建算法。在本系列中,您将会看到涵盖随机变量、抽样分布、置信区间、显著性检验等主题的文章。

在每篇文章的最后,你可以找到练习来测试你的知识。解决方案将在下周的文章中分享。

迄今发表的文章:

像往常一样,代码可以在我的 GitHub 上找到。

置信区间和误差幅度

一群学生试图理解《老友记》中哪个角色最有趣,结果是钱德勒·宾和罗斯·盖勒。

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

图 1: *《老友记》*是一部美国电视情景喜剧,围绕住在纽约曼哈顿的六个二三十岁的朋友展开。

他们对罗斯实际获胜的可能性感兴趣,因为与钱德勒讽刺和诙谐的幽默感相比,他有一种非常笨拙的幽默感。他们决定在学校里发起一次投票。理想情况下,他们会询问全体学生,但很快他们就明白询问 5000 名学生的偏好是不可行的。相反,他们决定随机抽取 40 名学生,计算支持罗斯的样本比例。他们得出的第一个值是 p̂=0.61.

请注意,为了继续他们的研究,这组学生需要确保满足计算某个比例的有效置信区间的条件。有三种情况:

  • 样本必须是随机的。
  • 正态分布可以近似样本比例的抽样分布。经验法则是,你至少需要有 10 次成功和 10 次失败。
  • 要求样本是独立的。经验法则是,如果你是在没有替换的情况下抽样,你的样本量应该少于总体量的 10%。
import numpy as np
import seaborn as sns
import math
from scipy.stats import bernoulli, norm, t, skewnorm
import matplotlib.pyplot as pltp_hat = 0.61
n = 40print('Normal conditions:')
print('successes >= 10: ' + str(n*p_hat >= 10))
print('failures >= 10 : ' + str(n*(1-p_hat) >= 10))
print('--')
print('Independence condition:')
print(40/5000 < 0.1)Normal conditions:
successes >= 10: True
failures >= 10 : True
--
Independence condition:
True

所有条件都满足后,这组学生现在可以专注于构建样本比例的抽样分布;根据这一分布,他们计算了可能得到的样本比例及其可能性。

我们已经看到,抽样分布的平均值是实际总体比例 p 和样本比例的标准偏差:

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

让我们开始把这些概念和置信区间的概念联系起来。p̂ = 0.61 在范围内的概率是多少

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

对于正态分布,这大约是 95%。这相当于说有 95%的概率 p 在内

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

这是置信区间的基本概念。

现在,我们有一个问题。我们不知道 p ,所以我们需要使用一个估计值。我们最好的估计自然是 p̂.因此,不使用

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

我们使用标准误差:

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

计算我们的置信区间。

SE_hat_p = np.sqrt(p_hat*(1-p_hat)/n)
print(f'With 95% confidence between {np.round(p_hat - 2*SE_hat_p, 2)} and {np.round(p_hat + 2*SE_hat_p, 2)} of students prefer the awkward humor of Ross.')With 95% confidence between 0.46 and 0.76 of students prefer the awkward humor of Ross.

请注意,我们上面计算的置信区间可以根据我们实际选择的样本比例而变化。如果该组学生再次抽样 40 名新学生,则新的样本比例现在可以是 0.55。

p_hat = 0.55
n = 40
SE_hat_p = np.sqrt(p_hat*(1-p_hat)/n)
print(f'With 95% confidence between {np.round(p_hat - 2*SE_hat_p, 2)} and {np.round(p_hat + 2*SE_hat_p, 2)} of students prefer the awkward humor of Ross.')With 95% confidence between 0.39 and 0.71 of students prefer the awkward humor of Ross.

我们可以把这个概念和误差范围联系起来。我们第一次试验的误差幅度(知道我们有兴趣获得 95%的置信度)是我们 SE 的 2 倍。

一个经常出现的有趣问题是“你能做些什么来减少误差幅度”?请注意,误差幅度取决于 SE,SE 与样本大小成反比。因此,减少误差的一个可能方法是增加样本量。

print(f'Margin of error = {2*SE_hat_p}')Margin of error = 0.15732132722552272

同样的推理也适用。根据我们的样本比例,我们的误差幅度可能会有不同的值。

其思想是,如果我们重复使用这种计算置信区间的方法,每次都会产生不同的区间(取决于样本比例),其中 95%的时间包含真实比例。

confidence_interval=0.95
p = 0.61
n = 50
number_trials = 25

p_hat_list = []
SE_hat_p_list = []

for i in range(number_trials):
    s_ = bernoulli.rvs(p=p, size=n)
    p_hat = s_[s_==1].shape[0] / s_.shape[0]
    p_hat_list.append(p_hat)
    SE_hat_p_list.append(2*np.sqrt(p_hat*(1-p_hat)/n))j=0
_, ax = plt.subplots(1, 1, figsize=(6, 8))
for i in range(len(p_hat_list)):
    if (p>p_hat_list[i]-SE_hat_p_list[i]) & (p<p_hat_list[i]+SE_hat_p_list[i]):
        # interval contains p
        ax.errorbar(p_hat_list[i], np.arange(len(p_hat_list))[i],lolims=True, xerr=SE_hat_p_list[i], yerr=0.0, linestyle='', c='black')
        j +=1
    else:
        # interval does not contain p
        ax.errorbar(p_hat_list[i], np.arange(len(p_hat_list))[i],lolims=True, xerr=SE_hat_p_list[i], yerr=0.0, linestyle='', c='red')
ax.axvline(0.61, color='darkorange')
plt.xlim(0,1)
plt.show()
print(f'{j}/{number_trials}={np.round(j/number_trials,2)}')

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

图 2:样本比例的置信区间。

24/25=0.96

我们正在绘制样本比例 p̂和区间:

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

注意,大约 96%的样本区间包含真实比例 p 。随着样本数量的增加,这个数字将收敛到 95%。

number_trials = 2000

j=0
for i in range(number_trials):
    p_hat = bernoulli.rvs(p=p, size=n)
    p_hat = p_hat[p_hat==1].shape[0] / p_hat.shape[0]
    SE_hat_p = 2*np.sqrt(p_hat*(1-p_hat)/n)
    if (p>p_hat-SE_hat_p) & (p<p_hat+SE_hat_p):
        # interval contains p
        j +=1

print(f'{j}/{number_trials}={np.round(j/number_trials,2)}')1877/2000=0.94

如果我们对 99%的置信区间感兴趣呢?我们需要计算特定置信水平的临界值,也称为 z*。临界值只不过是低于和高于平均值的标准偏差的数量,我们需要得到这个值来获得期望的置信水平(99%)。请注意,使用 z 表或使用来自scipynorm.ppf时,请记住您获得的值是针对单尾置信区间的。这不是我们想要的,所以我们需要得到 99.5%的值(在分布的每个尾部留下 0.5%给出 99%的置信度)。

CI = 0.99
critical_value = norm.ppf(CI+(1-CI)/2) # we want the critical value for a two-tail distribution
critical_value2.5758293035489004

有 99%的可能性 p 在:

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

number_trials = 1000

j=0
for i in range(number_trials):
    p_hat = bernoulli.rvs(p=p, size=n)
    p_hat = p_hat[p_hat==1].shape[0] / p_hat.shape[0]
    SE_hat_p = critical_value*np.sqrt(p_hat*(1-p_hat)/n)
    if (p>p_hat-SE_hat_p) & (p<p_hat+SE_hat_p):
        # interval contains p
        j +=1

print(f'{j}/{number_trials}={np.round(j/number_trials,2)}')994/1000=0.99

比例的有效置信区间的条件

让我们首先回忆一下比例有效区间的条件:

  • 样本必须是随机的。
  • 正态分布可以近似样本比例的抽样分布。经验法则是,你至少需要有 10 次成功和 10 次失败。
  • 要求样本是独立的。经验法则是,如果你是在没有替换的情况下抽样,你的样本量应该少于总体量的 10%。

为了帮助我们理解其中的含义,我们将举例说明当其中一个条件不满足时会发生什么。首先,让我们创建一个函数来计算置信区间,并绘制最后 50 个样本。

def confidence_interval(p, n, number_trials, N, ci=0.95, sample='random'):
    p_ = bernoulli.rvs(p=p, size=N)
    p_hat_list = []
    SE_hat_p_list = []

    if sample!='random':
        # Inducing bias on the sampling
        p_.sort()
        p_ = p_[:-int(0.2*N)]
        np.random.shuffle(p_)

    for i in range(number_trials):
        s_ = np.random.choice(p_, n, replace=False)
        p_hat = s_[s_==1].shape[0] / s_.shape[0]
        p_hat_list.append(p_hat)
        SE_hat_p_list.append(2*np.sqrt(p_hat*(1-p_hat)/n))

    j=0
    _, ax = plt.subplots(1, 1, figsize=(6, 8))
    for i in range(len(p_hat_list)):
        if (p>p_hat_list[i]-SE_hat_p_list[i]) & (p<p_hat_list[i]+SE_hat_p_list[i]):
            # interval contains p
            if i > len(p_hat_list)-50:
                ax.errorbar(p_hat_list[i], np.arange(len(p_hat_list))[i],lolims=True, xerr=SE_hat_p_list[i], yerr=0.0, linestyle='', c='black')
            j +=1
        else:
            # interval does not contain p
            if i > len(p_hat_list)-50:    
                ax.errorbar(p_hat_list[i], np.arange(len(p_hat_list))[i],lolims=True, xerr=SE_hat_p_list[i], yerr=0.0, linestyle='', c='red')
    ax.axvline(0.61, color='darkorange')
    plt.xlim(0,1)
    plt.show()
    print(f'{j}/{number_trials}={np.round(j/number_trials,2)}')

第一个例子是我们的样本不是随机的,也就是说,我们从总体中取样的方式会引入一些偏差。参考我们的上下文,这可能意味着我们的学生小组正在调查学校喜剧俱乐部之外的人,钱德勒的笑话更有效地与他们联系在一起。我们的信心突然下降到 90%以下。

confidence_interval(p=0.61, n=35, number_trials=1000, N=500, sample='not_random')

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

图 3:非随机抽样的样本比例的置信区间。

884/1000=0.88

第二种情况是,我们不能假设我们的抽样分布是正态的。请注意,我们的抽样规模是 10,这并不保证成功和失败超过 10 次。同样,即使我们计算出 95%的置信区间,真实比例 p 在计算区间内的次数百分比大约是 90%。

n = 10
print('Normal conditions:')
print('successes >= 10: ' + str(n*p_hat >= 10))
print('failures >= 10 : ' + str(n*(1-p_hat) >= 10))Normal conditions:
successes >= 10: False
failures >= 10 : Falseconfidence_interval(p=0.61, n=10, number_trials=1000, N=500)

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

图 4:非正态分布样本比例的置信区间。

897/1000=0.9

最后,最后一个条件是样本之间的独立性。如果不满足 10%的经验法则,我们就不能假设独立。我们的信心再次下降到接近 90%。

n = 150
N=600
print('Independence condition:')
print(n/N < 0.1)Independence condition:
Falseconfidence_interval(p=0.61, n=n, number_trials=1000, N=N)

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

图 5:不满足独立性标准的样本比例的置信区间。

904/1000=0.9

现在我们已经看到了所有不满足条件的情况,让我们创建一个通过所有 3 个测试的情况。

confidence_interval(p=0.61, n=35, number_trials=1000, N=500)

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

图 6:满足所有 3 个标准的样本比例的置信区间。

947/1000=0.95

我们的信心有效地收敛到 95%。我们可以对自己的自信充满信心。

估计总体均值

我们一直在解决估计人口比例的问题,人口中有百分之几的人更喜欢罗斯的幽默而不是钱德勒的幽默。一个不同的问题是估计人口的平均数。让我们来看看主要的区别。当我们估计人口比例的置信区间时,我们定义:

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

根据同样的原则,我们将总体平均值定义为:

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

请注意,我们不知道我们的总体标准差,所以我们使用我们的最佳估计,样本标准差。不幸的是,如果我们使用这种方法来计算我们的置信区间,我们将会低估实际的区间。为了达到 95%的置信度,我们需要使用基于 t 分布的不同临界值。

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

让我们做几个实验来证明我们的观点。首先,我们基于样本标准偏差定义均值的置信区间,但从正态分布计算临界值。

def confidence_interval_mean(μ, σ, n, number_trials, N, ci=0.95, sample='random'):
    x_ = norm.rvs(loc=μ, scale=σ, size=N)
    x_hat_list = []
    SE_hat_x_list = []

    if sample!='random':
        # Inducing bias on the sampling
        x_.sort()
        x_ = x_[:-int(0.2*N)]
        np.random.shuffle(x_)

    for i in range(number_trials):
        s_ = np.random.choice(x_, n, replace=False)
        x_hat = np.mean(s_)
        x_hat_list.append(x_hat)
        SE_hat_x_list.append(norm.ppf(ci+(1-ci)/2)*np.std(s_)/np.sqrt(n))

    j=0
    _, ax = plt.subplots(1, 1, figsize=(6, 8))
    for i in range(len(x_hat_list)):
        if (μ>x_hat_list[i]-SE_hat_x_list[i]) & (μ<x_hat_list[i]+SE_hat_x_list[i]):
            # interval contains p
            if i > len(x_hat_list)-50:
                ax.errorbar(x_hat_list[i], np.arange(len(x_hat_list))[i],lolims=True, xerr=SE_hat_x_list[i], yerr=0.0, linestyle='', c='black')
            j +=1
        else:
            # interval does not contain p
            if i > len(x_hat_list)-50:    
                ax.errorbar(x_hat_list[i], np.arange(len(x_hat_list))[i],lolims=True, xerr=SE_hat_x_list[i], yerr=0.0, linestyle='', c='red')
    ax.axvline(μ, color='darkorange')
    #plt.xlim(0,1)
    plt.show()
    print(f'{j}/{number_trials}={np.round(j/number_trials,2)}')confidence_interval_mean(2, 0.5, 12, 2000, 1000)

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

图 7:使用 z*计算的样本均值的置信区间。

1837/2000=0.92

我们期待的事情发生了,因为真正的平均值只有 92%的时间包含在我们的置信区间内。这不是有意的,因为我们正在计算平均值的 95%置信区间。

在第二个实验中,现在使用的临界值是从 t 分布计算出来的。

def confidence_interval_mean_t(μ, σ, n, number_trials, N, ci=0.95, sample='random'):
    x_ = norm.rvs(loc=μ, scale=σ, size=N)
    x_hat_list = []
    SE_hat_x_list = []

    if sample!='random':
        # Inducing bias on the sampling
        x_.sort()
        x_ = x_[:-int(0.2*N)]
        np.random.shuffle(x_)

    for i in range(number_trials):
        s_ = np.random.choice(x_, n, replace=False)
        x_hat = np.mean(s_)
        x_hat_list.append(x_hat)
        SE_hat_x_list.append(t.ppf(ci+(1-ci)/2, df=n-1)*np.std(s_)/np.sqrt(n))

    j=0
    _, ax = plt.subplots(1, 1, figsize=(6, 8))
    for i in range(len(x_hat_list)):
        if (μ>x_hat_list[i]-SE_hat_x_list[i]) & (μ<x_hat_list[i]+SE_hat_x_list[i]):
            # interval contains p
            if i > len(x_hat_list)-50:
                ax.errorbar(x_hat_list[i], np.arange(len(x_hat_list))[i],lolims=True, xerr=SE_hat_x_list[i], yerr=0.0, linestyle='', c='black')
            j +=1
        else:
            # interval does not contain p
            if i > len(x_hat_list)-50:    
                ax.errorbar(x_hat_list[i], np.arange(len(x_hat_list))[i],lolims=True, xerr=SE_hat_x_list[i], yerr=0.0, linestyle='', c='red')
    ax.axvline(μ, color='darkorange')
    #plt.xlim(0,1)
    plt.show()
    print(f'{j}/{number_trials}={np.round(j/number_trials,2)}')confidence_interval_mean_t(2, 0.5, 12, 2000, 1000)

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

图 8:使用 t*的样本均值的置信区间。

1892/2000=0.95

我们的信心有效地收敛到 95%。再一次,我们可以对自己的自信充满信心。

有效 t 间隔的条件

我们已经看到了比例有效区间的条件。在 t 间隔的情况下,同样的规则适用。区别在于如何验证我们的分布是否可以被认为是正态分布。:

  • 样本必须是随机的。
  • 样本均值的抽样分布可以近似为正态分布。有三种方法可以实现:样本量大于 30(中心极限定理适用),原始分布是正态的,或者原始分布是对称的。
  • 要求样本是独立的。经验法则是,如果你是在没有替换的情况下抽样,你的样本量应该少于总体量的 10%。

我们把证明上述要点的实验作为本周的练习。

结论

在本文中,我们讨论了置信区间和误差幅度等概念。我们从定义和计算样本比例的置信区间开始。要计算这样的置信区间,必须满足 3 个条件。我们模拟了 3 种不满足条件的场景。通过分析这些影响,我们观察到在每个场景中引入的偏差影响了我们的信心水平。

我们还解决了计算样本均值置信区间的问题。在这种情况下,用于计算的临界值不能基于正态分布,而是基于 t 分布。通过模拟大量样本,我们展示了基于正态分布的临界值是如何低估实际置信区间的。最后,与我们对样本比例所做的一样,我们建立了有效 t 区间的条件。

保持联系: LinkedIn

练习

你将在下周的文章中找到答案。

  1. 更改函数confidence_interval_mean_t并构建 5 个不同的实验来计算样本均值的 95%区间,其中 3 个不满足 t 区间的条件,2 个满足。对于不满足条件的 3,定义以下情况:抽样不随机,原始分布不近似正态,不满足独立性。对于满足条件的两种情况,定义一种情况下原始分布是正态分布,另一种情况下原始分布是偏斜的,但采样均值是正态分布。对于后两种情况,真正的总体均值应该包含在 95%的计算置信区间内。

提示:您可能会发现使用 *scipy* 中的 *skewnorm* 函数很有用。下面,您有一个正态分布的修改版本,由偏斜度参数、平均值和标准偏差来偏斜。

# code adapted from https://stackoverflow.com/questions/49367436/scipy-skewnorm-mean-not-matching-theory

skew = 4.0
mean = 2
stdev = 0.5

delta = skew / math.sqrt(1\. + math.pow(skew, 2.))
adjStdev = math.sqrt(math.pow(stdev, 2.) / (1\. - 2\. * math.pow(delta, 2.) / math.pi))
adjMean = mean - adjStdev * math.sqrt(2\. / math.pi) * delta

print('target mean={:.4f} actual mean={:.4f}'.format(mean, float(skewnorm.stats(skew, loc=adjMean, scale=adjStdev, moments='mvsk')[0])))
print('target stdev={:.4f} actual stdev={:.4f}'.format(stdev, math.sqrt(float(skewnorm.stats(skew, loc=adjMean, scale=adjStdev, moments='mvsk')[1]))))target mean=2.0000 actual mean=2.0000
target stdev=0.5000 actual stdev=0.5000# Original skewed distribution

plt.hist(skewnorm.rvs(a = skew, loc=adjMean, scale=adjStdev, size=2000), bins=50);

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

# Approximately normal distribution of the sample mean because sample 
# size is bigger than 30 (CTL applies)

plt.hist(np.mean([skewnorm.rvs(a = skew, loc=adjMean, scale=adjStdev, size=35) for _ in range(2000)], axis=1), bins=50);

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

上周的答案

  1. 里克在一个遥远的星球上对 75 名公民进行了 SRS 调查,以了解抽样调查的公民中有多少人对自己的生活水平感到满意。假设生活在这个星球上的 10 亿公民中有 60%对自己的生活水平感到满意。对生活水平满意的公民比例抽样分布的均值和标准差是多少?
mu_hat_p = 0.6
print(mu_hat_p)

sigma_p_hat = np.sqrt(0.6*(1-0.6)/75)
print(sigma_p_hat)0.6
0.0565685424949238

2.某个拥有超过 1,000,000 个家庭的星球的平均家庭收入为 1,000,000 美元,标准差为 150,000 美元。Rick 计划随机抽取 700 个家庭样本,计算样本平均收入。计算 x̄.抽样分布的平均值和标准差

μ = 1000000
σ = 150000
n = 700

print(f'μ_x_bar = {μ}')
print(f'σ_x_bar = {σ/n**(1/2)}')μ_x_bar = 1000000
σ_x_bar = 5669.467095138409

3.Rick 正在对不同的入口枪进行质量控制测试,因为在制造过程中存在一些可变性。某枪靶厚 5mm。厚度分布向右倾斜,平均值为 5 毫米,标准偏差为 1 毫米。该零件的质量控制检查包括随机抽取 35 个点,并计算这些点的平均厚度。样本平均厚度的抽样分布是什么形状?样品中的平均厚度在目标值 0.2 毫米以内的概率是多少?

# Since n = 35 >= 30, the central limit theorem applies.
# Even though the population is skewed to the right, the sample means
# are normally distributed due to the sample size.μ = 5
σ = 1
n = 100norm.cdf(5.2, μ, σ/n**(1/2)) - norm.cdf(4.8, μ, σ/n**(1/2))0.9544997361036418

使用数据类的 Python 配置文件

原文:https://towardsdatascience.com/configuration-files-in-python-using-dataclasses-ec8528e72e01?source=collection_archive---------12-----------------------

使用 dataclasses 对 Python 中的配置文件进行类型安全解析

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

作者图片

TL;速度三角形定位法(dead reckoning)

有了 Python dataclasses和新的dataconf库,我们现在可以安全地将配置文件解析成数据类。对于来自 Scala 的用户来说,这是从 case 类和 PureConfig 类型安全解析的简单过渡。要查看 Python 和 PySpark 用例中的示例用法,请跳到用法。

介绍

啊,配置文件。一个人必须爱他们,对不对?也许吧?看情况。对于那些使用 Scala 和其他 JVM 语言的人,我们可以使用 HOCON 、json 的人类可读格式、typesafe configpureconfig 轻松地将复杂的配置或属性文件直接加载到 case 类中。有了这些,生活是美好的。我们的 Python 用户呢?

数据类的介绍

在 Python 3.7 中,数据类通过简单的 pip 安装向后兼容 Python 3.6。通过这个介绍,Python 本质上引入了可变格式的 Scala case 类。但是,dataclasses可以被冻结以实现不可变的变体。有了这个介绍,我们的 Python 用户能实现同样的简化的配置文件解析吗?还没有。的确,PyHocon 已经存在了很多年,但是仍然缺少了一些东西。2020 年 5 月,Github 用户 @zifeo 将他的库 dataconf 发布到 PyPI,这是链中的最后一环。

数据会议库

dataconf所做的是允许用户读入带有定义参数的配置文件,并直接输入到 Python dataclass中。大约在 2021 年 8 月,我在寻找一种将配置文件轻松传递到 Python 的方法时偶然发现了这个库。根据我使用 Scala 的经验和对 Python 的dataclasses的了解,我很高兴看到这个功能。在过去的几个月里,我添加了一些已经在版本0.1.50.1.60.2.0中发布的附加特性,以进一步复制pureconfig。目前,dataconf已经快速成熟,目前是版本0.3.0。由于缺少 Python 3.7.x中没有的更新,dataconf将只能在 Python >= 3.8.x上工作。

True Digital Group 这里,我们正在开发一个定制的 MLOps 管道,用 Python 以自动化的方式为我们的用户和客户服务。然而,为了编排这些管道,我们将使用类似于我们在 Scala 中构建的数据管道的配置文件。答案是。我添加了解析嵌套配置的能力,并使用 Python 中的抽象基类dataclasses模拟 Scala 密封特征的行为。这个库可能并不完美,但是我们现在可以依赖它来满足我们的 Python 管道需求。

为了使用dataconf,用户入口点主要是loadloads。然而,如果传递ConfigTree对象,它们将需要使用__parse。当前的计划是在未来的版本中,用from_configfrom_filefrom_string重构用法,使之类似于pureconfig或另一种类似的模式。带代码的演示报告可在这里找到。最后注意,版本0.2.0和更低版本不能解析-,所以使用版本0.2.1或更高版本。

用法示例

假设我们需要运行一个管道,接收数据或数据源,进行一些处理,然后将数据写出来。然而,数据可能来自 Python 中许多不同的文件格式,或者来自表、sql 查询或 HDFS 路径。在这种情况下,使用配置文件、数据类和dataconf可以简化我们的工作并避免分支。在示例中,我使用抽象元类来处理不同的输入类型。有了这个,我可以让PipeParamsParams手柄决定dataclass匹配。所有的类都带有load_df,所以我们可以使用相同的方法名调用来加载数据帧,而不管哪个被解析。下面的例子仅仅是关于如何使用 dataclasses 和dataconf来简化你的产品编码的皮毛。

原载于 2021 年 10 月 25 日https://tech . true analytics . ai

使用传统的机器学习算法配置 CNN 模型

原文:https://towardsdatascience.com/configure-a-cnn-model-using-traditional-machine-learning-algorithms-ac31a11e1c12?source=collection_archive---------21-----------------------

将集成学习算法应用于影像数据集,影像数据集是通过 python 实现由卷积图层提取的要素

***Table of Contents* 1\. Introduction
2\.** [**Layers**](#096c) **2.1\. Convolutional Layer
2.2\. Pooling Layer
2.3\. Dropout Layer
2.4\. Flatten Layer
3\.** [**Tutorial**](#5928) **3.1\. Dense Layer Approach
3.2\. Ensemble Learning Approach
4\. Results
5\.** [**Discussion**](#bab4)

1.介绍

在传统的机器学习应用中,在对数据集应用必要的数据预处理过程之后,它主要被转换成 (n_samples,n_features) 并应用该算法。为了避免过拟合和欠拟合等情况,样本的数量应该很大。为了防止这种情况,或者通过各种方法来扩展图像数据集的图像扩充,或者应用诸如特征提取、特征选择或维数减少的方法。

卷积神经网络(CNN)是一种深度学习方法,主要用于图像数据集。它通过用人工神经网络训练模型来用于分类。当我们处理该模型时,给定图像数据集的特征与其结构中的层一起被提取,并且这些获得的特征由诸如密集层的各种层训练。

本文包括如何使用集成学习算法对使用卷积层提取特征的图像数据集进行分类。python 实现丰富了这项工作。

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

照片由尤里·赛洛斯Unsplash 上拍摄

2.层

首先,让我们简要了解一下在构建本教程中使用的模型时使用的图层:

2.1.卷积层

卷积层是卷积神经网络(CNN)的主要构件。它们将像素值作为输入,并执行特征提取。它由过滤器和内核组成。学习是通过从数据集中提取一个子集,然后对其进行过滤和处理来进行的。利用线性乘法来执行这些处理,并且提取关于图像的诸如边缘检测之类的特征。图 1 显示了由具有不同内核的 cv2 库提供的梯度滤波器的应用。

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

图一。内核在渐变滤镜中的效果,图片作者

如果我们再深入一步,这个过程是如何发生的?如上所述,它是一个简单的数学运算,名为卷积。用数学来说明:

输入= [ 5 10 15 20 25 30]

过滤器= [0 1 0]

输出计算如下:

[5 10 15]  . [0 1 0] = 10
[10 15 20] . [0 1 0] = 15
[15 20 25] . [0 1 0] = 20
[20 25 30] . [0 1 0] = 25

过滤后的矩阵,即输出为【10 15 20 25】。这个过程也可以作为 2D 卷积层多样化。

2.2.汇集层

汇集层对卷积层之后获得的矩阵值执行各种操作。平均池取确定的矩阵大小中像素值的平均值,而顾名思义,最大池取最大值。如图 2 所示,通过使用 2x2 池,4x4 矩阵已经缩小到 2x2 大小。它概括了特定区域的特征,降低了特征的维数。这样,在模型变得更加通用的同时,避免了过拟合

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

图二。最大池(左)和平均池(右)是做什么的?,来源

2.3.脱落层

用最简单的话来说,它删除了图 3 中获得的一些特征,也就是说,它导致了信息丢失。如果我们处理 128×128×3 的 RGB 图像,并考虑像素是图像数据集的特征,我们将有大约 50000 个特征。通过申请退学,可以放弃其中的一些功能。这样,也防止了过拟合

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

图 3。辍学层是做什么的?,来源

2.4.展平图层

扁平化层用于 CNN 模型第一部分的最后一层,该模型将矩阵形状从 3x3 转换为 9x1,如图 4 所示,以便为通过完全连接的层进行分类准备数据集。

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

图 4。展平图层是做什么的?,来源

3.辅导的

在图像的特征之后,使用卷积层提取数据集,这些特征分别由密集层和集成学习算法训练。讨论了实现和结果。

可以通过链接访问数据集。

3.1.密集层方法

该数据集由 233 个样本组成,包含杯子、盘子、碟子,被训练用于分类。首先,使用图像增强过程来扩展数据集。在应用数据预处理过程之后,它被分成训练集和测试集。训练数据集使用如下构建的模型进行训练:

  • [1] -图像放大、调整大小和缩放

预定义的图像增强过程重复 15 次,并且样本数量增加大约 3500。数据集中的所有图像都调整为 128 x 128 像素,每个像素除以 255 进行缩放。

  • 【2】-型号

CNN 模型由两个主要部分组成。使用‘model’提取特征,它作为第一个组件按顺序构建。由于像素是图像数据集的特征,并且图像的形状是 128×128×3,所以特征的总数是 49152。输入形状在第一卷积层中定义。在接下来的卷积层中, L1 & L2 regularizations被用于防止过拟合。*L1&L2 正则化的作用是调整权重的重要性,因此可以假设卷积层的正则化参数是层的学习速率。*此外,以不同的速率应用Dropout 以防止过拟合,最后,使用Flatten layer将模型的形状转换为(n_samples,n_features)。该模型的概要如图 5 所示。

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

图 5。模型摘要,图片由作者提供

查看展平层的输出形状,可以看到,开始时的特征数为 49152,使用层后为 1728。

在模型的第二部分中,在提取特征之后,应用密集层来执行分类过程。最后,通过组合输入(是提取特征的部分)和输出(是进行分类的部分)来创建“T4”。

  • 【3】-模型评估

准备混淆矩阵和测试数据集的分类报告来评估模型。

  • 【4】——模型泛化性能

使用 google images 随机下载了 15 张杯子和盘子的图像,并用训练好的模型进行预测,以测试模型的泛化性能。

3.2.集成学习方法

在引言句中已经提到,机器学习中的数据集是以 (n_samples,n_features) 的格式进行训练的。在这一部分中,应用了集成学习算法,但是可以使用任何分类算法来代替。查看图 5 中的展平图层,可以看到它被提取为 1728 个要素。在这一部分中,分类过程使用集成学习算法而不是密集层来完成,如下所示:

  • [1]-通过 CNN 模型的第一部分‘model’预测训练集、测试集和外部测试集,并创建派生数据集。
  • [2]-创建包含混淆矩阵结果的函数,以便应用所有算法。
  • [3]- XGBoost、LGBM、基于直方图的 GB、ExtraTree、AdaBoost、Bagging 算法在其基础版本中用于分类。

4.结果

密集层方法的混淆矩阵如图 6 所示。

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

图 6。测试集的混淆矩阵(左),外部测试集的混淆矩阵(右),图片作者

可以看出,在测试数据集中实现了 91%的成功,而在外部测试数据集中获得了 13/15 的准确性,该外部测试数据集是从不同的源随机生成的,用于模型泛化性能。

集成学习方法的结果如图 7 所示。

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

图 7。集成学习算法的结果,图片由作者提供

可以看出,尽管测试数据集精度高,但是在外部测试数据集中获得了低精度结果。这表示过拟合

5.讨论

由于这项研究主要是关于开发一个 CNN 模型,它不是集中在集成学习方法。然而,可以看出,尽管没有调整超参数,但是这些方法中的一些,例如 XGBoost,具有令人满意的结果。

有必要了解它是如何工作的,以促进卷积神经网络的应用。本文旨在提供不同的选择和灵活性。有可能提高在集成学习算法中获得的准确性结果,例如使用 GridSearch 检测超参数的最佳组合或扩展数据集。深度学习中的 CNN 模型在图像数据集上的效果无可争议地好,但当作为替代方案进行研究时,这种方法甚至可以被评估用于不同的目的。

回到指引点击这里

https://ibrahimkovan.medium.com/machine-learning-guideline-959da5c6f73d

在 1 分钟内创建一个你的同事能够理解的代码库

原文:https://towardsdatascience.com/configure-a-codebase-your-colleagues-will-understand-in-1-minute-faa02483cbf?source=collection_archive---------14-----------------------

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

晚上创作的背景照片 _ 陶—

实践教程

使用 PyScaffold 和预提交挂钩配置结构化数据科学报告

在组织中,数据科学代码库(又名存储库或包)有一个通用文件结构*。*

结构是指代码库中文件的布局,例如:

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

基本代码回购结构。(图片由作者创作)。

在大学、Kaggle 或宠物项目中,你可以在代码库结构上有点无赖——毕竟,最重要的是输出。

但是在组织中,代码库的结构也很重要,而且非常重要。

我们在这里讨论的是构建代码库的通用最佳实践——组织希望你作为数据科学家使用的那种。

为什么通用代码库结构很重要?

这很重要,因为在组织中,其他人会与你的代码进行交互。当其他人与你的代码交互时,你希望他们在尽可能短的时间内理解你的代码库这样他们就可以开始为之做出贡献。

如果文件结构是一种通用格式,您的数据科学家和开发人员同事只需花几分钟就能理解它,然后就能进入有趣的部分——钻研代码本身。

或者,如果代码库结构不是的通用格式,那么每次有人查看新的代码库时,他们将不得不花费额外的时间(比如 2 小时)来熟悉它的结构。无聊吧?我们宁愿直接找到代码并开始编程!

然后是整个团队的时间损失。如果你考虑一个有 100 名开发人员的企业,每个人平均一年开发 10 个现有的代码库,他们花 2 个小时熟悉每个代码库的结构—**2000 个小时仅仅是理解回购结构。**那就是每年有 83 天或 3 个月不必要的工作损失。

令人难以置信的是,如果开发者花 1 分钟,为回购建立一个共同的结构,这是可以避免的。对于 10 次回购,这是10 分钟的 成本,以节省 3 个月的损失时间。

多划算啊!

如何在 1 分钟内创建结构化 Git 回购

好消息是,实际上就这么简单:

your_directory$ **pip install pyscaffold**
your_directory$ **putup your_repo_name**

就是这样!在您想要存储 repo 的目录中执行这两行代码后,它将在大多数数据科学家常用的文件结构中创建—不到 1 分钟!它将看起来像这样,并立即准备好开始编码:

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

你的结构性回购。(图片由作者创作)。

让您的代码库更加可用

在你的新代码库中有 3 部分标准文件对此有帮助——src文件夹、 setup.cfg 文件(和预提交钩子)和 README 文件:

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

(图片由作者创作)。

src 文件夹

这个 repo 最重要的部分是 src (source)文件夹,因为这是您的数据科学代码将要存放的地方。您可以从 src 构建一个完整的数据科学项目,而无需接触任何其他文件。

src 文件夹最初看起来像这样:

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

使用 pyscaffold putup 函数后的 src 文件夹(图片由作者创建)。

可以忽略 init。py 和 skeleton.py 文件。重要的是您添加到该文件夹的内容,即用于数据清理、标记、建模等的功能。

构造 src 文件夹的常用方法如下:

  • 包含函数的文件
  • 一个连续调用这些函数并提供输出的 runner 文件

以下是一个 src 结构示例:

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

一个非常基本的 src 文件夹结构的例子(图片由作者创建)。

如您所见,有三个文件夹,每个文件夹都包含 python 文件和函数:

  1. **预处理:**用于清理你的数据(处理缺失值,标准化数据等)
  2. 模型:任何需要建立的模型(如贝叶斯神经网络)以及根据需要训练它的功能
  3. 结果:用于输出您的预测结果(以图表或 CSV 等形式)

然后我们有了非常重要的 runner.py 文件,它导入数据,按顺序调用这些函数,并提供输出(可能会将结果保存到 csv 或绘图到文件夹等)。

自述文件

自述文件是你回购的另一个重要部分。这告诉你的数据科学家同事如何使用你的代码库。它非常有用,可以解释如下内容:

  • 你的回购做什么
  • 需要哪些依赖项以及任何安装说明
  • 任何其他使用说明
  • 如何与作者取得联系

您的同事在开始处理您的代码库时,可能会首先查看这个文件,所以有必要弄清楚这一点

setup . CFG 文件&预提交钩子

在这最后一步,我们会告诉您的同事他们需要哪些安装来运行您的代码库,并配置规则(挂钩),以帮助确保只有格式良好的代码才能提交到您的代码库。

首先让我们看看 setup.cfg 文件。这里值得编辑的主要部分是“ install_requires”。这个是一个超级有用的部分,因为它告诉新用户需要哪些包和版本来运行你的代码库。如果没有这一点,您的同事可能会安装没有所需功能的旧版本(因此在运行时会导致错误)。

库以 == 版本 的形式添加到本节中,例如:

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

(图片由作者创作)。

在 install_requires 部分,我们还可以添加三个高质量的包,这有助于使您的实际代码对您的同事来说更具可读性:

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

(图片由作者创作)

预提交和预提交钩子是很棒的包!它们本质上拥有一组格式化“钩子”和格式化规则,在你提交任何东西之前,你的代码必须遵守这些规则。这些规则是标准的最佳实践,在数据科学中被广泛使用(并被期待)。例如:

  • 代码 行长度不能大于 100 个字符
  • 导入语句必须在文件的顶部
  • 每个函数之间必须留有两个空行

当您尝试提交时,预提交包将让您知道哪些规则没有被满足,以便您可以修复它们。

设置预提交挂钩的两个简单步骤:

  1. 通过在 repo 的终端(或其他 shell)中执行以下命令来安装预提交:
your_directory$ **pip install pre-commit**
your_directory$ **pre-commit install -t pre-commit**

2.创建一个. pre-commit-config.yaml 文件来存储你的钩子

这个文件是 pre-commit 在你提交某个东西的时候读取的— 所以 你应该在这里列出你想要哪个钩子。添加*。将 pre-commit-config.yaml* 文件提交到您的根文件夹(即 src 上面的文件夹)。

下面是一个基本配置,你可以复制到你的中。pre-commit-config . YAML文件开始—它指示上面要点中的三个钩子:尾随空格重新排序 python 导入flake8 (代码风格指南实施—使用非常广泛)。

用于复制和粘贴的代码:

default_language_version: python: python3repos: - repo: local hooks: - id: reorder-python-imports name: reorder-python-imports entry: reorder-python-imports language: python types: ["python"] - id: flake8 name: flake8 entry: flake8 language: python types: ["python"] - id: trailing-whitespace name:  trailing-whitespace entry: trailing-whitespace-fixer language: python types: ["python"]

它应该是这样的:

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

(图片由作者创作)。

**现在,当您提交时,钩子应该开始工作:)**为了进行测试,尝试提交一个包含错误代码的. py 文件——它应该被拒绝,并且应该在终端中返回一个需要修复的代码行列表。

**您可以在中添加任意数量的挂钩。预提交 config.yaml 文件。**预提交的文档可以在这里看到,更完整的钩子列表可以在这里看到。

**就这样!**您可以像往常一样将这个代码库推送到 GitHub,因为您已经掌握了专业代码库设置的基础知识:)

最后一个音符

结构化回购有用的关键在于,每个人都使用相同的结构——一种大家熟悉的已知结构。你的组织可能会有一个固定的结构,它可能与上面的不同。然而,上述方法是数据科学中一个众所周知的结构,在没有其他指导原则的情况下,这是一个很好的选择。

希望那有用!如果您有任何问题,请随时在 LinkedIn 上给我发消息。你也可以订阅我的帖子 这里

最后,如果你想进一步支持 Medium 上的作者,你可以在这里注册成为会员。

配置没有 DevOps 学位的 DVC 远程

原文:https://towardsdatascience.com/configure-a-dvc-remote-without-a-devops-degree-3b2b06961e8f?source=collection_archive---------37-----------------------

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

照片由 Honey Yanibel Minaya CruzUnsplash 上拍摄

有了 DAGsHub 储物件,一切都变得简单了

DVC 是一个伟大的工具;它可以让你追踪和分享你的数据、模型和实验。它还支持管道对典型 ML 工作流中的步骤进行版本控制。要共享您的数据和模型,您需要配置一个 DVC 遥控器(如 S3、GCloud Storage、GDrive 等。),但这样做可能会很麻烦,而且会花费大量时间。

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

要订购的东西太多了…照片由汉斯-彼得·高斯特 / Unsplash 拍摄

在这篇文章中,我将向你展示这种配置不应该如此困难;应该是流畅轻松的。为了解决这个问题,我们创建了 DAGsHub Storage,这是一个超级容易配置的 DVC 遥控器,无需信用卡,无需授予复杂的权限,也无需云设置。只需五个命令,您就可以开始了!

首先,您需要在 DAGsHub 上有一个项目。有两种方法可以做到这一点,要么从头创建一个要么从任何其他平台连接一个现有项目(我们支持 GitHub、GitLab、BitBucket 和任何其他可访问的 Git remote)。

如果你需要,我们有一个关于如何在我们的平台上开始一个新项目的教程https://dagshub.com/docs/experiment-tutorial/overview/

要继续这个教程,你需要先安装 DVC。

在 Git 项目中安装 DVC 后,通过运行以下命令初始化它

*dvc init*

该命令将创建.dvc/.gitignore.dvc/config.dvc/plots.dvcignore。这些条目可以用

*git commit -m "Initialize DVC"*

对于本教程,我已经创建了一个具有以下结构的新项目

*data
├── processed
│   ├── test_text.txt
│   └── train_text.txt
└── raw
    └── test_full.txt*

为了开始跟踪我们的数据,无论是文件还是目录,我们使用dvc add

*dvc add data*

**这里是 DVC 施展魔法的地方。存储关于添加到.dvc文件中的条目的元数据;这是一个小文本文件,包含关于如何访问原始条目的信息,但不是原始条目本身。这个命令将添加的条目添加到.gitignore文件中,这样我们就不会不小心提交了。

在我们的例子中,DVC 创建了一个名为data.dvc的文件,如下所示

*outs:
- md5: 61b3e1a6439d6770be4d210b758f6cbd.dir
  size: 0
  nfiles: 3
  path: data*

这是将由 Git 进行版本控制的文件。

在这一步之后,我们准备提交.dvc文件,就像我们处理任何源代码一样。

*git add data.dvc .gitignore
git commit -m "Add data"*

远程存储数据

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

配置一个桶不应该这么难!杰西卡·约翰斯顿 / Unsplash 拍摄的照片

太棒了。我们现在正在跟踪数据的版本,现在我们必须弄清楚在哪里存储数据本身。

正如我之前提到的,我将向你展示如何毫不费力地配置 DVC 遥控器。遵循五个简单的命令,您将把您的数据和模型与代码放在一起。为了便于比较,我还将向您展示设置遥控器的传统方式,这样您就可以很容易地理解使用 DAGsHub 存储节省的时间。

没有 DevOps 学位怎么做

在 DAGsHub,我们会自动为平台上的每个项目创建一个 DVC 遥控器来推送您的数据和模型,就像您收到 Git 遥控器来推送您的代码一样。这就是简单性开始显现的地方!要从该 URL 推送或提取数据,我们将使用现有的 DAGsHub 凭据(通过 HTTPS 基本身份验证)。这意味着我们不需要配置任何 IAM,不需要提供访问令牌来访问您的存储桶或任何与云提供商相关的东西。

公共存储库将拥有公开可读的数据,就像代码一样。如果您想要共享或接收来自协作者的数据,请将他们添加为项目协作者。如果你的库是私有的,那么只有维护者能够将数据拉进或推进其中。

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

基本上能克隆代码就能拉数据!在 DAGsHub 上添加合作者

让我们把手弄脏吧!

  1. 我们需要添加 DAGsHub 作为我们的 DVC 遥控器
*dvc remote add origin --local <https://dagshub.com/><username>/<repo_name>.dvc*

2.接下来,我们需要告诉 DVC 如何要求我们的凭证

*dvc remote modify origin --local auth basic
dvc remote modify origin --local user <username>
dvc remote modify origin --local ask_password true*

3.最后,将数据推送到新的遥控器

*# Make sure you are using DVC 1.10 or greater for the next command
dvc push -r origin*

就是这样!只需 5 个命令,您就可以毫不费力地配置您的 DVC 遥控器;我们从未打开云提供商网页,处理复杂的 IAM,或提供信用卡信息。

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

简易柠檬榨汁机。由 Unsplash 上的 Louis Hansel @shotsoflouis 拍摄的照片

如果你需要更多关于 DAGsHub 存储的信息,你可以阅读我们的 功能参考

如何用 DevOps 学位做这件事——一个比较

在我们深入本节之前,除了 DAGsHub 存储之外,DAGsHub 目前还支持 AWS S3GCS 。如果你的目标是用最简单的方式安装 DVC 遥控器,那么你已经完成了。

为了便于比较,我们来看看亚马逊 S3 是如何做的。

  1. 聘请 AWS 作为您的云提供商。这包括拿出你的信用卡(如果你已经有一个账户,你可以跳过这一步)
  2. 设置一个存储桶来存储您的数据
  3. 安装 AWS CLI 工具
  4. 使用 CLI 工具登录 AWS
  5. 如果将要使用存储桶的用户不是管理员,创建一个 IAM 用户
  6. 分配正确的权限来使用铲斗
*{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Principal": {
                "AWS": "<IAM-user-ARN>" (e.g: "arn:aws:iam::7777777:user/dags-lover")
            },
            "Action": [
                "s3:GetObject",
                "s3:PutObject",
                "s3:ListBucket",
            ],
            "Resource": [
                "arn:aws:s3:::/*"
                "arn:aws:s3:::"
            ]
        }
    ]
}*

很多事情,对吧?即使对于最有经验的用户来说,所有这些步骤都容易出错,所以如果你是第一次这样做,预计会错过一些东西。

这还没有结束。如果你想集成 DAGsHub,你需要在你的项目设置中添加一个存储键,这样我们就可以在我们的文件查看器中列出、显示和区分你的文件。

你会在https://dagshub.com/用户名> / <回购名称>/设置/存储/密钥中找到这个设置页面

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

DAGsHub 上的存储键菜单

一旦您输入您的 bucket URL,您将收到添加存储密钥的所有说明。

跟上!我们还没完成呢!现在你需要为 DVC 安装 S3 软件包

*pip install "dvc[s3]"
#Or if you are using poetry
poetry add dvc --extras "s3"*

接下来,我们需要添加 bucket 作为我们的遥控器

*dvc remote add s3-remote s3://your-bucket/storage*

最后,我们把我们的数据

*dvc push -r origin*

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

了解更多信息

我希望这能帮助你理解如何设置 DVC 遥控器(一个简单的方法和一个困难的方法)。更多关于 DAGsHub 的信息,请查看我们的网站文档,或者加入我们的 Discord 社区

在 Django 中配置读取副本数据库

原文:https://towardsdatascience.com/configure-a-read-replica-database-in-django-b0d54ec897f1?source=collection_archive---------29-----------------------

软件开发

何时以及如何在 Django 中配置读取副本数据库

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

图片由海燕Unsplash 上拍摄

何时以及如何在 Django 中配置读取副本数据库

在软件工程中,最关键的步骤之一是架构的选择,以至于选择中的任何错误都可能导致网站出现故障,从而对业务绩效产生不利影响。

通常,与系统性能相关的问题,尤其是对于大型复杂的系统,对于维护和诊断是至关重要的,因为它们可能与不同的软件环境相关。这些问题可能由多种因素引起,包括硬件、软件或网络相关问题。

下一篇文章将讨论与数据库性能相关的问题,以及使用读取副本减轻这些问题的方法。我目前的体验是基于部署在谷歌云平台上的 App Engine 应用和 PostgreSQL 复制

数据库中的性能问题

在大多数情况下,由于与数据库性能相关的问题,系统会变得混乱。造成这种情况的因素有很多,最常见的是选择了错误的模式设计。因此,如果在牢记预期操作的同时没有正确设计,数据库将最终表现不佳。相反,一个设计良好的模式不一定能达到标准,因为许多其他因素会影响它的性能,例如连接数、压力或负载处理能力,或者数据库要处理的数据量。例如,当单个数据库处理大量用户(考虑几千个)时,它将遇到大量连接命中,并且它不一定有资源来实时满足这些命中。因此,为了缓解这种情况,引入了副本的概念。

数据库副本

关于软件和硬件的术语“复制”是指利用特定资源的多个副本(或复制品)来改善/增强性能、服务可用性和容错的过程。关于数据库系统中的复制,通常认为多台服务器在处理相同的数据。有多种配置和过程可用于将复制合并到数据库中:

  • 在所有情况下都允许读或写命令。
  • 多个只读实例和一个主实例(允许读/写命令)。注意,在这种模式中,数据复制和同步可以以同步和异步方式执行。

在 Django 中处理读取副本配置

Django 应用中配置和使用读取副本之前,应考虑以下两点:

  • 读取副本实例应该在 Django 应用程序中声明为数据库。
  • 需要配置路由器来选择相应的读取副本。

在 Django 中声明读取副本实例为数据库的程序

Django 中将读取副本配置和声明为数据库的方法包括设置 Django 设置文件。如上所述,我们将设置一个默认的单个主实例(允许读/写的服务器)数据库,而读副本将被声明为附加数据库。例如,考虑到已经配置了两个复制副本,settings.py 文件应该如下所示:

DATABASES = {
    "default": {
        "ENGINE": "django.db.backends.postgresql",
        "HOST": "/cloudsql/project-id:region:master-instance-id",
        "NAME": "pg_master",
        "USER": "pg_user",
        "PASSWORD": "master_password",
    },
    "replica_1": {
        "ENGINE": "django.db.backends.postgresql", 
        "HOST": "/cloudsql/project-id:region:replica1-instance-id",
        "NAME": "pg_replica1",
        "USER": "pg_user",
        "PASSWORD": "replica1_password",
    },
    "replica_2": {
        "ENGINE": "django.db.backends.postgresql",
        "HOST": "/cloudsql/project-id:region:replica2-instance-id",
        "NAME": "pg_replica2",
        "USER": "pg_user",
        "PASSWORD": "replica2_password",
    }
}

一旦配置完成,这两个副本就可以通过 Django 应用程序使用了。我们可以通过使用 QuerySet API 的方法来再次确认这一点。例如,可以使用以下命令从主数据库和副本数据库检查 Lead 模型的可访问性:

# Here the leads are retrieved from the master instance:
Lead.objects.all()# Here the leads are retrieved from the replica instance 1:
Lead.objects.using('replica_1').all()# Here the leads are retrieved from the replica instance 2:
Lead.objects.using('replica_2').all()

也可以在通过传递“using”参数的“ save 方法保存对象时,将给定的数据库设置为可用。请注意,在一个读取副本中保存对象时,将会遇到错误,因为实例只允许读取操作,不允许写入。

路由器配置有助于在需要时访问特定的读取副本

一旦在 Django 应用程序中配置了副本实例,并且确保了可访问性,软件开发人员就以这样的方式设计程序,即在适当的相应副本上执行只读操作。因此,默认情况下,这种方法会妨碍可扩展性,因为它更像是配置复制副本实例选择的手动过程。这意味着将来添加更多的副本将需要修改代码并手动配置路由过程。

然而,手动配置的另一个聪明的方法是使用 Django 的数据库路由器。在这种配置中,可以创建定制的路由器,它自动选择默认实例来执行写操作,或者选择随机选择的副本来执行读操作。下面是自定义路由器配置,显示了该过程的工作原理:

class DatabaseRouter:
    def db_for_read(self, model, **hints):
        return random.choice(['replica_1', 'replica_2']) def db_for_write(self, model, **hints):
        return 'default' def allow_relation(self, obj1, obj2, **hints):
        return True def allow_migrate(self, db, label, model=None, **hints):
        return True

按照上面的过程,现在我们需要通过设置默认的数据库路由来更新“setting.py”文件:

DATABASE_ROUTERS = ['app.router.DatabaseRouter']

一旦更改生效,应用程序中的所有读取操作将被路由到副本,写入操作将被定向到主实例。

结论

总结一下我们的讨论,在 Django 中打开读取副本实例的过程非常简单。此外,它有助于增强应用程序的性能以及整个系统的功能。在我们原始代码的基础上,对配置文件和设置进行微小的修改,就可以让事情朝着对系统有利的方向发展。

感谢阅读这篇文章!如果你有任何问题,请在下面留言。另外,看看我以前的文章,你可能会喜欢:

https://vpodk.medium.com/principles-of-software-engineering-6b702faf74a6

验证性因素分析基础

原文:https://towardsdatascience.com/confirmatory-factor-analysis-theory-aac11af008a6?source=collection_archive---------0-----------------------

思想和理论

它是如何工作的,可以在你的研究中使用

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

Charles DeluvioUnsplash 上拍摄的照片

如果你已经做到这一步,你可能已经读过我的探索性因素分析(EFA) 文本。如果你还没有读过,在直接进入验证性因素分析(CFA)之前先检查一下,因为这两种分析有一些重要的相似之处!在本文中,我们将介绍 CFA 的基本原理,它是如何工作的,并且我们将比较 CFA 和 EFA。

我如何表示我的构造?

与 EFA 一样,CFA 使用公共因子模型,即它将观察变量之间的协方差视为一个或多个因素影响的反映,也是一个未解释的方差。这与网络分析不同,网络分析允许项目之间的协方差在它们之间有一个原因。换句话说,因素分析的心理测量模型一般认为项目的协方差只是因为有一个潜在的因素来解释它。这是一个要记住的非常重要的假设,因为也许你的结构不符合公共因子模型,而是一个网络模型。我将用 Borsboom 和 Cramer (2013)给出的一个例子来解释。

下面,我们看到一个测量重度抑郁症的工具的因子模型。在这份报告中,这些项目衡量的方面包括:情绪低落、体重增加、睡眠问题、运动问题、疲劳、注意力不集中等。我们从图中看到,项目得分的变化有一个共同的原因,即抑郁(即,一个人的抑郁水平越高,他们越多地报告有这些症状)。

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

主要抑郁因素模型。图片来自 Borsboom 和 Cramer (2013 年)

然而,我们可以认为一些项目之间的关系不仅仅是由于抑郁。这方面的一个例子是注意力集中问题的原因及其与其他症状的关系。睡眠有问题的人会变得疲劳,因此会有注意力问题(睡眠问题→疲劳→注意力问题)。换句话说,可以推断一个可观察变量和另一个变量之间的因果关系,这与公因子模型“决裂”。下图是这种模型的一种可能的表示形式,其中各个项目之间存在因果关系。

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

焦虑与抑郁症的关系。图片来自 Borsboom 和 Cramer (2013)。

那么,我如何知道我的结构是遵循公因子模型还是更像网络模型呢?嗯,基于理论!我知道研究人员在很长一段时间里只关心统计数据来指导一切,但对我们来说,重要的是从理论上重新思考我们的构建,然后从经验上测试理论。

好了,你决定最适合你的结构的模型是因子模型,现在呢?

什么是 CFA?我们何时申请 CFA?

CFA 是一种多变量统计,用于估计工具的结构,验证测量变量在多大程度上代表结构的数量。也就是说,它验证一个乐器的结构是否可以是真实的,但不一定是真实的。为此,我们需要陈述我们想要测试的结构。一般来说,当有先前的研究告诉我们该工具的维度时,就使用 CFA。例如,我们将有一项北美研究,它使用 EFA 来验证工具的维度,而您使用 CFA 来验证这种结构在巴西数据中的表现如何。然而,这不是你使用 CFA 的唯一方法!例如,你可以在同一个研究中使用 EFA(探索维度),但仍然可以使用 CFA 测试不同的理论模型。

因此,当您想要估计工具的维度时,EFA 和 CFA 都适用(注意,我说的是估计,而不是探索/发现维度)。例如,我们可以在自我报告工具中应用 CFA,其中项目代表行为、想法或感觉。另一个例子,我们可以将它应用于一系列其他的测量,比如焦虑的心理物理学测量。因此,CFA 适用于测量幸福、焦虑、偏见等属性的工具。

饱和/无限制模型和限制模型之间的差异

全民教育模式可以称为饱和/无限制模式。这是因为所有潜在维度解释了所有项目的差异,如下图所示。

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

饱和/无限制模型。作者制作的图像。

至于 CFA,我们可以称之为限制模型,即我们对模型施加一些限制,例如,一个因素不能与另一个因素的项目交叉加载。下图举例说明了受限模型。

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

受限模型。作者制作的图像。

当然,一种模式和另一种模式之间存在一些实际差异。第一个是,一般来说,CFA 的因子加载输出不同于 EFA。在 EFA 中,所有因素都有交叉负荷,而在 CFA 中,一些负荷被设置为 0,如下图所示。

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

CFA 中因子加载的例子。作者制作的图像。

我做了一个表格,展示了非限制模式(EFA)和限制模式(CFA)的区别。

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

EFA 和 CFA 的区别。作者制作的图像。

我们在上表中看到,对于验证性因素分析,我们需要有一个明确的假设,即背后必须有一个理论来直接指导我们的分析,我们不能只是在没有适当理由的情况下继续探索。这和 EFA 有一点不同,EFA 的结构背后有一个理论,但是你测试这个结构是否会在数据中得到佐证(通过平行分析之类的)。当然,在全民教育中,我们可以根据理论提取因素,这在某种程度上类似于直接指导分析的假设。

同样重要的是再次强调,在 CFA 中,我们可以测试不同的模型,能够进行修改并允许残差相关性。见下图。

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

同一结构的不同 CFA 模型。作者制作的图像。

我们甚至可以测试更复杂的模型,比如层次模型或者双因素模型。

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

分层模型(左)和双因素模型(右)。作者制作的图像。

简而言之,因为 CFA 对模型进行了限制,所以我们有可能测试大量的东西!CFA 的一个用途是通过多组 CFA,我在之前的文本中写过。

模型识别

当我们谈论一个受限模型时,我们必须处理一个称为模型识别的“问题”(Bollen,1989)。换句话说,我们需要我们的数据有足够的“信息”来进行必要的统计。

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

有 4 个项目的因素模型。作者制作的图像。

在上图中,我们使用 CFA 来估计单维度。我们看到我们估计了 4 个因子负载(λ;每个项目一个)和 4 个残差(ε;每项一个),也就是我们有 8 个信息需要估计。我们拥有的信息片段是 V1、V2、V3 和 V4 的分数(即这个人对每个观察到的变量的分数)以及它们之间的相关性。

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

V1、V2、V3 和 V4 之间的关联矩阵。作者制作的图像。

因此,我们有 4 个分数+ 6 个相关性= 10 条信息。换句话说,由于我们手中有 10 条信息,用 4 个项目我们可以估计 8 条因子载荷和残差。按照这个逻辑,很容易看出,为了能够识别模型,每个潜在因素的最小项目数是 3 个项目。看,在有 3 个项目的单因素模型中,我们将估计 3 个因素负荷+ 3 个剩余= 6 个必要信息。我们有 3 个项目的信息+ 3 个相关性= 6 个信息。所以我们将有 0 个自由度(DF)。

  • 如果 DF < 0, the unidentified model (nothing will be estimated);
  • If DF = 0, the model is under-identified (only factor loadings will be arbitrarily estimated; no fit indexes will be generated);
  • If DF> 1,过度识别的模型(一切都可以估计)。

只有当 DF> 1 时,才应解释模型,因为这是解决项目和潜在变量的协方差方程的唯一方法,允许拟合指数的输出。

拟合指数

拟合指数代表你所估计的模型的似是而非程度。拟合良好的模型会减少适马矩阵(人口协方差矩阵,即您放入模型的模式)和 S 矩阵(样本协方差矩阵,即您的经验矩阵)之间的差异。

有几个适合指数,每一个都有其分界点(布朗,2015;Mair,2018)。我制作了另一个表格,显示了 fit 指数的描述及其建议。

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

不同的拟合指数及其推荐临界值。作者制作的图像。

拟合指数中的高级主题

一个模型可以有很好的拟合指数,但不能推广到总体。换句话说,我们必须小心适应指数!更复杂的模型通常具有更好的拟合指数。我们可以调整我们的模型来解释来自线性方程、二次方程甚至六次方程的数据。有时候,6 次方程完美地解释了数据!然而,考虑到方程的复杂性,这种模型不太通用。因此,我们在模型复杂性和拟合指数之间有一个成本效益关系,我们必须小心不要过度拟合(或夸大拟合)。

Bonifay 和蔡(2017)的一篇论文验证了以下每个模型的总体拟合程度。也就是说,模型是否总是呈现良好的拟合指数。为此,测试了一个半无限制模型(只有 2 个负载受到限制;黑色的模型);双因素模型(绿色模型);分级模型(蓝色和黄色);和一维模型(红色)。为此,对 1000 个模拟数据集的拟合指数进行了分析。

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

在 Bonifay 和 Cai (2017)中测试的模型。图像由 Bonifay 和蔡制作(2017)。

下图总结了他们的发现。我们看到,在样本空间所有可能的拟合指数中,半无限制模型和双因素模型几乎总是表现出良好的拟合指数。这意味着在这些情况下,我们不能以与其他模型相同的方式解释拟合指数。例如,如果您要比较双因素模型和一维模型,您很可能会在双因素模型中找到更好的拟合指数,但这不一定是解释数据的最佳模型。当然,我们必须比较嵌套模型的拟合指数,但是这个例子只是一个说明。

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

完整的数据空间。图像由 Bonifay 和蔡制作(2017)。

考虑到这一点,有一个闪亮的应用程序可以为你的数据模拟最合适的分界点(McNeish 和 Wolf,2020)。我不会详细解释它是如何工作的,因为网站本身有一个解释。这样,我们就有机会检查一维模型和多维模型的最合适的拟合指数,并测试它们的等价性。该站点如下所示。

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

闪亮的应用程序网站的图像。

非常感谢您阅读本文到目前为止!我希望你喜欢并学到了很多!如果你喜欢,不要忘记与同事和朋友分享你的知识!很快,我们将制作一个关于如何在数据集中做 CFA 的教程。跟着我!

这篇文章最初是在巴西葡萄牙语的 PsicoData 上发表的,我也是作者。

接触

LinkedInResearchGate谷歌学术 如需论文合作或统计咨询,可通过邮件联系(rafavsbastos@gmail.com)

参考

K.验证性因素分析。在 K. A. Bollen(编辑。),含潜变量的结构方程, 1989,Willey。

W.Bonifay 和 L. Cai,论项目反应理论模型的复杂性,2017,多元行为研究52 (4),465–484。

D.Borsboom 和 A. O. Cramer,网络分析:精神病理学结构的整合方法,2013 年,临床心理学年度回顾9 ,91–121。

T.A. Brown,应用研究验证性因素分析第二版, 2015,吉尔福德出版社。

页(page 的缩写)Mair,现代心理测量学带 R, 2018,施普林格。

D.麦克内什和 M. G .沃尔夫。验证性因子分析模型的动态拟合指数截止值,2020 年 7 月 7 日https://doi.org/10.31234/osf.io/v8yru

共形预测导论

原文:https://towardsdatascience.com/conformal-prediction-4775e78b47b6?source=collection_archive---------8-----------------------

量化人工智能不确定性时,你应该始终考虑的一种方法

在决策中,人工智能(AI)系统不仅需要做出预测,还需要量化其预测的确定性(不确定性)。例如,考虑一个股票自动交易系统,其中人工智能系统预测股票价格。由于股票市场的高度随机性,人工智能系统的点位预测可能与真实值有很大差异。但是,另一方面,如果人工智能系统可以估计保证以高概率覆盖真实价值的范围,交易系统可以计算最好和最差的回报,并做出更明智的决定。

共形预测是一种量化人工智能系统不确定性的技术。特别地,给定输入,保形预测估计回归问题中的预测区间和分类问题中的一组类。预测区间和集合都保证以高概率覆盖真实值。

在关于保形预测的教程中,Glenn Shafer 和 Vladimir Vovk 给出了如下定义:

“保形预测利用过去的经验来确定新预测的精确置信水平.”

在本文中,我们利用同独立分布(i.i.d)数据集上的保形预测,即,

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

其中 X 是输入要素,Y 是标注,n 是数据点的数量。我们还假设已经训练了一个机器学习模型 f: X->Y。该模型可以是经典的机器学习模型,如线性回归、支持向量机(SVM)或深度学习技术,如全连接或卷积网络。目标是估计模型输出的预测集。为了说明这个想法,我们将描述保形预测的步骤、保证和例子。

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

作者图片

一、步骤

a .确定分数函数以量化不一致性

确定一个合适的得分函数 s(X,Y) ∈ R,以测量模型输出ŷ’s 和标签 y 之间的差异。这个得分函数非常关键,因为它实际上决定了我们可以得到什么样的预测集。例如,在回归问题中,我们可以将|ŷ-y|作为得分函数。这样,得到的预测集的值在预测ŷ周围的 L1 范数球内;在分类问题中,我们可以把 1-ŷ_i 作为得分函数,其中ŷ_i 是真正经典的预测逻辑。通过这种方式,我们将获得一个预测逻辑大于某个阈值的类的预测集。

b .计算分数的(1- ɑ)分位数

计算分数{s_1,…,s_n}的分位数,其中

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

在全共形预测方法中,我们需要训练 m 个模型来计算分数并构建预测集,其中 m 是 Y { n+1 }可能取值的数量。这无疑在计算上是昂贵的。为了降低计算复杂度,可以使用归纳(分裂)保形预测。简而言之,该方法将整个训练集分成适当的训练集和校准集。然后,只在适当的训练集上训练模型;并且分数仅在校准集上计算。这样,我们只需要对模型进行一次训练。

c .使用模型预测和(1- ɑ)分位数构建预测集

使用分位数形成新示例的预测集,

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

对于(1-分位数),我们可以通过包含值 y 来构建输入 X_{n+1}的预测集,这些值的得分小于或等于。

二世。担保

保形预测可以提供数学上的严格保证。设 Y_{n+1}为真值。y 可以是分类问题中的类别标签,也可以是回归问题中的真实值。设τ(X_{n+1})为预测集(或区间)。我们定义τ(X_{n+1})覆盖 Y_{n+1}如果 Y_{n+1}在τ(X_{n+1})中,即,

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

然后,给定一组相同独立分布(i.i.d)的样本{(X_1,Y_1),(X_2,Y_2),,…,(X_n,Y_n)},共形预测集满足以下覆盖保证,即,

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

基于可交换性(i.i.d)假设的覆盖保证的证明可以在的附录《保形预测和无分布不确定性量化的简明介绍》中找到。注意,在这个证明中,( 1- ɑ)水平变为(n+1)(1- ɑ)/n,以考虑有限样本的情况。

三。示例

在这一节中,我们的目标是给出一些关于共形预测集的直觉。

a .分类预测集

我们在图 1 中显示了三个分类预测集。在这项任务中,训练一个神经网络来对输入图像进行分类。保形预测用于构建类别集(在花括号中),这些类别集保证以高概率包括输入图像的真实标签。

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

图 1 分类预测集(来自 Sangdon Park 等。:通过校准预测的深度神经网络的 PAC 置信集

b .回归预测区间

在图 2 中,我们展示了一个回归预测区间。该系统的目标是在给定输入 x 的情况下预测ŷ。保形预测构建回归预测集(蓝线之间的间隔),保证以高概率覆盖真实值 y。

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

图 2 回归预测集(来自 Anastasios N. Angelopoulos 和 Stephen Bates: 保形预测和无分布不确定性量化的温和介绍)

四世。结论

本文简要介绍了保形预测,包括它的步骤、保证和例子。我们可以将保形预测应用于分类和回归问题。在这两种情况下,保形预测旨在量化机器学习模型的不确定性。保形预测易于实现,并且可以提供严格的保证。我们相信保形预测是走向安全人工智能的一个很好的垫脚石,其中不确定性量化是必须的!

熊猫的多指标困惑?需要了解的 9 项基本操作

原文:https://towardsdatascience.com/confused-by-multi-index-in-pandas-9-essential-operations-to-know-e6aec29ee6d8?source=collection_archive---------11-----------------------

了解要领,不再有困惑

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

Erik Mclean 在 Unsplash 上拍摄的照片

介绍

在许多用例中,我们处理的是单级索引。在类似电子表格的表格中,最简单的情况是行号作为索引,列号作为列。你可能有一种误解,认为我永远不会处理多级索引。让我们考虑泰坦尼克号数据集。出于本教程的考虑,我们将只包括两个数字列:agefare以及三个分类列:sexclassembark_town

泰坦尼克号数据集

我们数据处理中的一个常见操作是查看相关组的平均数据,如下所示。为了简化显示,我将agefare的浮点数转换为整数。

分组平均数据

如您所见,这个数据集的索引看起来不像典型的单个级别。的确,这个DataFrame使用了分级索引,也就是俗称的多级索引。

你对多级索引了解多少?或者说,你有没有被多重索引迷惑过?让我们在本文中了解多级索引的基本方面。

1.什么是 MultiIndex?

我们提到过,单级索引使用一系列标签来唯一地标识每一行或每一列。与单级索引不同,多级索引使用一系列元组,每个元组唯一标识一行或一列。为了简化术语,我们只关注行的索引,但是同样的规则也适用于列。

多级索引

如上所示,我们可以访问一个DataFrame对象的 index 属性。您可能会注意到,我们将索引作为一个MultiIndex对象来获取,这是 pandas DataFrameSeries的多级或分层索引对象。这个对象有三个关键属性:**names****levels****codes**。我们来复习一下。

>>> df_mean.index.names
FrozenList(['embark_town', 'class', 'sex'])
>>> df_mean.index.levels
FrozenList([['Cherbourg', 'Queenstown', 'Southampton'], ['First', 'Second', 'Third'], ['female', 'male']])
>>> df_mean.index.codes
FrozenList([[0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2], [0, 0, 1, 1, 2, 2, 0, 0, 1, 1, 2, 2, 0, 0, 1, 1, 2, 2], [0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1]])
  • 名称:我们的指数对每一个指数级别都有三个名称:embark_townclasssex
  • 级别:每个级别的标签。embark_town有三个标签,class有三个标签,sex有两个标签。
  • 代码:表示每一级指标的整数。例如,FrozenList中的第一个列表指示所有行的’embark_town级别(0 - >‘瑟堡’,1 - >'昆斯敦,2 - >'南安普顿)。

2.将多索引转换为常规索引

在示例DataFrame(即df_mean)中,作为使用groupby功能的结果,自动创建多索引。如果我们从一个没有多索引的数据帧开始,但是一些列可以创建为多索引,那会怎么样呢?考虑下面的DataFrame

>>> df = df_mean.reset_index()
>>> df.head()
  embark_town   class     sex  age  fare
0   Cherbourg   First  female   36   115
1   Cherbourg   First    male   40    93
2   Cherbourg  Second  female   19    25
3   Cherbourg  Second    male   25    25
4   Cherbourg   Third  female   14    14

我们简单地重置了索引,创建了一个使用单级索引的DataFrame,这种DataFrame您可能更熟悉,对吧。需要注意的一点是,reset_index方法带有一个参数drop,该参数决定索引是被删除还是作为列保留。在我们的例子中,我们对drop使用默认的False,它会将多级索引转换为三列,这是我们想要的操作。

3.重新创建多重索引

为了为这个DataFrame创建多级索引,我们可以使用set_index方法将适用的列指定为索引,如下所示。

>>> df_mi = df.set_index(['embark_town', 'class', 'sex'])
>>> df_mi.head()
                           age  fare
embark_town class  sex              
Cherbourg   First  female   36   115
                   male     40    93
            Second female   19    25
                   male     25    25
            Third  female   14    14

如您所见,df_midf_mean DataFrame具有相同的多级索引。

除了用现有的列设置索引之外,我们还可以手动创建MultiIndex对象,如果愿意的话,将它分配给一个DataFrame。如下所示,我们能够重新创建一个与我们在df_mean中使用的对象相匹配的MultiIndex对象。from_product方法使用提供的列表顺序创建所有可能组合的产品。

手动创建多索引

除了 from_product 方法之外,还有几种方法经常用来创建MultiIndex对象,比如[from_tuples](https://pandas.pydata.org/docs/reference/api/pandas.MultiIndex.from_tuples.html#pandas.MultiIndex.from_tuples)[from_arrays](https://pandas.pydata.org/docs/reference/api/pandas.MultiIndex.from_arrays.html#pandas.MultiIndex.from_arrays)[from_frame](https://pandas.pydata.org/docs/reference/api/pandas.MultiIndex.from_frame.html#pandas.MultiIndex.from_frame)。用法应该很简单,感兴趣的读者可以参考各自的参考资料,了解如何使用它们(点击这些方法上的链接)。

4。选择特定级别

选择数据最直接的方法是使用带有loc属性的基于元组的索引。如前所述,多级索引本质上是一个元组列表。因此,我们可以为想要检索的行指定所需的元组。下面是一些例子。

>>> df_mean.loc[('Queenstown',)]
               age  fare
class  sex              
First  female   33    90
       male     44    90
Second female   30    12
       male     57    12
Third  female   22    10
       male     28    11
>>> df_mean.loc[('Southampton', 'Second')]
        age  fare
sex              
female   29    21
male     30    19
  • 您可以跳过元组中的前 n 个级别,这将检索更低级别的所有元素。例如,(‘Queenstown’,)将选择该级别的所有行,而(‘Southampton’, ‘Second’)将为embark_town选择级别为‘Southampton’的行,为class选择级别为‘Second’的行。
  • 检索到的数据没有指定的级别,因为所有数据都满足指定的级别。
  • 示例中没有显示的是,您可以省略 tuple 外延,这可以作为这些操作的快捷方式。例如,代替df_mean.loc[(‘Queenstown’,)]df_mean.loc[(‘Southampton’, ‘Second’)],你可以分别做df_mean.loc[‘Queenstown’]df_mean.loc[‘Southampton’, ‘Second’]。但是,通常不建议这样做,因为这会导致混乱。因此,我通常会列出所有适用的信息,这样就不会有歧义。
  • 另一件要注意的事情是,我省略了列的:选择器,因为我确实想选择年龄和费用列。如果您只选择列的子集,请指定。

5.使用 xs 选择横截面

除了使用loc方法,您还可以使用DataFramexs方法,该方法检索横截面数据行。要检索特定级别,只需指定索引。下面是一些例子。

>>> df_mean.xs('Queenstown')
               age  fare
class  sex              
First  female   33    90
       male     44    90
Second female   30    12
       male     57    12
Third  female   22    10
       male     28    11
>>> df_mean.xs(('Southampton', 'First', 'female'))
age     32
fare    99
Name: (Southampton, First, female), dtype: int64

您可以为xs设置的另一个有用的参数是level,它指的是在多索引中使用的级别。例如,要检索DataFrame中的所有第一类,我们可以执行以下操作,选择横截面数据。

>>> df_mean.xs('First', level='class')
                    age  fare
embark_town sex              
Cherbourg   female   36   115
            male     40    93
Queenstown  female   33    90
            male     44    90
Southampton female   32    99
            male     41    52

6.同时选择多个级别

当您想要选择具有不同级别的行时,可以在 list 对象中指定所需数据的索引。例如,假设我们要在第三名皇后镇(女性)和第一名南安普敦(男性)之间选择数据。下面是如何通过指定范围。请注意,该范围包括边界,就像您对单级索引使用loc一样。

>>> df_mean.loc[('Queenstown', 'Third', 'female'):('Southampton', 'First', 'male')]
                          age  fare
embark_town class sex              
Queenstown  Third female   22    10
                  male     28    11
Southampton First female   32    99
                  male     41    52

如果希望选择不连续的行,可以传递元组列表,这些元组是行的索引。考虑下面的例子,它只选择了两行数据。

>>> df_mean.loc[[('Queenstown', 'Third', 'female'), ('Southampton', 'First', 'male')]]
                          age  fare
embark_town class sex              
Queenstown  Third female   22    10
Southampton First male     41    52

与上面的例子密切相关的是,我们也可以通过传递一组列表来选择数据,但是它们做事情的方式不同。如下所示,列表元组将产生多级索引,每个列表引用每个级别的多个标签。

>>> df_mean.loc[(['Queenstown', 'Southampton'], ['First', 'Second'], ['female', 'male'])]
                           age  fare
embark_town class  sex              
Queenstown  First  female   33    90
                   male     44    90
            Second female   30    12
                   male     57    12
Southampton First  female   32    99
                   male     41    52
            Second female   29    21
                   male     30    19

7.使用切片的高级选择

当我们使用列表元组时,多级索引是从这些列表中创建的。但是,当某个级别有多个标签时,您可能希望使用 slice 对象来表示一系列标签,而不是逐一列出它们。考虑下面的例子。

>>> # Instead of df_mean.loc[(['Cherbourg', 'Queenstown', 'Southampton'], 'Second', ['female', 'male'])]
>>> df_mean.loc[(slice('Cherbourg', 'Southampton'), 'Second', slice(None))]
                           age  fare
embark_town class  sex              
Cherbourg   Second female   19    25
                   male     25    25
Queenstown  Second female   30    12
                   male     57    12
Southampton Second female   29    21
                   male     30    19
  • slice(start, end)定义范围内的所有指数。
  • 因为我们只有三个标签用于embark_town级别,而不是使用slice(‘Cherbourg’, ‘Southampton’),我们可以使用slice(None),这被自动解释为引用所有标签。
  • 除了使用slice函数,pandas 还提供了一种更好的方法来引用多索引——IndexSlice,这有点像 NumPy 中使用的引用。下面是一个例子。在本例中,:表示该级别的所有标签。
>>> df_mean.loc[pd.IndexSlice[:, 'First', :]]
                          age  fare
embark_town class sex              
Cherbourg   First female   36   115
                  male     40    93
Queenstown  First female   33    90
                  male     44    90
Southampton First female   32    99
                  male     41    52

8.重组级别

到目前为止,数据帧已经有了原始顺序的多级索引。然而,我们可能希望索引以不同的顺序排列。为此,我们可以使用reorder_levels方法。例如,期望的顺序是class-sex-embark_town,而不是embark_town-class-sex。这种操作如下所示。

>>> df_mean.reorder_levels(['class', 'sex', 'embark_town']).head()
                           age  fare
class  sex    embark_town           
First  female Cherbourg     36   115
       male   Cherbourg     40    93
Second female Cherbourg     19    25
       male   Cherbourg     25    25
Third  female Cherbourg     14    14

除了指定级别的名称,还可以通过指定级别的数值来支持。因此,上述操作相当于df_mean.reorder_levels([1, 2, 0])

如果你想切换两个级别的顺序,另一种方法是使用swaplevel方法。顾名思义,该方法直接在两个级别之间翻转顺序。

>>> df_mean.swaplevel(0, 1).head()
                           age  fare
class  embark_town sex              
First  Cherbourg   female   36   115
                   male     40    93
Second Cherbourg   female   19    25
                   male     25    25
Third  Cherbourg   female   14    14

9.排序多索引

多级索引重组后,DataFrame看起来不再有组织,因为顺序还是用原来的那个,是根据embark_town-class-sex的索引排序的。为了根据所需的级别聚合数据,我们可以对索引进行排序,以便更好地组织数据。

>>> df_mean.swaplevel(0, 1).sort_index().head()
                          age  fare
class embark_town sex              
First Cherbourg   female   36   115
                  male     40    93
      Queenstown  female   33    90
                  male     44    90
      Southampton female   32    99

在示例中,我们简单地使用了sort_index方法,默认情况下,该方法使用第一级对数据进行排序。

但是,如果您喜欢使用不同的级别对数据进行排序,我们可以指定级别的数值或名称,如下所示。

>>> df_mean.swaplevel(0, 1).sort_index(level='sex').head()
                           age  fare
class  embark_town sex              
First  Cherbourg   female   36   115
       Queenstown  female   33    90
       Southampton female   32    99
Second Cherbourg   female   19    25
       Queenstown  female   30    12

结论

在本文中,我们回顾了您可能需要用来处理多级索引的基本操作。我知道对于许多初学者来说这是一个令人困惑的话题,但是如果你掌握了要点,当多级索引相关时,你应该能够处理大多数日常工作。

感谢阅读这篇文章。通过注册我的简讯保持联系。还不是中等会员?使用我的会员链接,通过支持我的写作。

锥形与平面毛刺:初始数据

原文:https://towardsdatascience.com/conical-vs-flat-burrs-initial-data-57762063f915?source=collection_archive---------28-----------------------

咖啡数据科学

泰坦磨床项目综述

在咖啡社区,关于咖啡研磨机的讨论已经持续了很多年,特别是平磨锥与圆锥磨锥的对比。还没有一个决定性的答案,但是很多个月前( 2007 ),在家庭咖啡师论坛上,有一个关于多台研磨机的评论。

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

所有图片由作者提供

然而,该评论被分散在他们论坛的多个帖子上,最终结果并不明显。我对关于磨床相互比较的数据特别感兴趣。甚至他们对 grinders 的比较分析也是以文本形式(没有图表)在单条线程的多个页面上进行的。

我一直在为研磨机做一些咖啡颗粒分析,有人建议看看这项研究。所以我看了这个研究,我认为它在当时是一个伟大的研究,但是有一些小事情我会做得不同:

  1. 分析了每台研磨机的多种研磨设置(我见过一些,但不在本文中)。
  2. 测量更多变量,如输出重量(即 TDS)
  3. 采集更多样本
  4. 将所有数据绘制成图表
  5. 在数据收集的同一天收集所有数据,因为烘烤在数据收集期间老化了几天。

撇开这些批评不谈,这些数据非常有趣。我想把其中的一些绘制成图表,以便更仔细地观察。也许会出现一个更清晰的画面。

原始数据

我将把重点放在使用不同研磨机比较浓缩咖啡的数据上。他们每天使用相同的烘焙方法,将研磨机与他们的质量标准进行比较,如下图所示的 Mazzer Robur 。这台研磨机很贵,应该放在咖啡店里。

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

有两个剂量设置,13.5g 和 16.5g,并且在每个剂量设置下为每个研磨机拍摄两个镜头。更多详情,请参见数据

作者们还做了一个盲品测试,并相互比较了几组照片。

分析

让我们首先来看提取率,它是被提取的可溶物的量。他们有多页文字形式的数据,我在这里编译了一下。

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

他们在计算味道指标的最终分数时只有一个错误,所以这很好!

让我们通过将每台研磨机与基线进行比较来绘制一些数据。

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

数据显示,所有这些研磨机都无法达到与 Robur 相同的 EY。在 EY 也有一些很大的波动,这很可能是因为拍摄量而不是重量是停止的标准。由于无法获得注射重量信息,所以我无法使用总溶解可溶物(TDS)作为另一个比较指标。

然后我拿出了两剂:

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

对于 13.5 克的剂量,Robur 肯定更好。对于 16.5 克的剂量,就不太清楚了。肯定有一个较低的平均值,但它没有 13.5 克剂量的变化大。

我还看了研磨机和它们的磨锥装置:

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

我对锥形然后是平的毛刺感到惊讶,因为我本以为这些是最好的,但也许在颗粒分布和提取上有一种有趣的相互作用,这还不清楚。

另一个不清楚的变量是研磨机是如何调整的,因为研磨设置的变化很可能会产生更大的影响。另一个被控制的输出变量是时间,我也不认为时间是一个很大的变量,或者至少是总拍摄时间。

对于他们的口味测试,所有的测试都是相互关联的,我认为他们没有尽可能客观地在所有的研磨机上给每一个镜头打分。

我把他们赢-平-输的数字放在一起,我加入了一个决定性胜利的指标,这意味着任何平局都被认为是有问题的磨床赢了,而不是罗布。

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

罗布人赢了,但实际上,大多数研磨者的口味没有太大差异。

圆锥形与扁平形

我拿走了所有磨床的数据,忽略了照片是在不同的日子拍摄的。然后,我绘制了 13.5 克和 16.5 克拍摄的平均 EY,以查看不同类型的研磨机(即,圆锥形、扁平形和圆锥形然后扁平形)。

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

从该图来看,似乎有证据表明平毛刺具有更高的提取率。

因此,让我们将每种毛刺类型的最佳提取方法配对,不包括 Robur 刀片:

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

我们可以在 13.5 克剂量和 16.5 克剂量之间进行划分,但我们得到的是相同的模式:

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

这提供了一些强有力的证据,表明基于提取率,平毛刺比圆锥毛刺好,但成对的拍摄经过一周,这可能会引入一些误差。

相反,让我们根据时间上最接近的镜头来配对镜头。这些收集之间最多有 2 天的时间。结论还是和之前一样。

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

所有这些数据总体上意味着什么?从这些数据中可以得出两个结论,但要说这两个结论中的任何一个是确定的,还需要更多的数据和更多的控制。

  1. 罗布在性能上是无可匹敌的,但它几乎可以与之匹敌。
  2. 平毛刺比锥形毛刺提取率高。

如果你愿意,可以在 Twitter 和 YouTube 上关注我,我会在那里发布不同机器上的浓缩咖啡视频和浓缩咖啡相关的东西。你也可以在 LinkedIn 上找到我。也可以关注我

我的进一步阅读:

浓缩咖啡系列文章

工作和学校故事集

个人故事和关注点

乐高故事启动页面

摄影启动页面

使用图像处理测量咖啡研磨颗粒分布

改善浓缩咖啡

断奏生活方式概述

测量咖啡磨粒分布

咖啡萃取

咖啡烘焙

咖啡豆

浓缩咖啡用纸质过滤器

浓缩咖啡篮及相关主题

意式咖啡观点

透明 Portafilter 实验

杠杆机维护

咖啡评论和想法

咖啡实验

使用 Python 连接到 Azure SQL Server

原文:https://towardsdatascience.com/connect-to-azure-sql-server-using-python-76eba1fb458b?source=collection_archive---------9-----------------------

本文提供了在 Linux 操作系统上使用 Python 连接到 Azure SQL Server 的分步教程。

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

马库斯·温克勒在 Unsplash 上拍摄的照片

本文提供了在 Linux 操作系统上使用 Python 连接到 Azure SQL Server 的分步教程。

创建 Azure SQL 数据库/服务器后,您可以在概述页面上找到服务器名称。

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

Azure SQL Server 使用 ODBC(开放式数据库连接)作为驱动程序。

数据库驱动程序是实现数据库连接协议(ODBC 或 JDBC)的计算机程序。

让我用通俗易懂的语言解释一下。您还记得我们购买硬件或软件时,会附带一张驱动程序磁盘,您必须在使用应用程序之前安装该驱动程序吗?嗯,你可以把数据库想象成应用程序,数据库驱动程序本质上是使我们能够访问数据库的驱动程序,或者 DBMS(数据库管理系统)。不同的数据库系统(Postgresql、Mysql、SQL Server、Oracle 等)有不同的驱动程序,大多数不是 ODBC 就是 JDBC。

Pyodbc是一个开源的 python 包,使访问 ODBC 数据库变得容易。有些人使用pymssql,但pyodbc是最受欢迎的一个。

让我们把手弄脏吧!首先,导入所需的包。我们使用sqlalchemy,这是一个流行的 python SQL 工具包,在这里创建连接,使用urllib创建连接字符串。

import os
import pyodbc
import sqlalchemy assa
from sqlalchemy import create_engineimport urllib (Python 2.7)
from urllib.parse import quote_plus (Python 3)

注意,我们将用来生成连接字符串的 quote_plus 在 Python 2.7 和 Python 3 中是不同的。建立连接的第一步是声明环境变量。我们使用os.getenv来指定变量和凭证,以便它们处于安全的状态。

server = os.getenv('SERVER_NAME')
database = os.getenv('DB_NAME')
username = os.getenv('USERNAME')
password = os.getenv('PASSWORD')
port = os.getenv('PORT')

Azure SQL Server 的默认端口是 1433。我们还需要一个变量,司机。为了找到正确的驱动程序,在您的终端中运行以下命令行(确保您安装了**pyodbc**):

$ odbcinst -j
unixODBC 2.3.4
DRIVERS............: /etc/odbcinst.ini
SYSTEM DATA SOURCES: /etc/odbc.ini
FILE DATA SOURCES..: /etc/ODBCDataSources
USER DATA SOURCES..: /home/jamesho/.odbc.ini
SQLULEN Size.......: 8
SQLLEN Size........: 8$ cat /etc/odbcinst.ini
[ODBC Driver 13 for SQL Server]
Description=Microsoft ODBC Driver 13 for SQL Server
Driver=/opt/microsoft/msodbcsql/lib64/libmsodbcsql-13.1.so.9.0
UsageCount=1

驱动程序的信息存储在odbcinst.ini文件中。将驱动程序设置为您的驱动程序的名称。

driver = '{ODBC Driver 13 for SQL Server}'

接下来,我们将设置连接字符串。定义连接字符串有两种方法,一种是使用urllib包下的 quote_plus 解析字符串,另一种是使用 sqlalchemy 的 URL 格式。

# Using urllib
odbc_str =
'DRIVER='+driver+';SERVER='+server+';PORT='+port+';DATABASE='+database+';UID='+username+';PWD='+passwordconnect_str = 'mssql+pyodbc:///?odbc_connect='+quote_plus(odbc_str)#Using sa URL format
sa_url = f"mssql+pyodbc://{username}:{password}@{server}:{port}/{database}?driver={driver}"

不同数据库的连接字符串的完整列表可以在这里找到。

最后,创建一个引擎,并将字符串传递给引擎。使用引擎的 execute 函数运行您的查询,该查询也应该作为字符串传递。

engine = create_engine(connect_str / sa_url)print(engine.execute(‘’’
                      YOUR SQL QUERY
                     ‘’’).fetchall())

完整脚本:

import os
import pyodbc
import sqlalchemy assa
from sqlalchemy import create_engine
import urllib (Python 2.7)
from urllib.parse import quote_plus (Python 3)server = os.getenv('SERVER_NAME')
database = os.getenv('DB_NAME')
username = os.getenv('USERNAME')
password = os.getenv('PASSWORD')
port = os.getenv('PORT',default=1433)driver = '{ODBC Driver 13 for SQL Server}'#connect using parsed URL
odbc_str = 'DRIVER='+driver+';SERVER='+server+';PORT='+port+';DATABASE='+database+';UID='+username+';PWD='+ password
connect_str = 'mssql+pyodbc:///?odbc_connect=' + quote_plus(odbc_str)#connect with sa url format
sa_url = f"mssql+pyodbc://{username}:{password}@{server}:{port}/{database}?driver={driver}"engine = create_engine(connect_str/sa_url)print(engine.execute('''
                        YOUR SQL QUERY
                    ''').fetchall())

转到您的终端,像这样导出环境变量,并运行这个 python 脚本。

$export SERVER_NAME = 
$export DB_NAME = 
$export USERNAME = 
$export PASSWORD = 
$export PORT =$python {your script name}.py

您已经成功连接到您的 Azure SQL 数据库,并且可以使用 sqlalchemy 与其进行交互。

连接生物学和人工智能:生长神经细胞自动机

原文:https://towardsdatascience.com/connecting-biology-and-ai-growing-neural-cellular-automata-fd53f2834ee2?source=collection_archive---------24-----------------------

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

卡罗琳娜·格拉博斯卡在的照片

1966 年,被认为是 20 世纪顶级数学家之一的约翰·冯·诺依曼引入了术语细胞自动机,并将其定义为以离散步骤进化的动态系统。四年后,约翰·康威(John Conway)创造了众所周知的生命游戏(Game of Life),其主要特点是进化是由其初始状态决定的,不需要进一步的输入。

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

维基百科,康威的人生游戏

此后,基于这些细胞自动机(CA)的研究不计其数。像扬森斯(2009 年)或者梅勒妮·米切尔(1998 年)这样的评论描述了这个领域中一些最相关的作品。

然而,一篇引起机器学习社区注意的文章是由 Mordvintsev 等人(2020) 发表的,他描述并实现了一个开发细胞自动机更新规则的神经网络。此外,当我阅读这篇文章时,我的一个相关贡献是作者将这项工作与形态发生联系起来,形态发生是一个生物学术语,指的是单细胞如何自我组装成高度复杂的有机体的过程。

我在这篇文章中的目标是向您介绍几个概念,以便这篇文章之后变得易于阅读。其结构如下:

  1. CA 简介
  2. 与生物学的联系
  3. 生长神经细胞自动机
  4. 未来的工作

1.CA 简介

如前所述,细胞自动机(CA)被约翰·冯·诺依曼定义为一个以离散步骤进化的动态系统。换句话说,元胞自动机由一个网格单元组成,该网格单元根据一组预定义的规则在每个时间步进行更新。单元的新状态将取决于它的当前状态和它的紧邻单元的状态。

这里有一个基本的例子,以便你简单地理解它的方法。

  • 1D CA 有两个可能的状态和一个 3 单元的邻域

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

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

  • 在第一个时间步长之后,输出如下所示。

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

  • 在第二个时间步骤之后,这里是输出。

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

  • 经过 n 个时间步后,我们得到下图。

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

下面是它如何更新的动画:

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

维基百科,动画为规则 110。

更改算法会显著改变输出。例如,使用规则 18:

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

有趣吧?在我看来,非常令人惊讶的是,我们可以用如此简单的规则创建这些数字。

如果你感兴趣,这里有一个规则的编号系统。这在以下链接的章节编号系统中有很好的解释。

2.与生物学的联系

与 CAs 类似,大多数多细胞生物从单细胞开始其生命,并生长直至成为高度复杂的解剖结构。这个过程被称为形态发生,它包括细胞如何与它们的邻居沟通,以决定器官的形状和位置。或者,更令人印象深刻的是,何时停止。

有趣的是,一些贝壳的图案如芋螺Cymbiola 是由自然细胞自动机生成的。对于这些贝壳来说,色素细胞位于贝壳边缘的一个狭窄区域。每个细胞根据其相邻色素细胞的激活和抑制活性分泌色素,遵循数学规则的自然版本。细胞带在缓慢生长时在外壳上留下彩色图案。

尽管对于从单细胞和规则中出现复杂生物体的相互作用仍有许多问题,但似乎很清楚的是,进化已经将这些信息编码在它们的基因组编码细胞硬件中。

3.生长神经细胞自动机

由于理解细胞形态发生过程的重要性,我们在计算机科学界的目标是制定新的模型来帮助阐明这些过程。

如上所述, Mordvintsev 等人(2020) 做出了相关贡献,因为他们实现了一个自动机,你可以给它一个图像,并可以创建一个算法,不仅可以增长细胞,直到获得图像,而且还可以在被破坏时再生。

如果你想看他们的结果,我鼓励你去这个网页,玩动画。

https://distill.pub/2020/growing-ca/

在这篇文章中,我不打算解释这个模型的架构,因为其他优秀的文章已经描述过了。特别是,除了原文,我强烈推荐阅读以下文章,并尝试他的代码

https://medium.com/the-scinder/playing-pokemon-grow-with-differentiable-cellular-automata-a233eb345439

我做了一些修改就实现了它,下面是我的输出。

  • 培训的第 100 个时代

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

  • 训练纪元 500 年

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

  • 训练纪元 1000 年

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

4.未来的工作

一旦你到了这一步,我想你会对这个话题感兴趣。因此,我首先会建议阅读原文,然后观看以下视频(点击视频下方的链接)。它展示了一些现在正在进行的关于这个话题的研究。这个视频属于 Cross Labs ,这是一个跨学科的研究机构,致力于通过计算研究来理解智能和生命的数学基础。具体来说,如果你有 10 分钟的时间,从 12 点 20 分到 22 点 20 分。

https://www.youtube.com/watch?v=XVmzGW293bI&t = 797s

如果你喜欢这篇文章,请考虑 订阅 。你将获得我所有的内容+所有其他来自牛逼创作者的文章!

将 Google Colab 连接到 Amazon EC2 实例

原文:https://towardsdatascience.com/connecting-google-colab-to-an-amazon-ec2-instance-b61be9f9cf30?source=collection_archive---------15-----------------------

提升您的 Colab 笔记本电脑的 GPU 性能

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

照片由西格蒙德Unsplash 上拍摄

在深入学习教程之前。让我们来谈谈 Jupyter 笔记本。

朱庇特

Jupyter 是一个免费的、开源的、可共享的、交互式的 web 应用程序,它允许用户组合代码、计算输出、可视化、文本和媒体。

Jupyter 笔记本已经成为数据科学家的首选计算工具。名字是由 Jupyter 目前支持的 40+编程语言中的三种语言 Ju lia、 py thon、 R 组成的。

笔记本的问题

笔记本并不都很棒。与使用笔记本相关的一些问题包括—

笔记本在运行长时间异步任务时会遇到问题。像深度学习中典型的那样训练一个模型几个小时或几天可能会变得乏味,特别是当显示超时时。对此的解决方法是定期检查模型权重并将日志文件写入磁盘。

笔记本电脑出现故障时返回的错误(应该注意,这更多是用户问题)

它鼓励糟糕的软件工程实践。例如,缺乏单元测试,将代码编写成可重用的块。

然而,许多人会认为这些都不应该被认为是问题,因为笔记本电脑从来就不是为解决这些问题而设计的。它非常适合快速实验和原型制作。很有可能将代码移动到脚本中,并且仍然从笔记本中调用它们。

Jupyter 笔记本是一种探索工具,而不是生产工具

科拉布

google Colaboratory 是一个基于 Jupyter 的免费笔记本环境,运行在 Google 的云服务器上,允许用户利用 Google 提供的硬件(CPU、GPU 和 TPU)。其中后两个对于数据科学家和机器学习工程师来说相当有用。使用 Colab 的另一个优点是它允许访问 google drive,可以通过文件浏览器安装和访问它。Colab 还预装了一套像 TensorFlow 和 Keras 这样的深度学习库。

谷歌 Colab 提供了 12GB 的 NVIDIA Tesla K80 GPU,NVIDIA 计算能力为 3.7,可连续使用长达 12 小时。虽然这对于实验和原型制作来说非常好,但是在处理大型数据集和/或大型网络时,很快就会遇到限制。

在我们进入教程之前,重要的是要注意,这不仅适用于亚马逊的 EC2 实例,还可以用于谷歌云的计算引擎、微软 Azure 的虚拟机,甚至是本地设置。

将外部运行时连接到 Colab 只是允许用户在使用 GPU 加速而不是 Colab 默认提供的加速时保留 Colab 接口。

使用 AWS,许多人更喜欢使用 SageMaker,因为它负责在后台创建 EC2 实例和设置 Jupyter 笔记本连接的细节,这使得 Sagemaker 比 EC2 更贵。因此,创建一个 EC2 实例并将其连接到一个 Colab 笔记本上,比使用 SageMaker 更便宜,同时还能保留(许多人)首选的 Colab 接口。

比较成本,俄亥俄州地区 EC2 上的一个 p3.2xlarge 实例每小时的成本为 3.06 美元,而同一地区 SageMaker 上的相同实例每小时的成本为 3.825 美元。

让我们开始吧。

亚马逊 EC2

登录 AWS 管理控制台。

点击左上角的服务并选择 EC2。

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

EC2 仪表板

在左窗格中选择实例,然后启动实例。

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

EC2 左侧窗格

选择图像类型。这决定了预装的操作系统和软件版本。这里我们选择了一个 Ubuntu 18.04 安装和 TensorFlow 2.4.1 以及 CUDA 安装。

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

AMI 图像

接下来,我们选择实例类型。这将决定我们得到的硬件类型。出于本教程的考虑,我将选择一个 p 3.2x 大型实例。这包括一个 Nvidia V100 GPU、8 个 vCPUs 和 61GB RAM。

如果这是您第一次启动 GPU 实例,请注意默认情况下 GPU 实例不可用。查看包含的链接了解如何使用 AWS 增加 GPU 实例限制。此外,GPU 实例不是免费的,请参见此链接了解点播价格。请注意,不同地区的价格不同。

如果您希望设置存储和网络选项等其他详细信息,可以选择“配置实例详细信息”。要保留默认设置,请选择“查看并启动”。

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

实例类型

选择现有的密钥对或创建新的密钥对。这将作为登录服务器的身份验证。如果一个新的被创建,一个。pem 文件将被下载到您的本地计算机。

查看详细信息,然后单击启动

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

密钥对

通过单击左侧窗格中的实例,返回到实例仪表板。这将列出所有实例,包括刚刚创建的实例。等待创建的实例如下所示,实例状态显示为“正在运行”,状态检查为“2/2 检查通过”。这意味着实例现在正在运行。

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

单击实例 ID。您应该会看到如下所示的屏幕。然后点击连接。

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

通过 SSH 连接

单击 ssh 客户端的https://console.aws.amazon.com/ec2/v2/home?region=us-east-1#选项卡,查看该实例的 SSH 登录详细信息。

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

SSH 详细信息

然而,对于本教程,我们将使用 putty SSH 客户端登录到实例。Putty 可以从这里下载。我们使用 Putty 的主要原因是为了设置 SSH 隧道。这是让 Colab 连接到 EC2 运行时所需要的。

PuttyGen

在我们安装油灰之前。如果我们回想一下,从 AWS 下载的密钥文件是. pem 文件格式。我们需要将它转换成 putty 可以识别的格式。putty 的安装中包括另一个名为 PuttyGen 的程序。此工具可以将. pem 文件转换为. ppk 文件。打开 PuttyGen,选择文件→加载私钥

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

PuttyGen

选择。要加载的 pem 文件。选择文件→保存私钥以存储加载的内容。pem 文件在。ppk 格式。

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

PuttyGen 另存为 ppk

既然密钥文件的格式正确,我们就可以在 putty 上设置 SSH 连接了。

油灰

在前面的步骤中,在 SSH Client 选项卡中,我们查看了 EC2 实例的 SSH 登录信息。我们现在需要它。(需要注意的一点是,每次重启实例时,SSH 登录信息都会改变,请务必再次复制该信息)。

确保通过在“保存会话”文本框中指定名称并单击“保存”将详细信息保存到配置文件中。在下面的例子中,我选择“aws”作为要另存为的概要文件名。

油灰应如下图所示设置—

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

油灰型材

保存后,单击配置文件名,然后单击 Load。

SSH 隧道

在左侧导航树中,选择连接→ SSH →隧道。

在源端口中,填写 8888(我们将在后面指定,这是 Jupyter 将通过的端口)。在目的端口中,填写 127.0.0.1:8888,然后单击添加。最终结果应该如下所示—

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

SSH 隧道

也可以将它保存到个人资料中,这样就不需要每次都输入了。转到会话,选择配置文件,然后单击保存。

现在我们已经准备好用 putty 登录 EC2 实例了。在左侧导航树中,转到连接→ SSH → Auth,单击浏览并选择。ppk 文件,然后单击打开。

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

油灰认证

成功登录后,putty 应该看起来像这样。我们现在有一个命令行来控制 EC2 实例。只要 SSH 终端窗口打开,来自源端口的所有流量都会被转发到目的端口。

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

EC2 端子

如果 Jupyter 还没有安装,应该通过命令行安装。跟着这个链接

接下来需要安装由 Google Colabotory 创作的 jupyter_http_over_w 扩展,以允许连接到 Colab。在命令行中运行下面的命令—

*****pip install jupyter_http_over_ws******jupyter serverextension enable — py jupyter_http_over_ws*****

使用下面的命令在 EC2 实例上启动 Jupyter Notebook 服务—

****jupyter notebook \
 — NotebookApp.allow_origin=’**[**https://colab.research.google.com**](https://colab.research.google.com/)**' \
 — port=8888 \
 — NotebookApp.port_retries=0
 — NotebookApp.disable_check_xsrf=true”****

我们将端口 8888 指定为 SSH 隧道配置期间指定的相同端口。

如果一切顺利,终端屏幕上应该会显示一个 IP 地址。应该复制该地址,因为下一步将需要它。

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

笔记本终端

打开 Google Colab,在右上角选择 Connect to local runtime。

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

Colab 本地运行时

从终端复制 IP 地址并点击连接。

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

Colab 后端 URL

最终结果应该是这样的。请注意“已连接”旁边的“本地”。这意味着 Colab 连接到一个运行时,而不是默认的 Colab。我们还运行一些测试来确认 GPU 被检测到。

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

Colab 笔记本

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

Colab 列出设备

我们在下面注意到,检测到的 GPU 是 Tesla V100,这是典型的 P3.2xlarge 实例类型。

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

Colab T100

快速笔记。连接到本地运行时意味着 Colab 将不再能够访问 Google Drive。为了解决这个问题,一个可能的工具是 P yDrive

完成后,不要忘记关闭 EC2 实例。

参考文献

Stern J (2012)如何用 PuTTY 建立 SSH 隧道https://www . sky verge . com/blog/How-to-Set-Up-an-SSH-Tunnel-With-PuTTY/

Perkel J (2018)为什么 Jupyter 是数据科学家的首选计算笔记本https://www.nature.com/articles/d41586-018-07196-1

穆勒 A (2018)木星笔记本吸的 5 个理由https://towards data science . com/5-reasons-why-jupyter-notebooks-suck-4d c201 e 27086

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值