FlashBlade 上的 Jupyter 服务
如何管理大规模数据科学家的开发环境?
戴维·梅尼德雷在 Unsplash 上拍摄的照片
Jupyter 笔记本是数据科学家探索数据集和进行模型开发实验的绝佳工具。它们使开发人员能够轻松地用分析和可视化来补充代码。
与让用户管理他们自己的笔记本服务器的传统做法不同, JupyterHub 可以由一个组织来部署,以提供一个集中的笔记本平台。JupyterHub 还支持基础设施团队为每个用户提供对集中存储的访问:共享数据集、暂存空间和持久 IDE。
这篇博文展示了一个在纯存储闪存上部署 Jupyter-as-a-Service 的例子。用户可以在 Kubernetes 集群中通过零接触配置动态创建新的笔记本电脑服务器。IT 团队能够跨用户管理计算和存储资源的高效使用。
朱庇特枢纽
JupyterHub 用于管理和代理“单用户”Jupyter 笔记本服务器的多个实例。它在您的网络上提供了一个公共 HTTP 代理,因此用户可以从他们的浏览器登录到一个中央登录页面。一旦用户登录,JupyterHub 就会为该用户启动一个服务器(pod)。它会重新连接到该用户的永久存储。因此,用户可以拥有有状态的开发环境,但是计算节点仅在需要时使用。
我们将把 JupyterHub 部署为 Kubernetes 服务,这样它就可以作为集群的一部分轻松管理。
Kubernetes 环境中的 FlashBlade
出于几个原因,FlashBlade 是 JupyterHub 的优秀存储后端。
首先,它支持就地访问训练数据集,消除了在节点之间复制数据集的需要。数据科学家可以使用共享数据集,通过最少的数据管理来执行模型的训练和测试。
第二,FlashBlade 支持 Pure 的 CSI 驱动,Pure Service Orchestrator(PSO)。PSO 完全自动化 Kubernetes 集群中应用程序的持久卷 (PV)的创建和管理,通过消除新用户的手动存储管理,为 JupyterHub 部署带来自助服务。
JupyterHub 只是众多应用程序中的一个,它们共同为数据科学家形成了一个完整的人工智能平台。为了简化管理和高效的数据管理,所有这些应用程序都应该由相同的集中式存储提供支持。
移除存储筒仓。
装置
准备步骤
- 克隆我们的 AI 平台回购
- 在您的本地机器上,确保您的集群配置对于 kubectl 是活动的。
- 在您的本地机器上,安装舵和用于 PSO 的舵回复和用于 JupyterHub 的:
helm repo add pure [https://purestorage.github.io/helm-charts](https://purestorage.github.io/helm-charts`)helm repo add jupyterhub [https://jupyterhub.github.io/helm-chart/](https://jupyterhub.github.io/helm-chart/`)
- 群集中的每个节点都需要能够访问 FlashBlade 上的数据集。在
/datasets
将数据集文件夹直接挂载到每个集群节点。
部署 PSO
**定制:**您需要一个描述您的 FlashBlade 阵列的 psovalues.yaml 文件。最简单的方法是复制我们默认的。/psovalues.yaml 并调整“数组”部分。
定制示例:
arrays:
FlashBlades:
- MgmtEndPoint: "10.61.169.20" # CHANGE
APIToken: "T-c4925090-c9bf-4033-8537-d24ee5669135" # CHANGE
NFSEndPoint: "10.61.169.30" # CHANGE
安装:
helm install pure-storage-driver pure/pure-csi — namespace jhub -f ./psovalues.yaml
为共享数据集部署 PV
定制:
的。/datasetpv.yaml 文件用于创建名为“shared-ai-datasets”的持久卷声明。调整 datasetpv.yaml 以使用您的 FlashBlade 数据 VIP 和文件系统名称。
nfs:
server: 10.61.169.100 # CHANGE to your data vip
path: /datasets # CHANGE to your filesystem name
安装:
kubectl create -f datasetpv.yaml
部署 JupyterHub
自定义:
jupvalues.yaml 文件唯一需要的更改是添加一个安全令牌。生成随机十六进制字符串:
openssl rand -hex 32
复制输出,在 jupvalues.yaml 文件中,用生成的字符串替换 SECRET_TOKEN 短语:
proxy:
secretToken: 'SECRET_TOKEN' # CHANGE to 32-digit secret token
安装:
helm install jhub jupyterhub/jupyterhub — namespace jhub — version 0.8.2 -f jupyterhub/values.yaml
用 Jupyter 笔记本!
JupyterHub 现在可以使用了。
安装 JupyterHub 会创建一个代理服务,为最终用户提供流量服务。公共地址(proxy-public)可以通过以下方式找到:
> kubectl --namespace=jhub get svc proxy-publicNAME TYPE CLUSTER-IP EXTERNAL-IP
proxy-public LoadBalancer 10.43.197.255\. 10.61.169.60
当用户导航到 proxy-public 的外部 IP 地址时,他们将看到 JupyterHub 登录屏幕:
当 Victor 登录时,他可以访问共享数据集(如 cifar10 和 openimages)以及个人笔记本、绘图和文件的主目录。
结论
在 Kubernetes 集群内将 JupyterHub 作为服务运行很容易部署和管理。数据科学家不仅拥有支持其个人环境的持久存储,还可以访问所有共享数据集,而无需耗时的数据复制或复杂的数据管理。
我们的代码在 github 上:【https://github.com/PureStorage-OpenConnect/ai-platform
尝试这些快速安装步骤,并让我们知道进展如何。
从本地到生产的 Jupyter 部署模型
你现在处于哪个阶段?
凯文·杰瑞特在 Unsplash 上的照片
对于我们这样的书呆子来说,我们的数据分析习惯并不会随着我们合上笔记本电脑而停止。当你坐在数不清的会议上进行无休止的谈话时,你可能已经有了一些认识。对我来说,事实是从我的会议座位上可以看到 90%的开放屏幕显示 Jupyter 笔记本正在运行。
对于我们中的许多人来说,我们的笔记本服务器只是通过jupyter notebook
或jupyter notebook --allow-root --no-browser --port=8885
启动的,如果我们喜欢并强行解决我们不想解决的权限和端口问题。
这种方法的科学时间是明确的,但我想快速描绘一些先进的,可扩展的 Jupyter 部署和一些介于jupyter notebook
和魔法之间的中级水平。
希望你能感觉到什么是可能的。
模型 1:在您的笔记本电脑(Mac)上运行 JupyterLab
(谁在看这个帖子却没有 Mac?)
如果你只是想增强你的基本 Jupyter 体验,或者你只是想开始,我建议从这里开始。尤其是当你的数据集和实验只存在你的笔记本电脑上的时候。
JupyterLab 是 Jupyter 的一个 web 界面,它允许比传统的“树”视图更广泛的导航和灵活性,如果你启动 vanilla Jupyter,你就会看到它。JupyterLab 让你可以像浏览器一样在多个标签页中工作。
JupyterLab 提供了比传统的单一窗格“树”视图更丰富的开发体验。
直接从 mac 终端在 JupyterLab 自己的 conda 环境中运行 JupyterLab:
先决条件: 安装康达。
Conda 使您能够轻松管理软件包和环境,以便您可以在笔记本电脑(或另一台机器)上使用不同的库组合。这是一个非常简单的方法来安装所有你想尝试的有趣的新库。
从你 Mac 终端运行 JupyterLab: -
-步骤 1:创建一个新的“JupyterLab”conda 环境
conda create -n jupyterlab ipython jupyterlab python nodejs
-步骤 2:切换到那个新环境
source activate jupyterlab
-步骤 3:启动 JupyterLab
jupyter lab
该命令将自动启动一个浏览器窗口,但是每次您导航到 http://localhost:8888 时,您将获得您的实验室 UI。
服务器将一直运行,直到您手动关闭它(使用 CTRL-C)或关闭终端窗口。关于开始 JupyterLab 的进一步阅读是这里。
看中: 雅各布·汤姆林森的这篇伟大的文章讲述了如何在电脑启动时自动启动 JupyterLab。
模型 2:在数据集所在的远程服务器上运行 JupyterLab
也许你听说过“数据科学是导致 Excel 崩溃的任何东西”的说法,接下来的阶段是不适合笔记本电脑的任何东西。随着实验规模的扩大,你可能会遇到这两种情况
- 您的笔记本电脑计算能力不足
- 您的笔记本电脑存储空间不足
无论哪种方式,解决方案都可能是从您的开发运维/IT 团队那里获得一个强大的开发服务器。这个开发服务器将被托管在一个你永远看不到的实验室里。你只要远程访问它。
或者可能仅仅是 Covid 期间的 WFH 让你在通常直接工作的机器上远程工作。
在远程机器上启动 Jupyter 的挑战是访问 UI。
场景 A:在你和远程机器之间没有防火墙
将--ip
参数添加到 jupyter 启动命令中。它设置笔记本服务器监听的 IP 地址(默认值=“localhost”)。
jupyter notebook --ip=<remote server IP address> --port=8888
在您的笔记本电脑浏览器中,您可以直接连接到 http:// :8888/服务器,而不是导航到 http://localhost:8888/。
想象一下: 每次你打开笔记本电脑的时候,你会在你的远程主机上重启你的 Jupyter 吗?
你可以使用一个终端复用器,比如 tmux 或者 screen 来分离你的远程主机上的会话。这样,会话就不依赖于来自本地主机的连接。
关于 tmux 和 screen 的比较,可以看看这个 StackExchange 帖子 ,但是正如标题警告所说,这是一个基于观点的问题。
场景 B:您的笔记本电脑服务器运行在防火墙后的某个地方,比如公共云中。
说明因云供应商而异(见下文),但总体步骤如下:
- 从远程服务器中启动 jupyter
- 从您的本地机器,配置端口转发。
端口转发? 当你启动一个 Jupyter 服务器时,默认情况下,GUI 被托管在****机器上的一个端口上,在那里服务器被启动。在这个场景中,端口转发告诉您的本地机器接收特定本地端口的任何流量,并将其转发到远程机器上的端口。(延伸阅读: 你 CS 教育的缺失学期 )****
供应商特定说明:
AWS
-官方文档:为 AWS 深度学习 AMI 设置 Jupyter
-用户示例
GCP
-官方文档:连接到深度学习虚拟机映像的 JupyterLab
-用户示例(包括更改实例的防火墙设置作为端口转发的替代方案)
Azure
-官方文档:在 Azure 机器学习开发环境中配置 Jupyter(使用 Azure 笔记本作为服务器)
模型 3:在 Kubernetes 集群中运行 JupyterHub,为多个开发人员提供持久的开发环境。
这是我的梦想。
如果您使用以前的笔记本部署方法之一,
- 每次回到电脑前,您需要多长时间才能启动笔记本电脑?
- 你能探索多大的数据集?
- 你备份你的笔记本吗?
如果有人为您提供了一个可靠的开发环境,可以通过浏览器始终可用**,并且可以访问共享数据集和共享笔记本,会怎么样?(而且,正如 IT 团队可能关心的那样:它是安全的,可跨数十或数百个用户进行管理。)**
虽然这需要更多的配置——可能由了解您的网络设置的人来执行—JupyterHub可能是为整个团队托管自助服务环境的一种很好的方式。
JuyterHub 服务持续运行,为用户提供基于浏览器的登录。当用户登录时,会为他们启动一个 Jupyter 服务器,它会自动连接到 a)他们以前登录的个人数据和 b)他们需要试验的任何共享数据集。
JupyterHub 环境的用户可以快速、持久地访问大型共享数据集和他们自己的私人实验文件夹。
这种部署意味着用户不必在服务器之间复制数据,他们可以随时获得高可用性的开发环境,并且他们的实验易于备份和共享。
我之前曾发布过关于 IT 团队如何在 Kubernetes 环境中部署 JupyterHub 的详细步骤。我在这里简单总结一下。
有 Kubernetes 集群吗?
是的,我们今天用 Kubernetes:
- 为您的存储服务器安装 csi 驱动程序。CSI 驱动程序在后台运行,使 Kubernetes 能够直接使用存储,因此用户可以以完全自动化的自助方式访问数据。
- "导入"将您的共享数据集 TBs 作为 Kubernetes 卷,这允许您将该数据作为 Kubernetes 集群中的资源进行管理。
- 通过头盔部署 JupyterHub。如果您需要一个示例 JupyterHub values.yaml 文件来进行配置,请随意使用 mine 。
- 您可以将 JupyterHub 与 LDAP 服务器集成,以利用现有的用户帐户。
JupyterHub 将在群集外部的 IP 地址上提供登录屏幕,供您网络上的用户使用。当用户登录时,他们可以访问共享数据集以及个人笔记本、绘图和文件的主目录。
延伸阅读: Zero to JupyterHub 同 Kubernetes 。
我们今天不使用 Kubernetes: 安装 JupyterHub 更容易!点击查看简单步骤。
结论
当你回到电脑前,难道你不想直接跳到你的项目中吗?
无论您的实验和数据集位于何处,都有可能消除不断重新部署开发环境的麻烦。用你的时间去做更有用的事情,而不是一遍又一遍地旋转 Jupyter。
Jupyter 现在是一个成熟的 IDE
通过 nbdev 和 Jupyter 新的可视化调试器,有文化的编程现在已经成为现实。
笔记本一直是软件思想增量开发的工具。数据科学家使用 Jupyter 来记录他们的工作,探索和实验新的算法,快速勾画新的方法,并立即观察结果。
然而,当时机成熟时,软件开发人员转向经典的 ide(集成开发环境),如 Visual Studio Code 和 Pycharm,以将想法转换为库和框架。但是有没有办法将 Jupyter 转变成一个成熟的 IDE,将原始的概念转化成健壮的、可重用的模块?
为此,来自多个机构的开发者,包括 QuantStack、两个适马、彭博和 fast.ai 开发了两个新颖的工具;Jupyter 的 nbdev 和可视化调试器。
学习率是我每周给那些对 AI 和 MLOps 世界好奇的人发的简讯。你会在每周五收到我关于最新人工智能新闻、研究、回购和书籍的更新和想法。在这里订阅!
识字编程和 nbdev
1983 年,Donald Knuth 提出了一个新的编程范例,叫做识字编程。用他自己的话说,有文化的编程是一种将编程语言和文档语言结合起来的方法,从而使程序比只用高级语言编写的程序更健壮、更可移植、更容易维护,并且可以说编写起来更有趣。 主要思想是把一个程序当作一篇文献,写给人类而不是写给计算机 ”。
去年晚些时候,杰瑞米·霍华德和西尔万·古格被 nbdev 的设计深深吸引。这个框架允许您在熟悉的 Jupyter 笔记本环境中编写代码,在找到给定问题的有效解决方案之前探索和试验不同的方法。然后,使用某些关键字,nbdev 允许您将有用的功能提取到一个成熟的 python 库中。
更具体地说,nbdev 补充了 Jupyter,增加了对以下内容的支持:
- 遵循最佳实践,从笔记本中自动创建 python 模块
- 在标准 IDE 中编辑和导航代码
- 将任何更改同步回笔记本
- 从代码中自动创建可搜索的超链接文档
- pip 安装程序很容易上传到 PyPI
- 测试
- 持续集成
- 版本控制冲突处理
nbdev 使软件开发人员和数据科学家能够在不脱离 Jupyter 环境的情况下,遵循最佳实践,开发文档完备的 python 库。nbdev 在 PyPI 上,要安装它,只需运行:
pip install nbdev
对于可编辑安装,使用以下:
git clone https://github.com/fastai/nbdev
pip install -e nbdev
首先,阅读由开发者撰写的优秀的博客文章,描述 nbdev 背后的概念,并遵循文档中的详细教程。
缺失的部分
尽管 nbdev 涵盖了 Jupyter 内部 IDE 类开发所需的大部分工具,但仍然缺少一部分;可视化调试器。
因此,来自几个机构的开发人员团队昨天宣布了 Jupyter 可视化调试器的首次公开发布。调试器提供了您对 IDE 调试器的大部分期望:
- 变量资源管理器、断点列表和源代码预览
- 导航调用堆栈的可能性(下一行、进入、退出等。)
- 直观地在感兴趣的行旁边设置断点的能力
- 指示当前执行停止位置的标志
为了利用这个新工具,我们需要一个在后端实现 Jupyter 调试协议的内核。因此,第一步是安装这样一个内核。目前唯一实现的是[xeus-python](https://github.com/jupyter-xeus/xeus-python)
。要安装它,只需运行:
conda install xeus-python -c conda-forge
然后,运行 Jupyter Lab,在侧边栏搜索Extension Manager
并启用它,如果你还没有这么做的话。
启用扩展管理器
一个新的按钮将出现在侧边栏上。要安装调试器,只需转到新启用的Extension Manager
按钮并搜索debugger
扩展。
启用调试器
安装后,Jupyter 实验室将要求您执行构建,以包括最新的变化。接受它,几秒钟后,你就可以走了。
为了测试调试器,我们创建了一个新的xpython
笔记本,并编写了一个简单的函数。我们照常运行该函数,并观察结果。要启用调试器,请按窗口右上角的相关按钮。
启用调试器
现在,我们准备再次运行该函数。只有这一次,执行将在我们设置的断点处停止,我们将能够探索程序的状态。
调试代码
我们看到程序在断点处停止了。打开调试器面板,我们可以看到变量、断点列表、调用堆栈导航和源代码。
Jupyter 新的可视化调试器提供了 IDE 调试器所能提供的一切。它仍在开发中,因此,新的功能是预期的。它的开发者计划在 2020 年发布的一些功能有:
- 在变量浏览器中支持丰富的 mime 类型呈现
- 支持用户界面中的条件断点
- 从 JupyterLab Voilà预览扩展启用 Voilà仪表板的调试
- 启用尽可能多内核的调试
结论
Jupyter 笔记本一直是探索和试验代码的好方法。然而,软件开发人员通常求助于一个成熟的 IDE,复制工作的部分,以产生一个生产就绪的库。
这不仅效率低下,也是 Jupyter 产品的损失;识字编程。此外,笔记本电脑提供了一个更好的文档环境,包括图表、图像和视频,有时还有更好的工具,如自动完成功能。
nbdev 和 visual debugger 是两个旨在缩小笔记本和 ide 之间差距的项目。在这个故事中,我们看到了什么是 nbdev,以及它是如何使识字编程成为现实的。此外,我们发现了一个新项目 Jupyter 的可视化调试器如何提供缺失的部分。
我叫 Dimitris Poulopoulos,是希腊比雷埃夫斯大学*BigDataStack的机器学习研究员和博士©。我曾为欧洲委员会、欧盟统计局、国际货币基金组织、欧洲中央银行、经合组织和宜家等主要客户设计和实施人工智能和软件解决方案。如果你有兴趣阅读更多关于机器学习、深度学习和数据科学的帖子,请在 twitter 上关注我的 中 、LinkedIn或@ james2pl**。***
Jupyter 准备生产;原样
无需编写一行代码,即可将您的笔记本草稿转化为生产就绪的 Kubeflow 管道
机器学习项目通常由多个相互关联的步骤组成:数据采集、数据处理、数据建模、微调、测试等。这些步骤中的每一步都可以是一个独立的过程,以自己的节奏运行,具有明确定义的输入和输出。因此,数据科学家和 ML 工程师倾向于认为这些项目像管道。
数据科学家的理想场景是将 Jupyter 笔记本提供的实验环境转变为生产就绪的 ML 管道。
然而,ML 管道是一种很难编码的东西;连接到数据源,将正确的输入传递到每个步骤,序列化输出,检查点,找出依赖关系……如果我们能够自动化配置工作流执行所需的样板代码的苦差事,那不是很好吗?
数据科学家的理想场景是将 Jupyter 笔记本提供的实验环境转变为生产就绪的 ML 管道。嗯,我们今天就可以做。此外,我们无需编写任何代码就能做到这一点。
学习率是为那些对 AI 和 MLOps 的世界感到好奇的人准备的时事通讯。你会在每周五收到我关于最新人工智能新闻和文章的更新和想法。在这里订阅!
KubeFlow 简介
Kubeflow 是一个开源项目,致力于使 ML 项目的部署更加简单、可移植和可伸缩。来自文档:
Kubeflow 项目致力于使在 Kubernetes 上部署机器学习(ML)工作流变得简单、可移植和可扩展。我们的目标不是重新创建其他服务,而是提供一种简单的方法来将 ML 的最佳开源系统部署到不同的基础设施上。无论你在哪里运行 Kubernetes,你都应该能够运行 Kubeflow。
但是我们如何开始呢?我们需要 Kubernetes 集群吗?我们应该自己部署整个系统吗?我的意思是,你看过库伯弗洛的清单回购吗?
在 Kubeflow 上运行笔记本所需要的只是一个谷歌云平台(GCP)账户和你的旧笔记本文件!
此外,假设我们已经启动并运行了 Kubeflow 我们如何将我们的笔记本电脑转变为库巴流管道(KFP)?我们必须建立 docker 图像吗?你看过 KFP DSL 吗?我认为重点是消除样板代码。
嗯,我有好消息;我们所需要的只是一个谷歌云平台(GCP)账户和你的旧笔记本文件!
部署 Kubeflow
我将保持简单,不使它变得愚蠢。事实是,只需几分钟就可以轻松运行 Kubeflow 的单节点实例。我们需要的只是一个 GCP 帐户和从市场部署应用程序的能力。我们要用 MiniKF !
MiniKF 部署—作者图片
- 去你的 GCP 控制台
- 搜索市场然后找到 MiniKF
- 点击它并选择启动
- 设置 VM 配置,(由于我的配额,我通常将数据磁盘更改为标准持久磁盘)并单击 deploy。
就是这样!部署最多需要十分钟,您可以按照屏幕上的说明观看进度;ssh 进入机器,在终端上运行minikf
,等待直到您准备好端点和凭证。
MiniKF 的提供已完成—图片由作者提供
现在,我们准备访问 Kubeflow 仪表板。点击网址,输入你的凭证,你就可以开始了!
Kubeflow 仪表板—按作者分类的图像
运行 Jupyter 服务器
为了运行我们的实验,我们需要一个 Jupyter 笔记本实例。在 Kubeflow 中创建一个 Jupyter 笔记本相对容易。我们首先需要创建一个 Jupyter 服务器并连接到它。让我们这样做:
- 从左侧面板中选择笔记本
- 选择
New Server
按钮 - 填写服务器的名称,并请求您需要的 CPU 和 RAM 数量
- 让 Jupyter 笔记本图像保持原样——这对本教程至关重要(
jupyter-kale:v0.5.0-47-g2427cc9
—注意图像标签可能不同)
创建 Jupyter 服务器—作者图片
完成这四个步骤后,等待笔记本服务器准备好并连接。你将被转移到你熟悉的 JupyterLab 工作区。
Jupyter 到 ML 管道
那么,我们为什么要做这些设置呢?我们的目标是将我们的笔记本电脑转变为生产就绪的 ML 管道。我们如何做到这一点?
在这个例子中,我们将使用众所周知的泰坦尼克号数据集来演示一个我们可以遵循的简单工作流程。首先,在 JupyterLab 环境中创建一个新的终端,并克隆这个示例。
git clone [https://github.com/dpoulopoulos/medium.git](https://github.com/dpoulopoulos/medium.git)
如果您以前没有在 JupyterLab 中创建过终端,请注意 JupyterLab 终端提供了对系统 shells(例如 bash、tsch 等)的全面支持。)和 Windows 上的 PowerShell。您可以使用终端在系统 shell 中运行任何东西,包括 vim 或 emacs 之类的程序。所以你也可以用它来克隆来自 GitHub 的任何回购。
在 JupyterLab 中克隆泰坦尼克号的例子——图片由作者提供
克隆了回购之后,可以在medium > minikf > titanic.ipynb
中找到泰坦尼克的例子。您可以花一些时间浏览笔记本,但是有一个关键的步骤您需要首先运行:取消第一个代码单元的注释,并运行它以将必要的依赖项安装到您的环境中。
!pip install --user -r requirements.txt
运行这个单元后,重启内核,就可以开始了。如果你检查笔记本的左面板,你会看到一个紫色的图标。这是有趣的开始…按下它来启用羽衣甘蓝扩展。你会自动看到每个单元格都被标注了。
启用 Kale 扩展-按作者分类的图像
你可以看到笔记本是分节的;导入、数据加载部分、数据处理、模型训练和评估等。这正是我们用羽衣甘蓝注释的。现在,这个笔记本是预先注释好的,但是你可以随意使用。您可以创建新的管道步骤,但是不要忘记添加它们的依赖项。
在任何情况下,你都可以点击位于 Kale 部署面板底部的COMPILE AND RUN
按钮。无需编写一行代码,您的笔记本将被转换为 Kubeflow 管道,该管道将作为新实验的一部分执行。
从 Jupyter 笔记本到 Kubeflow 管道——作者图片
按照 Kale 提供的链接观看跑步实验。几分钟后,管道将成功完成其任务。这是图表的最终视图(不要忘记切换左上角的Simplify Graph
选项):
泰坦尼克号管道——作者图片
恭喜你!您刚刚将您的笔记本变成了一个管道,而没有编写一行代码,最重要的是,没有偏离常规程序。
结论
最后,您可以对这个数据集做更多的工作;可以多分析一下,添加交叉特征或者训练不同的分类器。事实上,在未来的故事中,我们将看到如何运行超参数调优,而无需添加任何额外的代码行。但是在数据集上实现最佳的准确性并不是本文的重点。
我们看到了如何在不编写任何样板代码的情况下启动单节点 Kubeflow 实例、创建笔记本服务器并将简单的 Jupyter 笔记本转换为 Kubeflow 管道。所以,去吧;实现自己的想法,一键变成 ML 管道!最后,不要忘记停止你的实例,以避免累积成本!
关于作者
我叫迪米特里斯·波罗普洛斯,我是一名为阿里克托工作的机器学习工程师。我曾为欧洲委员会、欧盟统计局、国际货币基金组织、欧洲中央银行、经合组织和宜家等主要客户设计和实施人工智能和软件解决方案。
如果你有兴趣阅读更多关于机器学习、深度学习、数据科学和数据运算的帖子,请在 twitter 上关注我的媒体、 LinkedIn 或 @james2pl 。
所表达的观点仅代表我个人,并不代表我的雇主的观点或意见。
Jupyter 笔记本:机器学习的简短介绍
Jupyter = Julia + Python + R
马里乌斯·马萨拉尔在 Unsplash 上的照片
如果你是一名数据科学家,你可能会每天记录完整的分析过程,就像其他科学家使用实验室笔记本记录测试、进度、结果和结论一样。你用什么工具来做同样的事情?我每天都在使用 Jupyter 笔记本,让我给你简单介绍一下。
- 什么是 Jupyter 笔记本?
- 为什么它对数据分析有用。
- Jupyter 笔记本有什么特点?
- 在机器学习中执行简单的数据分析。
Jupyter 笔记本简介
什么是 Jupyter 笔记本?
Jupyter 项目是 I-Python 项目的一个衍生项目,I-Python 项目最初只为 Python 语言提供了一个接口,并继续为 Jupyter 提供规范的 Python 内核。Jupyter 这个名字本身就来源于 Julia、Python 和 r 的组合。
这是使用 Jupyter 时的示例打开页面
为什么有用?
Jupyter 项目的存在是为了开发一个开放源代码平台、开放标准和跨多种编程语言(例如 Python、R 和 MATLAB)的交互式计算服务。
Jupyter 是一个基于云生态系统的网络应用,可以从很多地方获得,比如土星云。它也可以在各种各样的装置上本地使用。其中包含实时代码、等式、图表、交互式应用程序和降价文本。
Jupyter 笔记本的特点?
Jupyter 笔记本基本上是一个带有大量注释的 JSON 文件。笔记本有以下三个主要部分。
- **元数据:**定义的数据字典,用于设置和显示笔记本。
- **笔记本格式:**用于创建笔记本的软件的版本号。版本号用于向后兼容。
- **单元格列表:**有三种不同类型的单元格——降价(显示)、代码(激励)和输出。
如果在文本编辑器中打开 IPYNB 文件,您将看到 Jupyter 节点的基本内容
我们将如何使用 Jupyter 笔记本电脑?
有如下四个步骤。
- **第一步:**为数据分析创建一个新的笔记本。
- **第二步:**添加您的分析步骤、编码和输出。
- **第三步:**围绕你的分析,组织和展示降价,传达整个故事。
- **最后一步:**其他人可以通过修改参数和数据来使用交互式笔记本,以记录他们所做更改的效果。
获得带有土星云的 Jupyter 笔记本
获得 Jupyter 笔记本的最快方法之一是在 Saturn Cloud 上注册一个帐户。它允许您在云中快速启动 Jupyter 笔记本电脑,并根据您的需求进行扩展。
- 它部署在您的云中,因此无需迁移您的数据。通过 Jupyter 使用整个 Python 生态系统。
- 轻松构建环境和导入包(Pandas、NumPy、SciPy 等)。
- 您可以发布笔记本,并在云托管的 Jupyter 上轻松协作。
- 从笔记本电脑到服务器再到集群的可扩展 Dask。
以上是在土星云上创建 Jupyter 笔记本的步骤。
进一步见:https://www . Saturn cloud . io
我们能把 Jupyter 笔记本转换成 Python 脚本吗?
是的,您可以将 Jupyter 笔记本转换为 Python 脚本。这相当于将每个代码块(单元格)的内容复制并粘贴到单个。py 文件。降价部分也作为注释包含在内。
转换可以在命令行中完成,如下所示。
jupyter nbconvert --to=python notebook-name.ipynb
从笔记本到脚本的示例
使用 Jupyter 笔记本进行 ML 的一个例子
假设你是一名医生,你正在评估一千人的数据,并预测某人是否会感染冠状病毒。
我们将通过计算 TP、TN、FP、FN、TPR、TNR、PPV、NPV、FPR 和 ACC 等指标来逐步评估我们的算法。让我们假设你熟悉这些指标(如果不熟悉,请进一步阅读 here⁴).
在我们尝试评估我们的算法之前,有两件事。
- 我们预测的:
y_pred
。 - 我们得到的结果:
y_true
。
我们创建一个新的木星笔记本文件— “coronavirus.ipynb”
如下。
结论
我们学习了如何用土星云把 Jupyter 笔记本放到云上。我们也接触了笔记本的结构。我们看到了开发笔记本电脑时使用的典型工作流程。最后,我们在 ML 中做了一些简单的数据分析。
参考
[1] Jupyter 主页:https://jupyter.org
【2】土星云:https://www . Saturn Cloud . io
[3]Github 上的笔记本:
https://github . com/house cricket/notebooks/blob/master/coronavirus . ipyn
[4]测试机器学习算法准确性的度量标准https://medium . com/datadriveninvestor/Metrics-to-Test-the-Accuracy of-Machine-Learning-Algorithms-67 ADF 367 f 60
Jupyter 笔记本基本生产力黑客
来源。图片免费分享。
更高效地创建和编码
Jupyter 笔记本是一个动态的流行工具,帮助用户创建可读的分析,同时以一种有组织的方式组合代码、图像、注释、公式和图表。Jupyter 笔记本的前身是 IPython 笔记本,它是为 Ju lia、Python 和 R thon 设计的,已经席卷了编码界。在本文中,您将了解到一些使用 Jupyter 时最有用的生产力技巧。
多单元输出
Jupyter notebooks 用户不需要调用print()
,只需调用单元格末尾的一个函数就可以得到结果。不幸的是,默认情况下,Jupyter 笔记本不能在同一个单元中输出两个输出。为了输出多个单元,需要从IPython
重新配置外壳。
多光标
使用 Ctrl+单击创建多光标。无论在哪里
或者,例如,考虑更改列的名称。
列出所有变量
因为 Jupyter 笔记本是基于单元格的,所以很容易忘记变量和它们保存的值。然而,您可以通过调用%whos
来跟踪所有变量——它们的名称、数据类型以及它们存储的数据。它存储你加载的所有东西——模块、数据帧、数组、函数,所有的东西。这在数据分析中非常方便,因为许多错误通常是由于忘记变量名和值造成的。
乳液
您可以在减价单元格中键入 LaTeX,方法是将 LaTeX 括在美元($
)符号中。这在交流公式和变量之间的关系时特别有用。
您可以在此了解如何在 LaTeX 中构建更多数学结构:
任何数据科学简历的必备技能
towardsdatascience.com](/latex-for-data-scientists-in-under-6-minutes-3815d973c05c)
轻松链接到功能文档
如果你对任何函数的作用有疑问,只需输入?name_of_function
就可以启动该函数的文档和用法。
高分辨率绘图
在matplotlib
和seaborn
中创建的标准图可以以更高的分辨率变得更加清晰。为了演示,让我们首先创建一个具有正常随机性的标准正弦波图。
为了创造更清晰的思路,加上%config InlineBackend.figure_format =’retina’
。
线条、数字、注释和其他情节元素将变得更加清晰。
更改单元格语言
要更改单元格的语言,请在单元格顶部键入以下命令之一:
%%bash
%%HTML
%%python2
%%python3
%%ruby
%%perl
您还可以使用 HTML 来嵌入视频、图像或显示其他内容。
如果你喜欢这个,
你可能会喜欢我的其他一些文章。
数据帧是 Python 中操作和存储数据的最标准的方法——但是您知道您可以存储一个…
medium.com](https://medium.com/analytics-vidhya/styling-pandas-dataframes-more-than-just-numbers-4bbb790fb919) [## 真正的人工智能:理解外推 vs 概括
机器学习模型不需要智能,它们的大多数应用都需要执行任务,如…
medium.com](https://medium.com/swlh/real-artificial-intelligence-understanding-extrapolation-vs-generalization-b8e8dcf5fd4b)
使用 Docker 映像的 AWS EC2 实例中的 Jupyter 笔记本
数据科学和机器学习专业人员的最佳可能世界
在 Unsplash 上由 Zeshalyn Capindo 拍摄的照片
大多数数据科学和机器学习专业人士都喜欢 Jupyter 笔记本。除了少数异常情况,大多数数据科学和机器学习工作都发生在云中。所以别无选择,只能在云上使用 Jupyter。
在我的上一篇文章中,我解释了如何在 AWS Linux 实例上下载 Jupyter 笔记本,并使用 Xming 和 X11 转发在客户机上访问它。下面是那篇文章的链接
无处不在的云和 Jupyter 可用性的完美结合
towardsdatascience.com](/jupyter-notebook-on-aws-ec2-instance-f869f5aa4848)
在本文中,我将解释如何通过 Docker 映像直接访问 AWS EC2 实例中的 Jupyter 笔记本。不需要在 AWS EC2 实例中安装 Anaconda 或 Jupyter。
我假设你已经有了一个 AWS EC2 实例,并且知道如何通过 Putty 访问它
必备工具
确保您拥有最新版本的默认操作系统包。尤其是检查是否安装和配置了防火墙相关的软件包。我在 AWS EC2 上使用 Redhat Linux 实例。
首先要确认的是 iptables——安装了服务。如果没有,通过 yum 安装
sudo yum install iptables-services
作者图片
码头发动机安装
现在您已经准备好安装 Docker 引擎了。我按照下面链接的说明在我的 Red Hat Linux 实例上安装了 Docker 引擎。如果您的实例使用不同的操作系统,请查看下面链接中针对该操作系统的步骤。
要在 CentOS 上开始使用 Docker 引擎,请确保您满足先决条件,然后安装 Docker。要安装…
docs.docker.com](https://docs.docker.com/engine/install/centos/)
a.先做第一件事;运行以下命令安装所有 yum 实用程序
sudo yum install -y yum-utils
作者图片
b.获取最新的 docker 存储库
sudo yum-config-manager --add-repo [https://download.docker.com/linux/centos/docker-ce.repo](https://download.docker.com/linux/centos/docker-ce.repo)
c.现在安装最新版本的 docker 引擎和容器
sudo yum install docker-ce docker-ce-cli containerd.io
作者图片
d.启动 docker 服务。
sudo systemctl start docker.service
如果您没有收到任何错误消息,您的 docker 服务已经成功启动。
作者图片
e.您还可以检查 docker 服务的状态。
sudo systemctl status docker.service
作者图片
恭喜你!!您已经成功安装了 docker 引擎。现在,您已经准备好提取 Jupyter 笔记本图像。
Jupyter 笔记本
是时候拉 Jupyter 笔记本镜像了。
a.运行下面的命令来提取 docker 映像并启动 Jupyter notebook。
sudo docker run -p 8888:8888 jupyter/scipy-notebook
等待映像下载和提取完成。
作者图片
您将收到一条消息,表明 Jupyter notebook 正在运行,其中包含一个指向 Jupyter notebook 的链接。
作者图片
b.复制链接并删除 127.0.0.1 和您实例的公共 IP 地址。您可以在 EC2 Instance Connect 选项卡中看到您的实例的公共 IP 地址。
作者图片
c.如果您收到超时消息或站点无法访问消息,您的实例可能不允许在端口 8888 连接。
作者图片
d.转到 AWS 实例的 security 选项卡,单击安全组名称。
作者图片
e.单击 Edi 入站规则按钮。
作者图片
e.如下所示,为端口 8888 添加一个规则,并保存该规则。
作者图片
f.现在刷新你的浏览器。朱庇特笔记本会出现。
作者图片
恭喜你!!您的 Jupyter 笔记本正在等待您的下一次数据科学或机器学习冒险!
结论
云和 Docker 图像正在成为数据科学和机器学习专业人士生活中不可避免的一部分。Docker 图像就像已经为您完成的工作。尽可能地使用它来减少你在项目中的周转时间。
AWS EC2 实例上的 Jupyter 笔记本
无处不在的云和 Jupyter 可用性的完美结合
罗伯特·科林斯在 Unsplash 上拍摄的照片
Jupyter 是数据科学和机器学习专业人员使用最多的开发工具。考虑到大多数数据科学和机器学习项目都涉及到在云上处理数据,所以在云上使用 Jupyter 笔记本是有意义的。Jupyter 在无处不在的云实例上的灵活性是一个双赢的组合。
在本文中,我将向您介绍在 AWS EC2 实例上从 Linux 实例安装和运行 Jupyter 笔记本的步骤。
必备工具
我假设您已经有了一个 AWS EC2 实例,并且知道如何通过 Putty 访问它。
确保您已经在 Putty 中配置了 X11 转发。
作者图片
为了在 AWS 实例上启动 Jupyter notebook 并在您的计算机上访问它,您还需要 Xming 工具。Xming 可以从下面的链接下载
[## Xming X Server for Windows
免费下载 Xming X Server for Windows。系统服务器。Xming 是领先的 X 窗口系统…
sourceforge.net](http://sourceforge.net/project/downloading.php?group_id=156984&filename=Xming-6-9-0-31-setup.exe)
下载并安装 Xming 后,你应该会在电脑上看到两个图标 Xming 和 XLaunch 。点击 Xming,它将启动 Xming 服务器。
点击 XLaunch,进入下面的屏幕。
这是您将看到的第一个屏幕。不需要任何操作,请单击“下一步”。
作者图片
此屏幕上不需要任何更改。点击下一步按钮。
作者图片
此屏幕上不需要任何更改。点击下一步按钮。
作者图片
此屏幕上不需要任何更改。单击完成按钮。
作者图片
圣诞节可以开始了。
Anaconda: 与其在 AWS 实例中分别安装 Python 和 Jupyter,我建议安装 Anaconda。我在 AWS EC2 上使用 Redhat Linux 机器。默认情况下,它不附带 Anaconda 存储库。所以,第一步是通过 wget 命令获取 Anaconda。
a.首先,检查您的实例中是否安装了 wget 。如果没有,通过如下所示的 yum install 运行安装。
sudo yum install wget
作者图片
b.检查是否安装了 bzip2 。如果没有,通过 yum 安装
sudo yum install bzip2
作者图片
c.检查是否安装了 firefox 。如果没有,通过 yum 安装
sudo yum install firefox
d.检查是否安装了 xorg-x11 驱动程序。如果没有,通过 yum 安装
sudo yum install xorg-x11*
e.打开/etc/ssh/ssh_config 文件,并确保 ForwardX11 选项已取消注释并设置为 yes。
f.通过 wget 下载 Anaconda3
sudo wget [http://repo.continuum.io/archive/Anaconda3-4.3.0-Linux-x86_64.sh](http://repo.continuum.io/archive/Anaconda3-4.3.0-Linux-x86_64.sh)
作者图片
这将在目录中创建文件 anaconda 3–4 . 3 . 0-Linux-x86 _ 64 . sh。
g.运行下面的命令来安装 Anaconda 3。
bash Anaconda3-4.3.0-Linux-x86_64.sh
作者图片
点击进入并浏览条款和条件。一旦你得到下面的信息,写是。
作者图片
提及您想要安装 anaconda3 的位置
作者图片
等待 Anaconda3 安装完成。
作者图片
h.添加 Anacond3 二进制文件并在 bashrc 文件中显示变量。我用的是 vi 编辑器,你可以用 nano 或者别的。
sudo vi ~/.bashrc
在此文件中添加以下内容
export PATH=/u01/anaconda3/bin:$PATH
export DISPLAY=localhost:10.0
I .关闭实例并通过 Putty 重新登录。
j.确保 Xming 和 XLaunch 已打开。任务视图中应显示 Xming 图标。
k.让我们确认它已成功安装。检查 Anaconda、Python 和 Jupyter 的版本。
作者图片
恭喜你!您已经完成了所需的设置,并准备启动 Jupyter 笔记本电脑。
推出 Jupyter 笔记本
运行以下命令启动 jupyter 笔记本
jupyter notebook
作者图片
Jupyter 笔记本将在 Mozilla 浏览器的 X11 窗口中打开。
作者图片
恭喜你!现在您知道如何在 AWS EC2 实例上启动 Jupyter 笔记本了!
我和我的学生已经多次经历过这些步骤,并且已经能够在 AWS 实例上成功运行 Jupyter 笔记本。然而,如果您在任何步骤遇到任何问题,请随时写信给我,我会及时回复。
期待您的反馈。
笔记本——投资组合的杀手
为什么不应该将笔记本电脑作为数据科学投资组合的主要特征。
(Jupyter png src =http://pluspng.com/jupiter-planet-png-2876.html
T2:笔记本:所有现代科学计算机适应其学科的地方;一个避难所,一个和平的地方。我们都知道笔记本是一种神奇的工具,它不仅使科学计算变得更加容易,而且更加高效。对于机器学习应用来说尤其如此。研究和开发可以用夹在简单的短代码中的 markdown 单元来彻底解释——有什么不喜欢的呢?
笔记本很棒,是任何有抱负的数据科学家的投资组合中非常重要的一部分。很难否认,在现代数据科学和机器学习中,笔记本电脑并不是一个非常重要的必需品。然而,有一种方法可以让你看起来不太可能仅仅因为拥有一个主要由笔记本组成的文件夹而获得一份工作。
了解工作
将您的工作限制在笔记本上的部分问题是,大多数数据科学职位通常不会坐在笔记本上,不断地拟合和序列化模型。当然,这将总是非常具体地针对所讨论的职位,但在某种程度上——数据科学的现实可能会相当令人失望,不管你的机器学习武器库有多大。为了首先正确地推断数据,很有可能您将构建大量的基础设施。对于拥有数千员工的公司的初级数据科学家或实习生来说,情况尤其如此。
明确地说,低级别的创业公司在完全不同的战线上陷入了同样的陷阱。即使是唯一的数据科学家也会让你陷入这种境地,因为你需要数据来为一家小型创业公司做任何事情。这份工作可能比大公司的数据科学家职位更难。然而,如果你像我一样,喜欢展示你的创造力,并涉足不同的计算学科,这种环境可能会让我兴奋。
问题是:
如果大部分工作是流水线操作和建立数据基础设施,那么笔记本有什么价值呢?
正如我之前所说的,虽然笔记本肯定是创建可重复研究的好方法,但如果招聘经理查看 Github 的个人资料,而它只返回 Jupyter-Notebooks 的存储库,很可能你不会得到这份工作。这是因为你展示的技能只是工作的一部分,而不是全部。我可以假设您可以在笔记本上编写足够的代码,但是
- 可以部署一个模型吗?
- 你能进行 SQL 查询吗?
- 您能做些什么来自动化和控制我们数据系统的后端?
笔记本电脑能够正确提供的唯一信息是您执行操作(如拟合模型)的能力。在投资组合的笔记本部分,我关注的另一个关键是组织。你的代码的可复制性如何,你让你的同事观察你执行的代码有多容易?这些都是关于你的非常重要的信息,可以从你的笔记本上收集。虽然笔记本是你整体投资组合的一小部分,但它们仍然很重要。幸运的是,我写了一篇关于这些主题的文章,你可以在这里更新你的笔记本:
你的假设还是假设!
towardsdatascience.com](/the-data-scientists-guide-to-reproducible-research-ea1a512be3e5)
一个隐喻
我们可以对笔记本电脑做一个很好的比较,那就是终端会话。让我们假设我们是开发运营工程师,我们的工作是部署全栈 web 服务。我的开发-运营组合的最大部分当然不会是我的终端会话的输出,尽管它们可能很重要。虽然运行后端的配置文件和代码肯定是开发-运营工程师组合的一大部分,但最重要的事情是返回产品。产品是公司所追求的。如果你能够运输一个产品,那么你很可能拥有重复这项工作所需的所有技能。
类似地,我们可以把它比作一个全栈的 web 开发人员。没有一个招聘经理会花时间去检查你的存储库,下载你所有的文件来研究你的代码。当然,可能会出现一些文件的峰值,以查看您在笔记本或应用程序中执行了多少冗余操作,但重要的是要记住,最重要的是提供一些实用且实际可用的东西:
一个产品。
黑仔投资组合
我回顾了如此多的作品集,甚至有同事的作品集都是以 Jupyter-Notebook 为中心的。虽然这些肯定是数据科学家投资组合的一大部分,但最重要的是交付一个真实的结果。问题是许多数据科学家不愿意使用 BASH,这是一个很大的问题,因为它经常成为这项工作的主要内容。
制作一个模型是很棒的,但是如果你不知道如何部署它或者获取它的数据,那么这个模型本质上是没有用的。如果它不能被查询并产生适当的回报,那么这个模型将永远不会有任何真正的用途。尽管幕后发生的事情可能比观众所相信的要高级一些,但是如果产品做得很好,那么你就有可能得到这份工作。
结论
虽然 Jupyter 笔记本电脑是现代科学计算的主要产品,也是一个适当的数据科学家的投资组合所必需的,但缺乏与工作的许多主要操作相关的内容通常会被排除在投资组合的这些部分之外。Jupyter 是一个很好的工具,可以让代码变得清晰、可复制,但是在某些情况下,它确实有点不太好用。
我想我可能会触及这个主题,因为有许多数据科学家对笔记本有点着迷。虽然笔记本电脑在任何科学计算工作中都是非常重要的一部分,但笔记本电脑不太可能成为 Github 帐户的主要产品,我认为科学家不仅仅是 Jupyter,这一点非常重要。笔记本修改起来也相对简单,所以润色一下可能是个好主意!
Jupyter 笔记本到 PDF 的几行
轻松将您的 Jupyter 笔记本转换为 PDF 文件
作者创建的图像
在我们的 Jupyter 笔记本上工作时,有时我们希望以可读的形式共享我们处理过的数据集,包括创建的图和我们已经创建的降价解释。有一种简单的方法可以将我们的 Jupyer 笔记本转换成 PDF 文件。只需一个简单的设置,您就可以访问 PDF 格式的笔记本。
例如,我会使用我在文章这里中提供的笔记本来转换成 PDF 表单。下面是我的 Jupyter 笔记本。
下面是 PDF 格式的笔记本。
如你所见,它显示了所有的代码和你的解释。有多花哨?
现在让我告诉你怎么做。
Jupyter 到 PDF
我们需要做的第一件事是安装必要的软件包。在这里,我们将使用名为 notebook-as-pdf 的软件包来帮助我们将 Jupyter 笔记本转换为 pdf 文件。您需要在命令提示符下运行以下代码。
pip install -U notebook-as-pdf
我们还需要一个额外的铬设置。它用于执行 HTML 到 PDF 的转换。只需在代码提示符下运行以下代码。
pyppeteer-install
就这样,我们已经做好了准备。现在,让我们打开您打算转换为 PDF 的笔记本。在您的笔记本中,单击文件菜单栏,然后选择下载为,然后选择 PDF via HTML 来转换笔记本。
就这样,你已经有了一个 PDF 格式的笔记本。如果您喜欢使用命令提示符来转换笔记本,您可以使用下面的代码来完成。
jupyter-nbconvert --to PDFviaHTML example.ipynb
结果将被称为 example.ipynb,因为我们的 Jupyter 笔记本被称为 example.ipynb
结论
这里我向你展示了一个将你的 Jupyter 笔记本转换成 PDF 文件的技巧。这可能很简单,但从长远来看是有用的。
如果你想了解更多关于这个包的信息,你可以访问网站这里。
在我的 社交媒体 上访问我。
如果您没有订阅为中等会员,请考虑通过我的推荐订阅。
Jupyter 笔记本调整使 python 项目对非技术人员可读
让数据科学项目更具可读性和可展示性
“这看起来像希腊语!”,我的妻子说,每次她看着我的 Jupyter 笔记本或很少命令行,当我试图 git bash,pool 和其他一切数据科学家和用户这样的工具,如 Jupyter 笔记本,命令行,python,然后一切。嗯,实际上有相当多的希腊人,尤其是在这个严重依赖大量统计和数学的行业。我自己一直很难接受大量的新术语提醒,Josh 解释道,他管理着我的一个了解希腊语的 youtube 账户,Josh 的 Statsquest。
来自 giphy.com 的史蒂文·A 对 T2 的数据和数学着迷
虽然她确实了解数据科学的一些基础知识,包括收集、处理、设计、建模和可视化发现。事实是,我有时希望能够以最简单易懂的方式解释我们所做的一些项目的过程和最终产品。虽然侧边演示文稿是开始这种简单的数据科学项目总结的绝佳场所,但 Jupyter 笔记本仍然可以让那些愿意进一步探索这一过程的人更容易阅读。
下面我列出了一些你可以在笔记本上做的基本事情,让它看起来更像样,最重要的是更容易理解。
- 总结你的优秀工作- 清晰的问题定义,包括流程和方法的总结以及发现和后续步骤。
- 目录 -包括一个清晰的目录,包括标题和副标题。让您的技术笔记本易于浏览。检查目录扩展的n 扩展。下面的例子展示了我和我的同事 Muoyo Okome 最近完成的一个项目的目录。该项目的目标是尝试发现数据是否可以帮助芝加哥市的拼车司机赚更多的钱。
3.使代码折叠和标题可折叠- 除了目录之外,您希望允许查看您代码的人能够只选择他们感兴趣的主题,由于某种原因,您的技术笔记本仍然包含复杂的代码或太多的代码单元,您可以使用扩展折叠部分代码。您也可以使用隐藏所有输入。再次nbextensions是这方面的一个关键。
4.简洁的可视化效果——包括易于理解且外观简洁的可视化效果,可以很容易地给出正在发生的事情的清晰画面,并突出一些关键的发现。
总之,让你的非技术性笔记本干净、整洁、易于浏览是很重要的。这将帮助大多数人容易理解我们作为数据科学家所做的一些工作。我真的找到了nbextensions工具,它拥有上面大部分突出显示的扩展以及更多。正确安装后,您可以通过 jupyter 笔记本电脑的以下界面启用这些功能:
n 扩展接口
要安装 NBextentions,请使用下面的代码
!pip 安装 jupyter _ contrib _ nb extensions
!pip 安装https://github . com/ipython-contrib/jupyter _ contrib _ nb extensions/tarball/master
!jupyter contrib nbextension 安装—用户
希望这将有助于您向技术人员和非技术人员发布和分享您的辛勤工作成果。
IDE 中的 Jupyter 笔记本
Visual Studio 代码与 PyCharm
我每天都用 Jupyter 笔记本工作。每天我都在使用和编辑 Python 库。两者都是我作品中的关键元素。笔记本是记录和解释你的发现的好方法。从长远来看,库是一项安全的投资,因为它们使您的代码可重用。现在,你有没有想过……除了用 Jupyter 做笔记本,用 ide 做图书馆,我们还能做别的吗?
如果你知道我是 Jupytext 的作者,你就已经知道我认为能够在你最喜欢的 IDE 中编辑你的 Jupyter 笔记本有很多附加价值。
如果你没有听说过 Jupytext,那么让我提一下 Jupytext 是 Jupyter 的一个插件,它可以让你将传统的笔记本与一个或多个文本文件配对。配对的文本文件,例如 Python 脚本,可以编辑(使用任何文本编辑器或 IDE),然后当您重新加载笔记本时,您可以在 Jupyter 中获得更改。
Jupytext 提供了一种从 IDE 访问笔记本的方法。但这不是唯一的方法。Spyder 在为脚本提供双百分比单元格标记的交互模式方面有着悠久的历史。Hydrogen 是 Atom 编辑器的一个插件,可以让你交互式地运行这些脚本。而我最常用的两个编辑器,PyCharm 和 Visual Studio Code,现在让你直接在 IDE 里打开你的.ipynb
笔记本!
我很好奇,想看看这有多有效。那些 ide 的笔记本使用体验比 Jupyter 好吗?我会掉包吗?在本文中,我描述了我目前使用笔记本的工作流程,然后将它与 PyCharm 和 Visual Studio 代码现在可能实现的工作流程进行了比较。
我的 Jupytext 工作流程
我将以典型的一天工作为例。今天,我要回答一个关于我们的数据和算法的新问题。原来我以前已经回答过类似的问题了。所以,首先,我搜索我现有的笔记本中哪一个最接近今天问题的答案。
由于我使用 Jupytext,我所有的.ipynb
笔记本都有配对的.py
表示。所以我打开 PyCharm,使用在路径中查找搜索窗口,在我收集的.py
笔记本中找出能够让我开始今天问题的:
让我补充一下
- 当您将搜索限制在
*.py
文件,并将.ipynb_checkpoints
添加到 PyCharm 设置/编辑器/文件类型中的忽略文件和文件夹时,搜索体验会大大改善 - 并且,如果您想将当前目录中的所有笔记本与
percent
脚本配对,您可以简单地运行jupytext --set-formats ipynb,py:percent *.ipynb
。
现在我打开现有的笔记本,它将作为模板。我将它的内容摘录——我想开始的部分——复制到一个新的.py
文件中。我负责包含 YAML 头,因为它是定义 Jupytext 配对信息和笔记本内核的地方。然后我把新的.py
笔记本调到今天的问题。在一个减价单元格中(用# %% [markdown]
分隔),我写下一些我今天想做的事情。然后我调整代码以更好地解决当前的问题。在 IDE 中这样做比在笔记本中更舒服。它也更加安全和快速,因为我受益于 IDE 语法检查和突出显示。
当我的草稿足够好的时候,我在 Jupyter 中打开.py
文件作为笔记本(在 Jupyter 笔记本中单击;在 JupyterLab 中,右击该文件,并选择用/Notebook 编辑。在这个阶段,它没有输出,所以我运行它。当然,新笔记本在第一次运行时可能不会很好,所以我继续在 Jupyter 中编辑笔记本,直到它正常运行。
当我在 Jupyter 中保存笔记本时,.py
文件会更新以匹配最新的内容。此外,还创建了一个包含输出的.ipynb
文件,因为 Jupytext 头在这一行有ipynb
:formats:ipynb,py:percent
。如果我忘记复制标题,我可以使用 Jupyter 中的 Jupytext 菜单,选择:将笔记本与。ipynb 文档激活与.ipynb
笔记本的配对。
现在我完成了。通常,我会共享.ipynb
文件(例如,使用 Jupyter nbviewer),并对.py
文件进行版本控制。
我最喜欢这个工作流程的什么?
- 在笔记本中搜索非常容易——它们只是文本文件。
- 起草一个新的笔记本太舒服了。我以前从未能够如此轻松地从不同的笔记本中复制粘贴多个单元格。
- 当我在 PyCharm 中编辑
.py
笔记本时,我受益于 IDE 的高级功能:语法检查、补全、重新格式化、文档提示… - 我也可以在 Jupyter 中自由编辑笔记本。
- Jupytext 解决了版本控制的问题。通常,我不想将笔记本输出保存在
git
中,所以我只对.py
文件进行版本化,它有一个干净的差异历史。
注意,这里我使用 PyCharm Professional,但这只是因为它是我最喜欢的 IDE。您可以使用任何其他编辑器,工作流程将是相同的。
我不太喜欢的是:
- 每个笔记本都有一个双重表示(
.ipynb
/.py
)。这可能会让不止一个用户感到惊讶。 - 在两个编辑器(这里是 PyCharm 和 Jupyter)中同时处理同一个文档需要格外小心。在切换到另一个编辑器之前,我必须注意在当前编辑器中保存文档(并且可能会禁用自动保存)。我需要在我切换到的编辑器中刷新笔记本。
- PyCharm 可以执行和调试我的脚本,但是,输出在终端中显示为文本,所以实际上,我更喜欢在 Jupyter 中执行笔记本。
PyCharm 的 Jupyter 笔记本
PyCharm 是我最喜欢的代码编辑器。请不要问我为什么,因为我不确定有一个单一的原因…但是我可以肯定的是,在那里编辑脚本和库是非常棒的!此外,我喜欢 PyCharm 的测试和调试工具套件(看看附录,了解如何配置 PyCharm)。并且版本控制被很好地集成…
PyCharm 有两个版本:社区版和专业版。你已经可以用社区版做很多事情了。然而,Jupyter 笔记本只有专业版。
我准备了一个测试笔记本
- 减价牢房
- 一个代码单元,输出一个熊猫数据帧
- Matplotlib 图
- Jupyter 小部件
- 和一个阴谋。
现在我在 PyCharm Professional 2019.3.1 中打开笔记本,我得到了这个:
这是超级令人印象深刻的,不是吗?
我最喜欢什么?
- 笔记本里的所有输出都工作!甚至是小部件,或者 Plotly 图。干得好,皮查姆!
- 我可以把笔记本编辑成 Python 脚本。就像用 Jupytext 一样,复制粘贴多个单元格是超级容易的!仅用
#%%
创建一个新的代码单元。使用#%% md
创建降价单元格。 - 执行单元格的快捷键与 Jupyter 中的相同(Ctrl+Enter,Shift+Enter 执行并将光标移动到下一个单元格)。并且预览窗口与输入窗口很好地同步。当您单击一个输入单元格时,视图窗格会自动滚动到相应的输出,反之亦然。
- 当您键入或检查代码时,您可以利用 PyCharm(例如,ctrl+click 将您带到函数或对象的定义)。代码补全、文档提示等都可以在笔记本上找到。
- 您可以在笔记本或底层库上设置断点。
- 记事本变量出现在变量资源管理器中:
如果有我不喜欢的东西,也许这就是笔记本的展示方式。它与 Jupyter 明显不同,因为输出显示在预览窗格中。我不习惯那样。这也减少了我的地块或表格的可用空间。我想我更喜欢输出在输入之下,比如 Code、Hydrogen 甚至 RStudio。此外,在工作中,我可能会写很长的笔记本,对于这种笔记本,目录扩展非常有用,因为它让我可以轻松地在笔记本的不同部分之间导航——我可能会错过 PyCharm 的笔记本编辑器中的这一功能。
如果你是 PyCharm 开发团队的一员,让我告诉你,作为一个笔记本用户,我很高兴看到你在这方面的工作!你做了令人印象深刻的工作!现在我有一些额外的观察给你:
- 你会考虑在代码单元后显示输入吗?你能做到这一点并让我们轻松地选择/复制/粘贴多个单元格吗?
- 减价单元格标记不标准。按照 Spyder 的约定,
# %% md
是一个标题为md
的单元格。你可以用# %% [md]
或# %% [markdown]
来代替吗,比如 Code,Hydrogen 或 Jupytext? - 搜索窗口(在路径中查找)不能很好地用于笔记本——它显示他们的 JSON 内容的摘录。展示他们的
.py
形象本可以更加用户友好。 - 在笔记本的上下文中,重新格式化代码(Ctrl+Alt+L)是无效的。
- 执行笔记本增加了一些单元格元数据(
{"pycharm": {"is_executing": false}}
)。 - 最后,也许
.py
格式并不适合所有的笔记本。我的一些教程包含大量文本,对于这些,我更喜欢使用 Jupytext 的 Markdown 格式。PyCharm 可以很好地处理 Markdown 文件,但是它不允许我在那里运行代码…在 IDE 中把这些文档渲染成笔记本,你会怎么想?
干得好,皮查姆!现在让我们看看 VS 代码提供了什么。
Visual Studio 代码中的 Jupyter 笔记本
Visual Studio Code 是由微软开发和维护的免费开源编辑器。它不是专门针对 Python 的,并且有许多语言的插件。在这里,我们将测试 1.41.1 版本的代码,由微软于 2020 年 1 月 13 日发布的最新 Python 扩展。
每当我想编辑 Markdown 文件,或者用 Python 之外的任何语言编写的脚本,比如 Javascript 或 Typescript,我都会使用代码。但是直到最近,我都不怎么使用 Python 代码。回想起来,我认为原因是我不知道如何设置代码来与我的 conda 环境一起工作。这个问题现在已经解决了,并记录在附录中,我要感谢来自 Python Visual Studio 代码团队的露丝安娜帮助我解决了这个问题。
现在让我用代码打开我们刚刚在 PyCharm 中打开的同一笔记本。结果是这样的:
我喜欢什么?
- 有用!所有的输出都显示得很好(小部件还不被支持,但是我被告知它们会在下一个版本中被支持)。
- 在这里,执行一个单元格的快捷键与 Jupyter 中的相同(Ctrl+Enter,Shift+Enter 执行并将光标移动到下一个单元格,Esc-A 创建上面的单元格,等等)。
- 我喜欢把输出放在 Jupyter 代码下面。
- 由于自动完成,输入代码很舒服。
- 我们可以在变量资源管理器中检查笔记本变量。
但也许我想要更多。我想一次选择/复制/粘贴多个单元格。我想导航到一个函数的定义,就像我们在脚本中用 ctrl-click 一样。为什么我们没有和.py
脚本一样的上下文菜单?我想在我的笔记本上设置断点…但是我已经说过了,我希望有一个目录来帮助我在长笔记本中找到方向。
我的故事结束了吗……没有!还有最后一件事我想试试。在 Code 的文档中:在 Visual Studio Code 中使用 Jupyter 笔记本据说一旦将笔记本转换成 Python 脚本就可以设置断点!让我们试试那个。
Visual Studio 代码中的交互式脚本
现在我们点击将笔记本转换成 Python 脚本。我们得到一个看起来像皮查姆的笔记本的脚本:
我喜欢这里的什么?
- 我可以利用 Code 的高级功能来编辑文件。Ctrl+click 起作用,让我导航到定义。我可以轻松地一次选择/复制/粘贴多个单元格。
- 表格、图和交互式图在交互式预览中工作。
- 我可以在终端中键入和执行 Python 代码,而不必创建新的单元。这太棒了!有多少次,我创建了一个新的单元格,只是因为我需要检查一个变量,然后我忘了从笔记本上删除那个单元格…
- 该脚本使用与 Jupytext 相同的单元格标记。这意味着我可以依靠 Jupytext 在笔记本和脚本之间进行转换和同步。在 Jupyter 中,我会使用 percent 脚本访问 Jupytext/Pair,并保存/重新加载笔记本以更新两个文件。在终端中,我会使用
jupytext notebook.ipynb --set-formats ipynb,py:percent
然后使用jupytext notebook.ipynb --sync
来保持两个文件同步。
我更喜欢的是断点。在脚本上放一个断点,就可以调试单元格看变量了!
我很喜欢那种互动模式!此时,在编辑器中编辑笔记本是我最喜欢的方式之一。
现在我有几个问题要问 Visual Studio 代码 Python 扩展的开发人员:
- 我知道我可以将 VS 代码连接到本地或远程 Jupyter 内核。现在,我可以在 Jupyter 和 Code 之间共享同一个会话吗,比如使用
%connect_info
魔法命令?这将使我能够在 Jupyter 中执行我的笔记本的大部分内容,并且只调试代码中的特定单元,而不必重新运行笔记本的全部代码。 - Jupytext 允许我将笔记本编辑成脚本或减价文件。我发现 Markdown 格式更适合包含文本多于代码的笔记本,比如教程或文档。你想为笔记本提供降价模式,还是相反,让降价文件以笔记本的形式在代码中交互执行?
结论
Visual Studio 代码和 PyCharm 是两个很棒的代码编辑器。它们使得设计、编辑或重构 Python 代码变得如此容易。所以我真的很欣赏能够在这些 ide 中打开笔记本的想法。
笔记本在 IDE 中应该如何表现?我喜欢 PyCharm 的类似脚本的笔记本模式和代码的交互式脚本模式,因为它们允许在笔记本上以与使用脚本完全相同的方式工作(复制/粘贴、在代码中导航、设置断点……)。
我会将笔记本电脑切换到 IDE 吗?我想我会继续在 IDE 和 Jupyter 之间切换,当我想在我的笔记本中搜索,起草新的笔记本,重构现有的笔记本,或者设置断点时,当我想使用目录在笔记本中导航,分析情节,评论我的发现,或者展示笔记本时。
感谢
我要感谢 Python Tools for VS 、 Python Visual Studio Code 和 JetBrains PyCharm 开发人员所做的工作。根据经验,我知道在 IDE 中处理笔记本有很大的潜力,但这并不是一个简单的挑战。所以我喜欢看到更多的人致力于此。
让我也感谢帮助我改进这篇文章的早期读者:弗朗索瓦·沃茨,以及 CFM 、埃里克·奥·莱比戈、弗洛伦特·扎拉和文森特·阮。
附录——如何重现该研究
在这一部分,我分享了我关于如何正确安装 Python 以及配置 PyCharm 和代码的笔记。我的笔记是针对 Windows 10 的,但我希望它们适用于任何平台。
获取示例文件
请从我的 GitHub 仓库中克隆环境和示例文件:
git clone https://github.com/mwouts/notebooks_in_vscode_and_pycharm_jan_2020.git
用 conda 创建 Python 环境
请安装一个迷你巨蟒或巨蟒。如果不知道区别,就拿 Miniconda,比较轻。
然后进入开始菜单,键入 Miniconda 然后点击 Anaconda Powershell 提示符(Miniconda3) 。在终端中,将目录更改为此项目,然后创建示例 Python 环境,例如
cd Documents\Github\notebooks_in_vscode_and_pycharm_jan_2020 conda env create --file environment.yml
现在,我们用以下方式激活环境
conda activate notebooks_in_vscode_and_pycharm_jan_2020
发射 Jupyter
我们刚刚创建的环境包括 Jupyter 和 Jupytext。用…发射 Jupyter
cd Documents\Github\notebooks_in_vscode_and_pycharm_jan_2020
conda env create --file environment.yml
您将能够探索我们的示例脚本和笔记本,并了解 Jupytext 是如何工作的。
配置 PyCharm
假设您已经安装了 PyCharm Community 或 PyCharm Professional,并且已经在 PyCharm 中打开了我们的notebooks_in_vscode_and_pycharm_jan_2020
项目。
下一步是告诉 PyCharm 我们想要使用哪种 Python。为此,在使用conda activate notebooks_in_vscode_and_pycharm_jan_2020
激活环境后,我们在 Windows 上执行where.exe python
,或者在 Linux 或 Mac OSX 上执行which python
:
现在我们转到 File\Settings,搜索项目解释器,点击 gear/Add,选择现有环境,粘贴 Python 解释器的完整路径——在我的例子中是:C:\Users\Marc\Miniconda3\envs\notebooks_in_vscode_and_pycharm_jan_2020\python.exe
。
配置 Visual Studio 代码
Visual Studio 代码的文档详细解释了如何用虚拟 Python 环境配置 Visual Studio 代码。
如果您想使用 conda,您必须从 Conda 中的启动代码。所以我们进入 Anaconda PowerShell 提示符,通过键入code
启动 VS 代码:
现在你可以关闭外壳了。作为从 conda 环境继承的代码,您将能够从该环境中使用 Python 和 Jupyter。
让我强调一下,如果您不在 conda 中启动 Visual Studio 代码*,您将会得到各种类型的错误,包括:*
conda is not recognized as internal or external command.
- 我知道,你把康达加到了你的道路上…但这还不够)
- 或者甚至,
"Import Error: Unable to import required dependencies: numpy:"
。
JupyterLab 2.0
让我们来一窥 Jupyter 笔记本编辑的未来。像编码辅助和更多☀️这样的特性让未来看起来很光明
前几天,我写了一个故事你还在用 JupyterLab 吗?我得到了惊人的回应。读者向我推荐了各种为数据科学开发的新 ide,但其中有一个非常突出。
Michal Krassowski 给我留了一张纸条,上面写着他和其他贡献者正在做的一个项目。JupyterLab-LSP 是 JupyterLab 的一个语言服务器协议集成。简而言之,它为 JupyterLab 增加了新的超能力,比如代码导航、悬停建议、linters、自动完成和重命名。我真的很兴奋,因为它解决了大多数问题,PyCharm 优于 JupyterLab。
米哈尔·克拉索夫斯基的笔记
让我们试驾一下吧
这里有几个你可能会感兴趣的链接:
- [Labeling and Data Engineering for Conversational AI and Analytics](https://www.humanfirst.ai/)- [Data Science for Business Leaders](https://imp.i115008.net/c/2402645/880006/11298) [Course]- [Intro to Machine Learning with PyTorch](https://imp.i115008.net/c/2402645/788201/11298) [Course]- [Become a Growth Product Manager](https://imp.i115008.net/c/2402645/803127/11298) [Course]- [Deep Learning (Adaptive Computation and ML series)](https://amzn.to/3ncTG7D) [Ebook]- [Free skill tests for Data Scientists & Machine Learning Engineers](https://aigents.co/skills)
上面的一些链接是附属链接,如果你通过它们购买,我会赚取佣金。请记住,我链接课程是因为它们的质量,而不是因为我从你的购买中获得的佣金。
编码林挺和吸尘建议
安装 JupyterLab-LSP 后,您会在状态栏中看到“完全初始化”图标。这意味着 JupyterLab-LSP 正在工作。
代码林挺工作很好。在下面的示例中,它显示“由未使用的导入”警告。
用 JupyterLab-LSP 在 JupyterLab 中编码林挺
代码完成
这是我最期待的功能之一。我们来测试一下。
从下面的视频中可以看出,代码完成(CC)对 pandas 或 numpy 不起作用。我还用 pandas DataFrame 中的列尝试了 CC,但没有任何不同。CC 在系统库和我定义的类上工作得很好。
使用 JupyterLab-LSP 在 JupyterLab 中完成代码
功能签名建议
一些熊猫函数有很多参数,其中一些我很少使用。每次我使用这样的功能时,我都必须去谷歌搜索文档来更新我的记忆。
JupyterLab-LSP 增加了函数签名建议(FSS),效果很好。你得到一个漂亮的弹出窗口——不太打扰,刚刚好。
JupyterLab 中的函数签名建议
FSS 可以通过突出你正在编辑的当前论点来进一步改进,就像 NeoVim 中的deo complete-Jedi插件。
在 NeoVim 与 deo complete-Jedi 的功能签名建议
函数签名建议非常有效,但仍有改进的空间
诊断面板
JupyterLab-LSP 还有一个漂亮的诊断面板,列出了所有的警告和错误。这非常有用,因为红色下划线可能会被忽略。
带有 JupyterLab-LSP 的 JupyterLab 中的诊断面板
重命名变量
我对这个有点失望,因为我以为它会进行重构,但它是一个关键字替换。我试图重构一个变量名,但它也重命名了一个字符串,如下面的视频所示。
使用 JupyterLab-LSP 重命名 JupyterLab 中的变量
其他特色
JupyterLab-LSP 包含了许多有用的功能,比如“转到定义”——你想看看熊猫数据帧在幕后是如何工作的吗——只需使用“转到定义”。
代码格式化在某些时候也会成为 LSP 扩展的一部分!
W 你想看看熊猫数据框架是如何在幕后工作的吗——只要使用 Go to Definition
你自己试试
确保您安装了最新的 JupyterLab 在撰写本文时是 2.1.0。您还需要在 JupyterLab 中启用扩展管理器。
pip install -U jupyterlab
安装 LSP 服务器扩展:
pip install jupyter-lsp
安装节点(该命令适用于 macOS):
brew install nodejs
安装前端扩展:
jupyter labextension install @krassowski/jupyterlab-lsp
为编程语言安装 LSP 服务器:
pip install 'python-language-server[all]'
启动 jupyterlab,您应该会在状态栏中看到“完全初始化”图标。
判决
比尔·牛津在 Unsplash 上的照片
根据我所做的正面评论,你可能会认为我会每天使用 JuypterLab 2.0 和 LSP。你会惊讶地发现,在我写完这篇文章后,我已经安装了旧版本。这是为什么呢?
虽然新功能运行良好,但我使用的其他扩展还不支持 JupyterLab 2.0。这些是用于 Vi 键绑定的 jupyterlab-vim 和用于代码格式化的jupyterlab _ code _ formatter。这两个扩展目前对我来说比 LSP 支持更重要。也许我们可以两全其美,因为 JupyterLab-LSP 似乎也支持 JupyterLab 1.x,但我还没有试过。
# for JupyterLab 1.x
jupyter labextension install @krassowski/jupyterlab-lsp@0.8.0
简而言之,JupyterLab-LSP 是一个巨大的改进,我可以说我将来肯定会使用它
在你走之前
在 Twitter 上关注我,在那里我定期发布关于数据科学和机器学习的。
保持冷静和堆叠—使用 mlxtend 在 Python 中实现堆叠回归
如果你曾经在一些 Kaggle 比赛中结合多个 ML 模型来提高你在排行榜上的分数,你知道这是怎么回事。事实上,这些 Kaggle 竞赛的许多获胜解决方案使用集合模型,而不仅仅是单一的微调模型。
集成模型背后的直觉非常简单:有效地组合不同的 ML 算法可以降低不幸选择一个差模型的风险。
在这篇文章中,我将讨论堆叠,一种流行的集成方法,以及如何使用 mlxtend 库在 Python 中实现一个简单的 2 层堆叠回归模型。我选择的示例任务是 Airbnb 价格预测。
古玩目录
概观
堆叠,或堆叠泛化,是一种元学习算法,它学习如何以最佳方式组合每个基础算法的预测[1]。
简单来说,这就是如何建立一个两层堆叠模型。第一层,有些人称之为基础层,包括基础模型。在分类的上下文中,您可以将基本模型视为任何可用于进行预测的分类器,如神经网络、SVM、决策树等。类似的逻辑也适用于回归。在我们使用训练集训练这些模型之后,第二层通过从这些模型中获取预测以及对样本外数据的预期输出来构建元模型。你可以想到这种元模型的最简单的情况是平均出基础模型的预测。
避免过度拟合的常见方法是在这些基础模型上执行交叉验证,然后使用折叠外预测和输出来构建元模型。
查看大卫·沃尔菲特的论文,了解更多关于堆叠工作原理的技术细节。
我选择了 Kaggle ( link )的 Airbnb 价格预测任务作为这里的示例,因为它是一个相对简单的数据集,具有较小的样本大小和一组功能。任务是根据卧室数量、租赁类型(整个公寓或私人房间或合租房间)等信息预测 Airbnb 上的公寓租赁挂牌价格。
要查看完整的 Python 代码,请查看我的 Kaggle 内核。
事不宜迟,让我们进入细节!
探测
出于本文的目的,我不会讨论预处理步骤,但请参考 Kaggle 内核了解全部细节。
在高层次上,我检查了每个特性的分布,删除了异常值,为分类“room_type”创建了虚拟变量(因为只有三个类别),并对特性进行了标准化。
训练/测试分割
我将数据集的 70%设置为训练集,剩下的 30%将用作测试集。
X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.3, random_state=1)
基本型号
让我们首先建立一些基础模型。这里我选择了 Xgboost 、套索回归和 KNN 作为三个基础模型。原则上,当模型在不同的范围内,并且它们的预测误差尽可能不相关时,叠加效果最好,这样单个模型的弱点和偏差可以被其他模型的优点抵消[2]。
绩效指标
在评估模型的性能度量方面,我选择使用平均绝对误差(MAE) ,它衡量预测值与测量值的差距。
基本型号的性能
让我们快速检查三个基本模型的性能(所有默认超参数):
Model: XGBRegressor, MAE: 35.80629559761084
Model: Lasso, MAE: 35.0691542225316
Model: KNeighborsRegressor, MAE: 38.35917874396135
MAEs 在 35-38 之间,这意味着预测价格平均与真实价格相差 35-38 美元。
使用 mlxtend 构建堆叠模型
现在,我们可以为元学习者建立基础模型。或者,我们可以使用 mlxtend 库(文档)中的‘StackingCVRegressor’来创建快捷方式:
from mlxtend.regressor import StackingCVRegressorstack = StackingCVRegressor(regressors=(XGBRegressor(),
Lasso(), KNeighborsRegressor()),
meta_regressor=Lasso(), cv=10,
use_features_in_secondary=True,
store_train_meta_features=True,
shuffle=False,
random_state=1)
使用相同的三个基础模型,对于元学习者,我选择使用 Lasso。我们也可以尝试其他回归模型作为元学习者,然后在上面构建另一个元学习者(三层堆叠!)注意,在这种配置中,我还选择使用原始训练数据作为元模型的输入,因为它可以为元模型提供更多的上下文。
现在,让我们将训练数据放入模型中,并在测试集上检查性能:
stack.fit(X_train, y_train)
X_test.columns = ['f0', 'f1', 'f2', 'f3', 'f4', 'f5', 'f6', 'f7', 'f8', 'f9', 'f10', 'f11'] # Xgboost internally renames the features
pred = stack.predict(X_test)
score = mean_absolute_error(y_test, pred)
print('Model: {0}, MAE: {1}'.format(type(stack).__name__, score))
--------------------------------------------------------------------
Model: StackingCVRegressor, MAE: 34.01755981865483
我们看到新的 MAE 大约是 34,与最佳基础模型 Lasso 的结果相比减少了 1。
虽然这种差异看起来微不足道,但像这样的小收获实际上可以在排行榜上产生巨大的差异。
如果你想研究集成神经网络,看看这篇论文。
警告
尽管有堆叠功能,但还是要记住以下几点:
- 有效地使用堆栈有时需要一些尝试和错误,并且不能保证堆栈在所有情况下都会提高性能。
- 堆叠在计算上可能是昂贵的,尤其是当堆叠层数很高时。
- 随着叠加层数的增加,模型的可解释性降低。对于 Kaggle 竞争来说,这不是一个大问题,但是对于商业案例来说,理解特性的重要性及其对结果变量的增量影响可能更重要。
后续步骤
以下是我们接下来可以尝试的几件事:
- 超参数调整—我们可以在选定的模型中调整一些超参数,以进一步优化性能。在这个过程中,“GridSearchCV”可能是一个有用的工具。
- 继续堆叠—尝试构建额外的堆叠层,并绘制性能指标与层数的关系图,以检查边际回报递减是否成立(应该成立!).
摘要
让我们快速回顾一下。
我们使用 mlxtend 库在 Python 中实现了一个简单的两层堆叠回归模型,将其测试 MAE 与三个基本模型的测试 MAE 进行了比较,并观察到了改进。
我希望你喜欢这篇博文,并请分享你的想法:)
查看我的另一篇关于使用 t-SNE 降维的文章:
[## 在 MNIST 上使用 t-分布随机邻居嵌入(t-SNE)进行降维…
t-SNE vs PCA vs PCA & t-SNE
towardsdatascience.com](/dimensionality-reduction-using-t-distributed-stochastic-neighbor-embedding-t-sne-on-the-mnist-9d36a3dd4521)
参考
[1]https://machinelementmastery . com/stacking-ensemble-machine-learning-with-python/
http://support . SAS . com/resources/papers/proceedings 17/SAS 0437-2017 . pdf
数据科学家制作网站指南
一个全面的指南来学习 HTML/CSS
对 HTML 的恐惧是心灵上的——黑仔
除了建模,数据科学家还花大量时间写作。他们写作来交流见解,他们写博客,他们发微博。数据科学领域的主题数量极其庞大。从自然语言处理到面部识别,从预测客户流失到检测罕见的深空事件,关注的范围是无限的。然而,大多数数据科学经验涉及 Python 和数据收集:数据科学家很少处理 HTML、CSS 和 JavaScript,即所谓的 web dev 语言*。*具有讽刺意味的是,这种设计经验的缺乏限制了数据科学家的影响力,否则他们可能会在漂亮的作品集或博客中展示他们的项目。实际上,创建自己的数据科学网站或博客是非常容易的,尽管前期对 CSS 和 HTML 有所畏惧,以至于你可以在几天内学会制作一个漂亮的个人网站所需的一切。
无论是个人还是公司使用,制作自己网站的资源多得令人困惑,还有更多关于如何制作的教程,这是其中之一!
我希望这篇文章能为提供一个干净、最新、最简单的指南,让你对 HTML、CSS 或 JavaScript 一无所知。
web 开发中最令人困惑的部分甚至不是 HTML 或 CSS。有了 Google 和 Stack Overflow,修改网页外观的技巧和工具就相对简单了。相反,困难来自于理解技术如何交织在一起,以及什么样的抽象构成了一个“网站”
这篇文章将介绍网站的三个主要抽象概念:
- HTML、CSS 和 JavaScript ,以及你不应该担心它们的原因。
- 主持。你的页面内容实际上在哪里?
- 域名。“你如何通过传统顾客到达那个页面”。com 的名称?
步骤 1: HTML、CSS 和 JavaScript
这里有一个他们工作的快速概述,只是为了一个基本的理解或复习。
HTML…
是“超文本标记语言”,它只是用于在最基本的层次布局网页的构建模块。所有你看到的像<p>code stuff</p>
一样的标签都是 HTML,甚至右击你正在阅读的这个页面,点击‘检查’就会打开你浏览器的编辑器,向你展示这个页面的直接主干布局。HTML 主要关注矩形网页的大块内容。HTML 与样式、颜色或交互性无关。它的代码不是真正的功能性的,或者严格来说不是编程。更确切地说,HTML 是颜料下面的砖块。你不能对它进行样式化或者与之交互,但是你可以对它进行绘画(CSS)并且在之后添加门和窗(JavaScript)。
CSS…
是“级联样式表”,它与外观和样式有关。它涉及不同的字体系列、不同的字体大小、颜色、不透明度、分层和形状变化。这看起来是设计中最表面的层面,但是 CSS 实际上为用户体验做了相当多的工作。如果没有由聪明的 CSS 应用驱动的直观感受,即使最好的幕后设计和功能(由 JavaScript 驱动)也是无用的。每当你将光标悬停在社交媒体上的“竖起大拇指”图标上,它就会改变颜色或大小,这就是 CSS 驱动光滑和令人满意的用户体验的无意识力量。
JavaScript…
是三人组真正的“编程语言”。由于互连抽象的上下文,编程语言通常是为功能性和交互性保留的名称,而 JavaScript 在网站下以功能和数据流的形式处理这些抽象。每当用户点击按钮、填写表格或搜索栏,或者点击另一个页面的链接时,必须运行不可见的脚本来处理预期的效果。这些以基本函数、类和对象的形式出现。
所有这三样东西…
是你不应该为建立自己的网站而担心的事情!除非你是一个网络开发高手,或者是为了迎接挑战而从零开始建立一个网站,否则你可以随时学习 HTML、CSS 和 JavaScript 的基础知识,因为有了模板,这是可能的。
什么是模板?
它是 HTML、CSS 和 JavaScript 的预开发代码库,有足够简单的主干,可以直观地更改。许多入门程序员一开始可能会认为这是欺骗,因为这不像是你在建立自己的品牌或者在努力。但这对学习过程至关重要,因为 HTML 和 CSS 最好是自上而下学习**。教程只是不提供学习所必需的个人投资。**
正式的教程提供了结构化的知识,但是建立你自己的品牌是一个非常混乱和特殊的过程,学习 HTML 标签和 CSS 规则的基础知识通过使用一个漂亮的模板,并在进行中做一些小的修改会更好。首先改变
使用谷歌查找“免费 html5 模板”或“免费响应 html 模板 2020”等。有无穷无尽的选择,所以只需选择一个看起来漂亮简单的。我使用了 HTML5 UP,这是一个 Creative Commons 免费模板库,但它们中的任何一个都或多或少是一样的。Github pages 还与另一个免费模板源 Jekyll themes 集成在一起,因为 Github Pages 上的托管(见步骤 2)是免费的,Jekyll 是构建快速博客或个人网站的一个很好的选择。
一旦你下载了一个模板或主题,在你喜欢的代码编辑器中打开文件库作为一个新的项目,它可能是 Visual Studio 代码,然后开始修改!index.html
文件包含 HTML,您可以在其中修改文本和结构的构建块,而main.css
文件包含 CSS 规则。只是玩一玩,很快你就会发现没有任何教程你能做多少。打开index.html
文件(默认情况下应该在浏览器中打开)进行预览,然后通过几个小时的反复试验进行小的修改,观察哪些代码变化产生了哪些视觉变化。然后,只有当你足够了解你困惑的背景,判断一个教程是否值得时,才使用教程或指南。大多数时候,你真正需要学习的是一长串快速的 Google/Stack-overflow 解决方案。
第二步:托管
这是一个相对简单的步骤。建立一个网站背后的大部分努力都是为了让网页看起来更好,其中很大一部分就是 CSS。一旦完成,你只需要找到一个地方让代码“在野外”生存。如果你希望你的网站可以随时随地被访问,那么你应该利用网络上任何主要的免费托管服务。标准的免费托管位置是 Github Pages 用于较小的网站,如博客和个人网站,设置它的过程很简单。它很大程度上涉及到用你电脑上的代码在 Github 上创建或初始化一个存储库(例如,在你在 Visual Studio 代码中使用的项目目录中),将它公开,并在“设置”中设置 Github 页面。在“设置”中,向下滚动到“源”,并选择“主分支”,以使该存储库中的 HTML 代码在以下位置可见:your _ username . github . io/your _ project _ repository _ name
例如,如果我的 Github 配置文件名为bluepanda
,我的网站库名为bamboo
,Github Pages 以上述方式启用,那么在短暂的延迟之后,URL bluepanda.github.io/bamboo
应该会显示您的网站!这里有一个很好的 Github 页面指南,尽管文档对于最新的指南总是很有帮助。
第三步:域名
你如何最终让你的网站建立在一个自定义域名上,比如bamboo.com
,而不是略显尴尬的bluepanda.github.io/bamboo
?这一步很快也很容易,但是由于配置 DNS 设置的复杂性,有点奇怪和吓人。首先,你需要寻找一个域名提供商!这要花钱,但通常是每年 8-12 美元。这就像在你选择的提供商上搜索你定制的想要的域名一样简单,比如bamboo.com
(快速搜索‘域名提供商’应该足以提供主要的大域名,但它们基本上都是一样的),然后付费!
然后是 DNS 设置,这是最棘手的部分。重要的是要知道这很容易做到,你可以担心以后理解不理解。同时,一步一步地跟随文档绝对值得。这些步骤仅仅包括通过在 Github Pages 设置中添加您的自定义域名(如bamboo.com
)将一个CNAME
文件添加到存储库中,以及通过您的 DNS 提供商设置一个A
记录。如果你遇到困惑,在这里搜索一下可能会有用,但是 Github 关于设置域名的文档非常好。
就是这样!使用一个 1) HTML 模板,2)在 Github 页面上托管它,3)用自定义域名注册这个库,这些都是创建你自己的网站的步骤!即使您已经对本指南中的一些步骤非常有经验,我希望看到所有步骤是如何连接的会有所帮助,因为我发现本指南中的步骤 1-3 很少集成在一个教程中。
感谢阅读!
刚刚发布:BigQuery 用户友好的 SQL 函数
从 BigQuery 截断表到动态 SQL 支持;我们涵盖了 Google Cloud 发布的 12 个用户友好的 BigQuery 函数。
授权给作者的图像
随着 12 个新的 BigQuery SQL 特性的发布,我们很兴奋地看到 BigQuery 的能力得到了进一步的提升。谷歌云将这些描述为“用户友好的 SQL 功能”。那么,让我们来看看现在有什么可能。
1.通过 DDL 添加表列
BigQuery 的新特性是能够通过 ALTER TABLE DDL 语句添加新列。这是具有传统本地数据库平台背景的数据专业人员所期望的标准,所以很高兴看到 Google Cloud 已经承认了这一点。
alter table mydataset.mytable
add column a string,
add column if not exists b geography,
add column c array<numeric>,
add column d date options(description="my description")
我们喜欢这样的语法:如果一个列还不存在,就只添加一个,这对于幂等部署来说很方便。也完全支持记录。从 BigQuery 文档中了解更多信息。
2.截断表格
现在支持 TRUNCATE TABLE,这将满足那些来自本地后台的用户。与 BigQuery 中会产生扫描成本的 DELETE DML 语句不同,TRUNCATE 属于不断增长的 BigQuery 自由操作列表。我们肯定会经常用到这个。
truncate table [project_name.] dataset_name.] table_name
为了降低查询扫描成本,我们建议在需要删除表的全部内容时使用 TRUNCATE 而不是 delete。
3.Unicode 表命名
BigQuery 现在支持 Unicode 表命名。由于支持多语言,表名不再仅限于字母、数字和下划线。
小心表格命名,确保表格一致、易读,并遵循组织内的命名惯例。
4.BigQuery 联邦表变得(甚至)更好了
在 Ancoris,我们喜欢 BigQuery 中的联邦(外部)表;它们作为一种强大的零数据工程方法,可以轻松地从 Google 云存储中摄取文件,包括常见的格式,如 JSON 和 CSV。
很高兴看到您现在可以使用 DDL 语句创建外部表了。
下面的示例创建了一个从两个不同的存储 URIs 读取 CSV 的表:
create external table dataset.CsvTable options(
format = 'CSV',
uris = ['gs://bucket/path1.csv', 'gs://bucket/path2.csv']);
要了解更多信息,请参见这些创建联邦表的例子。我们计划在接下来的几周内做一个技术指导来展示什么是可能的。
5.使用 SQL 将数据从 BigQuery 导出到 Google 云存储
这在发行说明中被掩盖了一点,但是在我们看来这是一个非常强大的特性。您现在可以使用新的 EXPORT DATA SQL 命令将 BigQuery 查询的结果导出到 Google 云存储中;支持所有 Bigquery 支持的数据格式和压缩类型。
这里有一个取自 BigQuery 导出数据文档的例子。
export data options(
uri='gs://bucket/folder/*.csv',
format='CSV',
overwrite=true,
header=true,
field_delimiter=';') as
select field1, field2
from table1
order by field1 limit 10
很高兴看到没有外出费用;您只需为任何扫描的 BigQuery 数据和存储在 GCS 中的数据付费。
这似乎加强了谷歌云减少复杂数据工程需求的愿望,这是我们(和我们的许多客户)所共有的。如果将它与从目标 GCS bucket 触发的云函数结合起来,就可以提供一种简单的机制,将数据传递到 BigQuery 之外的数据管道中。
6.立即执行(动态 SQL)
BigQuery 现在支持动态 SQL 的执行。语法非常熟悉,特别是对于那些有 MS SQL 背景的人来说。
-- create a temporary table called Books.
execute immediate
‘create temp table books (title string, publish_date int64)’;-- add a row for Hamlet
execute immediate
‘insert into books (title, publish_date) values('Hamlet', 1599)’;
更多例子见 BigQuery 动态 SQL 支持。
一般来说,我们非常谨慎地使用动态 SQL,并尽可能避免使用它(主要是因为 SQL 注入的风险,它会使代码更难阅读和调试)。
7.授权的用户定义函数(UDF)
对于那些不熟悉BigQuery UDF的人来说,这些是 big query 中的标量函数,允许您使用 SQL 或 Javascript(以及相关的 Javascript 库)对数据进行操作。
BigQuery 现在支持授权的 UDF,这允许授权的使用者(通过 IAM)查询数据集中的表,即使调用 UDF 的用户无权访问这些表。你们中有 MS SQL 背景的人,这类似于 SQL Server 中的表值函数的许可;这些通常用作(锁定的)表的安全层,并加强行/列级别的安全性。
8.查询结果中有重复的列名
BigQuery 现在允许您在一个查询中多次选择同一个(未分类的)列,方法是附加一个后缀 _n,其中 n 是观察到的重复次数。
9.新的 BigQuery 最后一天日期函数
BigQuery 已经很好地支持了使用 SQL 的日期操作。看起来在这个版本中,谷歌云已经认识到了一个常见的商业主导用例;查找给定期间的最后一天,例如一个月的最后一天或一周的最后一天。
新的 LAST_DAY 函数具有直观的语法,易于阅读:
select last_day(’2020-10-23’, week) as last_day_of_week
2020-10-24
注意默认情况下,这将返回下一个星期六,因为在 BigQuery 中一周从星期日开始。
要强制一周从星期一开始:
-- the last day of the week
-- (week starting monday)select last_day(’2020-10-23’,
week(monday)) as last_day_of_week
2020-10-25
10.BigQuery 中的日期算法
我们习惯于使用 data_add 和 date_sub 函数进行日期运算,但是现在您可以使用+和-操作符来完成这项工作。
-- you can now do this
select ’2020-10-23’ + 2
2020-10-25-- instead of this
select date_add(’2020-10-23’, interval 2 day)
2020-10-25
11.新的 BigQuery 字符串函数
许多(总共 14 个)新的用于操作字符串的 BigQuery SQL 函数。以下是我们特别喜欢的几个:
大查询串联运算符“||”
作为一个团队,我们认为这种连接字符串的方法比 concat 函数更容易阅读。
-- the new way
select ’The ’||‘quick ’||‘brown ’||‘fox’ as quip-- the old way
select concat(’The ’,‘quick ’,‘brown ’,‘fox’) as quip
BigQuery 指令
这将返回字符串中搜索值的索引。注意,字符串中的第一个字符索引为 1,如果没有找到该字符串,则返回 0。
第三个参数是位置,表示从哪里开始搜索。默认值为 1。如果提供了负数,这表示从字符串末尾开始-n 个字符。
最后一个参数是的出现次数,如果提供了该参数,则指定要搜索的字符串的出现次数,例如 2 表示查找搜索值的第二个出现次数的索引。
select instr(’banana’,‘an’)
2
select instr(’banana’,‘an’,3)
4
select instr(’banana’,‘an’,1, 2)
4
select instr(’banana’,‘an’,1, 3)
0
BigQuery Soundex
这在我们的列表中,因为我们都认为它非常简洁。这个函数返回一个单词的拼音,表示为 soundex 代码(alpha 后跟 3 个数字)。该算法于 1918 年首次获得专利,可用于模糊逻辑匹配,例如检测人名的拼写错误:
select soundex(’Brian’)
B650
select soundex(’Bryan’)
B650
select soundex(’Briann’)
B650
select soundex(’Brrian’)
B650
select soundex(’Brenda’)
**B653**
12.扩展信息模式
ANSI SQL 标准中指定的 INFORMATION_SCHEMA 允许用户查询包含或引用数据的各种对象或实体的元数据,如表、视图、存储过程和用户定义的函数。下面是 BigQuery INFORMATION_SCHEMA 文档。
BigQuery 引入了许多新的对象,包括表、视图、例程(存储过程、UDF)和数据集,使得这一点变得更加容易。
select table_name
from mydataset.INFORMATION_SCHEMA.TABLES
where table_name like 'scenario%'
注意表格是大写的(BigQuery 区分大小写)。
意见
总之,这是对 BigQuery SQL 库的一个很好的补充,我们肯定会在客户端项目中使用它。我们将在即将发布的数据操作系列中讨论其中的一些主题。
后续步骤
2.了解更多关于 Ancoris 数据,分析& AI
3.与作者连线
刚刚在我的锻炼中使用了机器学习!
计算机视觉在健身中的应用演示
我是体重法的忠实粉丝,通常也是锻炼的忠实粉丝,但我不太喜欢去健身房。
此外,在这个由于冠状病毒而被迫封锁的时期,尝试不同的方式来进行健身和训练可能是有用的。
于是我问自己:有没有办法把机器学习用在这方面?我能把两种激情结合起来做点有用的东西吗?
一个主要的问题是有一种方法来验证一个练习的正确性,所以我做了一些实验并尝试了一种方法,发现…
好了,不想剧透什么,就继续看下去了解一下吧!
框定问题
和往常一样,让我们从框定问题开始。我们想要实现的是使用视频作为输入,有一种方法来评估练习的正确性。
最佳方案应该是使用实时流,但是现在让我们简单地使用一个文件,因为毕竟我们想在构建之前验证一种方法。
因此,第一步应该是有一个(希望)正确执行的视频,因为它可以用作比较其他视频的基线。
这是第一个视频,在我的地下疲劳室拍摄的:)
基线 ok 执行
我的第一个想法是使用 CNN 来建立一个分类器,但是,除了所需的例子数量之外,我不确定图像序列像素是否有助于训练一个关于练习执行中什么是错什么是对的模型。
所以,我做了一些研究,看看是否有可能使用视频作为输入来获得不同的特征,并找到了一个很棒的库, OpenPose ,一个“用于身体、面部、手和脚估计的实时多人关键点检测库”。
看到演示视频,我明白这可能非常有用,所以我试图将它应用到我的问题中,并有了这个…
使用 OpenPose
(我将在后面的附录中写下所有必要的设置步骤)
正如你在视频中看到的,该库可以很好地跟踪不同的身体部位(使用带有 18 个关键点的 COCO 配置)
很酷的一点是,也可以输出一个 json 文件,一帧一帧地显示所有的位置,所以应该可以用数字来表示一个练习。
因此,做一些辅助功能,并使用 Plotly,这是这个练习看起来如何考虑 y 轴移动-跳过 x 轴,因为给定相机位置不太有用。
姑且称之为**“ok1”**
好习题 ok1 的分解分析
很好,下一步是找到一种方法来比较两个不同的执行,看看是否有显著的差异。
让我们首先基于这些指标进行一个视觉比较,我们称这个执行为**“失败 1”**
故障 1
让我们比较一下运动的图表
ok1 和 fail1 的比较
存在明显的差异。
让我们尝试另一个失败的表现(“fail 2”)
故障 2
让我们与基线正确执行 ok1 进行比较
ok1 和 fail2 之间的比较
现在让我们来比较两个好的表现(让我们称之为第二个**“ok 2”**)
ok2
ok1 和 ok2 的比较
曲线看起来非常相似,所以我们根据经验测试了这种方法。
现在的问题是:考虑到可能有不同的时间尺度,有没有办法评估这些单变量时间序列曲线之间的相似性?
原来有一种叫做动态时间扭曲的东西可以用来“测量两个时间序列之间的相似性”。更多此处
Python 中有实现吗?当然,使用 tslearn.metrics
所以让我们分析一些数字
首先比较“ok1”和它自己
dtw_value for feature nose_y is 0.0
dtw_value for feature right_shoulder_y is 0.0
dtw_value for feature right_elbow_y is 0.0
dtw_value for feature right_wrist_y is 0.0
dtw_value for feature left_shoulder_y is 0.0
dtw_value for feature left_elbow_y is 0.0
dtw_value for feature left_wrist_y is 0.0
dtw_value for feature right_hip_y is 0.0
dtw_value for feature right_knee_y is 0.0
dtw_value for feature right_ankle_y is 0.0
dtw_value for feature left_hip_y is 0.0
dtw_value for feature left_knee_y is 0.0
dtw_value for feature left_ankle_y is 0.0
dtw_value for feature right_eye_y is 0.0
dtw_value for feature left_eye_y is 0.0
dtw_value for feature right_ear_y is 0.0
dtw_value for feature left_ear_y is 0.0
dtw_value for feature background_y is 0.0
所以 0 值是最大相似度,分数越低表示相似度越高
让我们现在尝试测量 ok1 和 fail1
dtw_value for feature nose_y is 188.00378744123748
dtw_value for feature right_shoulder_y is 155.97642562435527
dtw_value for feature right_elbow_y is 156.39925059973916
dtw_value for feature right_wrist_y is 17.982641407757672
dtw_value for feature left_shoulder_y is 13.5329438534267
dtw_value for feature left_elbow_y is 158.0005797757085
dtw_value for feature left_wrist_y is 27.544745106825722
dtw_value for feature right_hip_y is 12.151614599714703
dtw_value for feature right_knee_y is 191.94638493339747
dtw_value for feature right_ankle_y is 223.23781654997444
dtw_value for feature left_hip_y is 263.0165952996121
dtw_value for feature left_knee_y is 195.8379463587177
dtw_value for feature left_ankle_y is 227.95958454954243
dtw_value for feature right_eye_y is 288.64055642788685
dtw_value for feature left_eye_y is 192.9321060365538
dtw_value for feature right_ear_y is 192.15753964939807
dtw_value for feature left_ear_y is 190.20149442225735
dtw_value for feature background_y is 189.09276308989186
我发现采用一个整体值来获得更简洁的信息很有用,比如中位值
dtw_median : 189.6471287560746
ok1 和 fail2 之间的比较
dtw_value for feature nose_y is 65.28319682858675
dtw_value for feature right_shoulder_y is 38.87442004120449
dtw_value for feature right_elbow_y is 37.75683113715981
dtw_value for feature right_wrist_y is 18.907807197028447
dtw_value for feature left_shoulder_y is 19.50736795264806
dtw_value for feature left_elbow_y is 45.031636992674414
dtw_value for feature left_wrist_y is 36.101698713495466
dtw_value for feature right_hip_y is 13.248353503737741
dtw_value for feature right_knee_y is 39.45295418596681
dtw_value for feature right_ankle_y is 49.27277845829276
dtw_value for feature left_hip_y is 65.78598402395453
dtw_value for feature left_knee_y is 38.59586190254078
dtw_value for feature left_ankle_y is 44.54850474482842
dtw_value for feature right_eye_y is 64.17832564035923
dtw_value for feature left_eye_y is 50.02819053653649
dtw_value for feature right_ear_y is 50.233695101993064
dtw_value for feature left_ear_y is 45.21480605000976
dtw_value for feature background_y is 42.15576012017812dtw_median : 43.35213243250327
ok1 和 ok2 的比较
dtw_value for feature nose_y is 16.023831603583467
dtw_value for feature right_shoulder_y is 11.24889546622242
dtw_value for feature right_elbow_y is 11.94796246520719
dtw_value for feature right_wrist_y is 20.509653605070962
dtw_value for feature left_shoulder_y is 19.65007578484111
dtw_value for feature left_elbow_y is 14.486468134089847
dtw_value for feature left_wrist_y is 7.208783392501132
dtw_value for feature right_hip_y is 14.17544715061928
dtw_value for feature right_knee_y is 25.759515076957445
dtw_value for feature right_ankle_y is 43.123581089700735
dtw_value for feature left_hip_y is 83.91171946754521
dtw_value for feature left_knee_y is 23.860467116131673
dtw_value for feature left_ankle_y is 44.80603683656928
dtw_value for feature right_eye_y is 91.27560108813313
dtw_value for feature left_eye_y is 31.263050533657154
dtw_value for feature right_ear_y is 25.735729785455852
dtw_value for feature left_ear_y is 12.39151408383979
dtw_value for feature background_y is 11.887661376402017dtw_median : 20.079864694956036
因此,该值似乎可以用作一个指标,根据要找到的阈值来比较两次执行的正确性。
作为一个经验性的反检验,让我们从这个值开始尝试其他例子
ok1 和 check1 ->中位值 82。46860 . 66666666666
ok2 和 check 2–>中位值 19660 . 666666666616
确定并检查 3 ->中位值 25。48860 . 88888888861
似乎低于 30 的中位值可能是起始阈值
让我们在视频上看到他们
不允许跳跃!
不完全的
好的。
结论
这只是这个实验的开始:假设这是正确的方法,有很多开放点,例如:
- 不同身高的人怎么样?他们也需要一个个人基线,或者可以概括?
- 不同的相机位置怎么样?
- 如何推断阈值?
- 如何对执行中的错误给出更详细的建议?
- 如何在连续视频流中处理练习的相关部分?
- 可以跟踪使用哑铃等工具进行的练习吗?(提示:是的,但是也有特定的对象检测库)
我有一些想法要检查,我会在未来做,即使因为可能性是美妙的。
更新:我从这开始增加了其他功能。在这里查看
想象一个带有摄像头的工作站
- 当您用面部识别输入时,识别您
- 加载您的“wod”(当天锻炼)
- 检查给出提示的练习的正确性
- 向在场或可能与几十人一起参加远程课程的培训师发出执行不当的信号,允许他/她采取纠正措施。
甚至培训也可以根据之前的课程和个人的整体情况进行定制。
一如既往,我对这些技术可能实现的目标和想象感到惊讶,使用它们非常有趣。
同时,祝你锻炼愉快,注意安全。
附录
Docker+OpenPose
我没有直接安装 OpenPose 和所有必要的依赖项,而是选择了 Docker 方法。你可以在这里找到图片:https://hub.docker.com/r/garyfeng/docker-openpose/
请记住,对于实时方法来说,使用容器可能不是正确的解决方案,因为有很多延迟,但我没有尝试过其他解决方案,所以我不能肯定地说。
但是在运行之前,需要使用 GPU 运行容器,否则 OpenPose 不会启动。这里是所有做这件事的指令(用 Invidia GPU):【https://github.com/NVIDIA/nvidia-docker
您将在命令中看到“privileged”和-e DISPLAY = $ DISPLAY-v/tmp/. X11-UNIX:/tmp/. X11-UNIX 部分,如果需要的话,它们用于访问容器内的摄像机。
在启动 docker 命令之前,请确保执行:
xhost +
所以容器可以连接。
然后,就发射
docker run --privileged --gpus all -v <host path to share>:/**data** -e DISPLAY=$DISPLAY -v /tmp/.X11-unix:/tmp/.X11-unix -it garyfeng/docker-openpose:latest
过一会儿,您将进入容器内的 bash shell
如果你查看 OpenPose 文档,有很多参数,但是让我们看几个例子
build/examples/openpose/openpose.bin --face
它应该打开相机,并开始检测你脸上的关键点。
我之前用来创建数据的命令是:
build/examples/openpose/openpose.bin --video /**data**/<input file> --write_video /**data**/<ouptut file> --no_display --write_keypoint_json /**data**/<folder with json output files>
注意启动容器时挂载的“data”文件夹。如果您更改了它,请确保根据命令进行相应的调整。
Python 代码
现在让我们看一些 Python 代码来处理本文中使用的数据
import pandas as pd
import os
import numpy as npdef read_pose_values(path, file_name):
try:
path, dirs, files = next(os.walk(path))
df_output = pd.DataFrame()
for i in range(len(files)):
if i <=9:
pose_sample = pd.read_json(path_or_buf=path+'/' + file_name + '_00000000000' + str(i) + '_keypoints.json', typ='series')
elif i <= 99:
pose_sample = pd.read_json(path_or_buf=path+'/' + file_name + '_0000000000' + str(i) + '_keypoints.json', typ='series')
else:
pose_sample = pd.read_json(path_or_buf=path+'/' + file_name + '_000000000' + str(i) + '_keypoints.json', typ='series')
df_output = df_output.append(pose_sample, ignore_index = True)
return df_output
except Exception as e:
print(e)
这用于返回一个 DataFrame,其中包含在 OpenPose json 输出路径中找到的所有 json(注意,如果有 1000 个以上的文件,它会中断——肯定要修复:)
'''
Nose – 0, Neck – 1, Right Shoulder – 2, Right Elbow – 3, Right Wrist – 4,
Left Shoulder – 5, Left Elbow – 6, Left Wrist – 7, Right Hip – 8,
Right Knee – 9, Right Ankle – 10, Left Hip – 11, Left Knee – 12,
LAnkle – 13, Right Eye – 14, Left Eye – 15, Right Ear – 16,
Left Ear – 17, Background – 18
'''
from sklearn.preprocessing import MinMaxScalerdef transform_and_transpose(pose_data, label):
output = pd.DataFrame()
for i in range(pose_data.shape[0] -1):
if len(pose_data.people[i]) > 0:
output = output.append(pd.DataFrame(pose_data.people[i][0]['pose_keypoints']).T)# drop confidence detection
for y in range(2,output.shape[1] ,3):
output.drop(columns=[y], inplace=True# rename columns
output.columns = ['nose_x', 'nose_y', 'right_shoulder_x', 'right_shoulder_y', 'right_elbow_x', 'right_elbow_y',
'right_wrist_x', 'right_wrist_y', 'left_shoulder_x', 'left_shoulder_y', 'left_elbow_x', 'left_elbow_y',
'left_wrist_x', 'left_wrist_y', 'right_hip_x', 'right_hip_y', 'right_knee_x', 'right_knee_y',
'right_ankle_x', 'right_ankle_y', 'left_hip_x', 'left_hip_y', 'left_knee_x', 'left_knee_y',
'left_ankle_x', 'left_ankle_y', 'right_eye_x', 'right_eye_y', 'left_eye_x', 'left_eye_y',
'right_ear_x', 'right_ear_y', 'left_ear_x','left_ear_y','background_x', 'background_y']
# interpolate 0 values
output.replace(0, np.nan, inplace=True)
output.interpolate(method ='linear', limit_direction ='forward', inplace=True)return output
这里,我们基于 COCO 设置和基本插值对列进行重命名,如果值为 0(例如,当鼻子在引体向上栏后面时):
def model_exercise(json,name,label):
df_raw = read_pose_values(json,name)
return transform_and_transpose(df_raw,label)df_exercise_1 = model_exercise('<path to json>','<file_name>','<label>')
将所有这些放在一起,使用函数得到最终的数据帧。
现在让我们看一些图表:
import plotly.graph_objects as go
from plotly.subplots import make_subplots
def plot_y_features(df):
fig = make_subplots(rows=3, cols=6, start_cell="top-left")
r = 1
c = 1
X = pd.Series(range(df.shape[0]))
for feature in df.columns:
if '_y' in feature:
fig.add_trace(go.Scatter(x=X, y=df[feature], name=feature),
row=r, col=c)
fig.update_xaxes(title_text=feature, row=r, col=c)
if c < 6:
c = c + 1
else:
c = 1
r = r + 1
fig.update_layout(title_text="Exercise y-axis movements breakdown", width=2000, height=1000)
fig.show()plot_y_features(df_exercise_1)
画出所有位置的支线剧情。
现在比较两个练习:
def plot_comparison_y_features(df1,df2):
fig = make_subplots(rows=3, cols=6, start_cell="top-left")
r = 1
c = 1
X1 = pd.Series(range(df1.shape[0]))
X2 = pd.Series(range(df2.shape[0]))
for feature in df1.columns:
if '_y' in feature:
fig.add_trace(go.Scatter(x=X1, y=df1[feature], name=feature + '_ok'),row=r, col=c)
fig.add_trace(go.Scatter(x=X2, y=df2[feature], name=feature + '_fail'),row=r, col=c)
fig.update_xaxes(title_text=feature, row=r, col=c)
if c < 6:
c = c + 1
else:
c = 1
r = r + 1
fig.update_layout(title_text="Exercise y-axis movements breakdown comparison", width=2000, height=1000)
fig.show()plot_comparison_y_features(df_exercise_1, df_ok2)
最后是动态时间弯曲部分:
def evaluate_dtw(df1,df2,feature, plot=False):
x1 = range(df1.shape[0])
y1 = df1[feature].values x2 = range(df2.shape[0])
y2 = df2[feature].values
dtw_value = evaluate_dtw(df1[feature],df2[feature])
print("dtw_value for feature {} is {}".format(feature, dtw_value))
return dtw_valuedef evaluate_dtw_values(df1,df2,plot = False):
dtw_values = []
for feature in df1.columns:
if '_y' in feature:
dtw_values.append(dtw(df1,df2,feature,plot))
return pd.DataFrame(dtw_values)
仅此而已!谢谢你。
库存预测的合理性
机器学习算法能证明有效市场假说是错误的吗?
来自《走向数据科学》编辑的提示: 虽然我们允许独立作者根据我们的 规则和指南 发表文章,但我们并不认可每个作者的贡献。你不应该在没有寻求专业建议的情况下依赖一个作者的作品。详见我们的 读者术语 。
简介(预测的有效性)
根据美国经济学家、畅销书《华尔街随想》的作者伯顿·戈登·马尔基尔的说法:“在科学的审视下,图表阅读必须与炼金术共享一个基座。”马尔基尔和学术界的许多其他人都认为,根据有效市场假说的条款,股票市场是一个股票价格波动非常大的地方,其结果无法根据过去的数据合理预测。话说回来,是不是经常这样?
有效市场假说认为:证券在交易所总是以公允价值交易,股票价格应该代表所有相关信息,即阿尔法的产生是不可实现的。简单地说,该假设断言,在一段时间内的任何给定时间,市场都有能力适应新信息,因此不可能超越它。换句话说,基本面分析比技术分析更有优势。一个人的猜测和另一个人的一样好,或者如马尔基尔的名言所说:“你的猜测和猿的一样好。”
现在应该更清楚为什么作为现代金融理论基石的有效市场假说的支持者认为股票市场的预测是无效的。然而,这并不能解释金融服务领域的绝大多数机构,如交易公司、共同基金和对冲基金,它们采用定量交易算法和图表数据,通过技术分析每年产生数十亿美元的利润。行为金融学还表明,股票市场的投资者远非理性,这意味着未来的价格事实上可以在“一定程度上”基于对历史趋势的分析来预测。这意味着股票市场预测的概念肯定有一些优点。
摘要
本报告旨在探讨预测证券价格的有效性。更具体地说,它解决了一个研究问题:根据历史股票数据训练的机器学习模型能否准确预测未来数据,以及预测到什么程度?
因此,它的特点是使用一种称为 LSTM(长短期记忆)的深度学习类的机器学习算法进行单变量时间序列分析。微软公司(MSFT)的历史股票数据用于数据探索、预处理、后处理、可视化以及模型拟合和评估。从最近的日期开始的十五个营业日的股票市场预测也在接近结束时进行。此外,均方误差、均方根误差和 R 平方作为评估模型总体性能的主要估计量。
与实际价格相比,该模型生成的结果值相当准确。因此,可以得出结论,机器学习确实可以是在很大程度上预测股票数据的有效方法。
包含整个程序的 GitHub 库可以在这里访问。
方法学
数据采集-
MSFT 的数据集是通过名为 Tinngo 的金融市场 API(应用程序编程接口)获得的,并使用 pandas_datareader 包进行访问。为了了解正在处理的数据,下面是将其转换为数据框后的原始形式。
数据集由 14 个要素组成,如列所示。
数据预处理-
在最初的清理/格式化阶段实施了一些简单的过程,以便为将来使用数据集做准备。
- 所有列标题的第一个字母都大写。
- 日期列中的值被转换为日期时间对象。
- 从日期列的值中删除了时间值,因为它不涉及 MSFT 价格的日常时间序列模式。
- 创建了一个循环来检查任何缺少的值;对于所有列中的所有行,它都返回 false,这表明没有丢失值。
生成的新数据框如下所示:
初步数据可视化-
深入了解 MSFT 价格运动的复杂本质非常重要,因为这有助于在未来决定最有效的机器学习模型。由于“收盘”功能涵盖了每个交易日结束时股票的现金价值,因此执行了仅与“收盘”相关的某些可视化方法。
绘制了一个箱线图和一个补充描述图,作为数据可视化这一阶段的第一步。
**
从箱线图可以很容易地看出,似乎没有超出分布数据的最小和最大范围的极端异常值。
图表中的高标准差确实揭示了过去五年 MSFT 价格的波动性。更准确地说,在 96.44 美元的平均值周围有 41.91 美元的离差。此外,这个值必须有所保留,因为标准差的项可能与基础证券的价格有关。这意味着标准差的值可以反映股票价格而不是波动性。因此,使用变异系数来评估波动的真实程度,变异系数代表标准差与平均值的比率。这有助于理解样本中数据相对于总体均值的可变性程度。
由此得出的变异系数为:41.91 ÷ 96.44 = 0.4346。由于该值远低于 1,因此可以有把握地假设 MSFT 总体上不像之前假设的那样高度不稳定。此外,考虑到微软公司基于其资产负债表的强大财务健康,预计与其股权相关的风险应处于较低水平。
为了更好地显示 MSFT 证券的过去趋势,绘制了一个折线图。图表的主要亮点是 2020 年 3 月至 6 月证券价值的大幅下降和快速恢复。这种极端的波动性可以解释为由于最近的 2020 年新冠肺炎疫情对整个股票市场的忧虑态度。
型号选择-
如前所述,选择了单变量时间序列分析,该分析用单个时间相关变量检查一个序列。这是在初步数据可视化阶段之后完成的;在做出这个决定之前,我们考虑了一些因素:
- 报告的目的不是要找出多个系列之间的相关关系。更确切地说,它是分析单个价格序列如何在其自身的历史视角上发展的行为。
- 数据集中的许多其他特征已被证明对收盘价影响很小甚至没有影响。股息是一个例外;然而,API 并不提供关于它的数据。
- 虽然特征高,低,开放和他们的调整后的对应物可能对收盘价有一个小的影响,这可能只是通过引入噪音使模型过于复杂。
考虑到这些因素,建立了长短期记忆(LSTM)神经网络作为执行单变量时间序列预测的最佳选择。这些推理属于 LSTM 的架构,它在时间序列的每一步存储信息的能力,以及研究问题的性质。
为了理解 LSTM 网络的结构,首先必须理解人工神经网络和递归神经网络(RNNs)的概念。人工神经网络基于互连的数据处理组件的网络,这些组件被称为组织成层的节点。一层中的给定节点通过权重与前面层中的所有其他节点相连,权重影响信号的强度和网络的输出。有三种类型的节点:1)收集数据的输入节点,2)生成值的输出节点,3)修改数据的隐藏节点。
RNN 是一种人工神经网络,它以前馈方式工作,允许信息从一个步骤按顺序传播到另一个步骤。然而,与基本前馈神经网络不同,RNNs 在层之间具有递归关系。这意味着他们利用反馈回路,即所谓的时间反向传播,将细节传回网络,这样来自先前输入的信息就可以持续。
展开的 RNN |来源:https://colah.github.io/posts/2015–08-Understanding-LSTMs/
然而,RNNs 也处理消失梯度问题,即在时间段的大间隙之间逐渐丢失信息。当更新神经网络中的权重的梯度由于时间上的反向传播而收缩时,就会发生这种情况。长期短期记忆网络通过实施内部机制(细胞状态和门)来调节信息流,从而改善了这一缺点。细胞状态在整个序列处理过程中传输相关信息,而门是不同的神经网络,它选择哪些信息可以在细胞状态中持续存在。有三种门:1)遗忘门,它选择相关信息来存储和传递,2)输入门,它更新单元状态,3)输出门,它确定随后的隐藏状态。这些操作使得 LSTM 模型善于学习长期依赖关系。
https://colah.github.io/posts/2015–08-Understanding-LSTMs/ LSTM 网络中的复读模块|来源
因此,LSTM 网络被确定为处理报告时间序列问题的最佳选择。有关 rnn 和 LSTMs 的更多信息可在此处查看。
数据-后处理-
在本节中,来自预处理阶段的数据被进一步讨论,目的是为 LSTM 模型做准备。形成了一个新的数据帧,该数据帧仅由“Close”组成,并以“Date”作为索引值。由于日终现金价值最能代表某一特定日的证券市场价格,因此重点是“收盘”。
LSTM 模型对比例很敏感;因此,来自新数据帧的数据通过从 0 到 1 的缩放进行标准化。这将提高网络收敛的速度。
***#Scaling Data**mms = MinMaxScaler(feature_range = (0,1))scaled_close = mms.fit_transform(df_close).reshape(-1,1)*
新的数据集然后被分成两个部分:80%的训练和 20%的测试。这将允许在最初 80%的数据(训练集)上训练模型,然后在剩余部分(测试集)上重新评估其性能。
***#Splitting Train/Test Data**train_ratio = 0.80rolling = 60train_data = np.array(scaled_close[:int(len(df_close)*train_ratio)])test_data = np.array(scaled_close[int(len(train_data))-rolling:])*
“滚动”变量代表时间步长,即模型分析产生输出的天数。考虑下面的例子:
有一个用于训练机器学习模型的值序列。在每一行中,序列的四个值作为输入,随后的第五个值作为输出;随着行的前进,输入和输出组在序列中向下移动一个值。变量“滚动”代表用于产生输出的输入数量。这个概念进一步应用于将训练集和测试集分成输入集和输出集。
***#Separating x/y Training Sets**x_train = []y_train = []for i in range(rolling, len(train_data)): x_train.append(train_data[i-rolling:i,0]) y_train.append(train_data[i,0])**#Separating x/y Testing Sets**x_test = []y_test = df_close[int(len(train_data)):]for i in range(rolling, len(test_data)): x_test.append(test_data[i-rolling:i])*
LSTM 网络需要三维数组数据作为输入。第一个维度表示批量大小,第二个维度描述时间步长,最后一个维度描述特征。因此,输入被整形以符合这些要求。
***#Reshaping x/y Sets**x_train, y_train = np.array(x_train), np.array(y_train)x_train_shape = x_train.shape[0]x_train = np.reshape(x_train, (x_train_shape, rolling, 1))x_test, y_test = np.array(x_test), np.array(y_test)x_test_shape = x_test.shape[0]x_test = np.reshape(x_test, (x_test_shape, rolling, 1))*
模型制作-
为了构建 LSTM 模型,从 Keras 库中导入了某些模块。
*from keras.models import Sequentialfrom keras.layers import LSTMfrom keras.layers import Densefrom keras.layers import Dropout*
1)顺序将被用作初始化神经网络的构造器,2) LSTM 将协助添加长短期记忆层,3)密集将添加密集连接的神经网络层 4)丢弃将添加丢弃层以防止模型过度拟合。
生成的模型如下所示:
***#LSTM Model**lstm = Sequential()lstm.add(LSTM(rolling, return_sequences = True, input_shape =(rolling, 1)))lstm.add(Dropout(0.2))lstm.add(LSTM(rolling, return_sequences = True))lstm.add(Dropout(0.2))lstm.add(LSTM(rolling))lstm.add(Dropout(0.2))lstm.add(Dense(1)) lstm.compile(optimizer = 'adam', loss = 'mse', metrics = ['mean_squared_error'])*
LSTM 模型是用以下参数创建的:
- 60 个单位作为 LSTM 层中输出空间(时间步长)的维度。
- Return_sequences = True,返回每个输入时间步长和堆叠的隐藏状态输出
- LSTM 层。(以便随后的 LSTM 层具有三维序列)
- 0.2 作为丢弃层的输入,丢弃 20%的层,以防止模型过度拟合。
- 密集层中的输入 1 指定一个单位的输出。
- Adam optimizer 是一种更新网络权重的优化算法,用于编译模型。
- 均方误差被设置为损失优化器。
然后用来自数据训练部分的输入和输出集来拟合该模型。然后用某些特征对其进行训练,例如 epochs,其指示学习算法将在整个数据集中工作的次数,设置为 60,分配给 x_train.shape[0]的批量大小,以及给定测试集的验证集。
***#LSTM Model Fitting**lstm.fit(x_train, y_train, validation_data=(x_test, y_test),epochs = 60, batch_size = 50, verbose = 1)*
模型评估指标-
被选择用来评估 LSTM 模型性能的三个估计量是均方误差(MSE)、均方根误差(RMSE)和 R 平方。MSE 应评估误差平方和返回误差方差的平均值。RMSE 是 MSE 的平方根版本,它将计算残差(预测误差)的标准偏差。最后,R 平方度量将展示回归线与实际数据点的拟合,因为它测量模型所解释的响应变量变化的百分比。
结果
使用 Sequential 的 predict()和 MinMaxScaler 的 inverse_transform()函数,从拟合的模型生成预测,并从 0 到 1 的范围内重新缩放。这导致了两套价格预测;一个用于训练部分,一个用于测试部分。
模型在训练集上的性能由三个模型评估度量来评估。
这些 MSE 和 RMSE 值立即表明在实际历史数据点周围没有太多误差,因为两者都接近于 0。R 平方的值表明 MSFT 99.53%的价格可以用模型解释。虽然这些结果最初可能说明了预测的惊人准确性,但存在严重的过度拟合问题,因为它可能无法很好地转化为看不见的数据。
通过绘制实际训练数据集及其预测值,可以更好地可视化这些指标。
该模型在测试集上的性能由相同的三个评估指标进一步评估。
与训练集相比,MSE 和 RMSE 更高,R 平方更低。然而,这些 MSE 和 RMSE 仍然被认为非常低。这证明了模型集与实际值相差不大。R 平方值表明 94.2%的 MSFT 价格可以用模型解释。
再次,这是可视化的图形实际训练数据集和预测值。
实际值与预测值的图表:
讨论
可以有一定把握地说,LSTM 模型在预测股票价格方面证明是成功的。与真实数据点相比,特别是测试部分的预测值相当准确;0.17 的 MSE 和 0.41 的 RMSE 接近于 0 并且非常低,因此表明平均误差偏差很小。这一印象被 0.942 的 R 平方进一步证实,因为该模型能够解释测试集中 94.2%的 MSFT 股票价格。
虽然最初有人担心该模型在训练集上过度拟合,因为它在所有三个指标上都非常接近完美,但实际上它最终很好地转变为预测测试集上的未知数据。然而,仍然有一个问题值得关注,即为什么模型表现得如此之好,它涉及单步和多步时间序列预测之间的差异。迄今为止建立的模型是单步时间序列预测模型,因为它使用几个输入来生成一个输出。但是,请考虑已定型的模型是否是多步时间序列投影,在这种情况下,也将接受多个输入并生成多个输出。毫无疑问会有不同的结果。
创建多步时间序列投影的一种常用方法是通过递归方法,这种方法包括制作单个投影并将其附加到下一组输入中,以预测后续的时间步。
然而,它也引入了将早期误差传播到未来预测中的问题;来自时段 t 和 t+1 的预测误差将延续到后续时段。因此,如果单个预测在某种程度上不准确,则下一个值链很有可能变得越来越错误,因为错误的值将被用作未来的输入。因此,由于误差传播,多步时间序列预测模型有可能在更长的预测时间内退化。
在本报告中使用的单步模型的情况下,即使一个预测完全偏离实际值,后续的预测也很有可能被实际值带回正轨。
话又说回来,这个关注点不应该完全抹黑模型的准确性。如前所述,该模型在捕获 60 个数据点作为输入以生成一个输出方面表现良好,这平均只会在训练数据上偏离 0.19 美元,在未看到的数据上偏离 0.41 美元。因此,即使在递归多步时间序列预测的情况下,基于该模型的预测在未来的某个时期也应该是相当准确的,很可能小于 60 点。
结论
预测股市还是有一些好处的,尤其是通过像机器学习这样强大的方法。该报告的研究结果表明,在单步时间序列预测问题的情况下,使用 LSTM 网络可以产生具有良好准确性的结果,更具体地说是 94.2%。对此的解释可能是,尽管有效市场假说可能在很长一段时间内成立,但它并不能完全解释证券价格的短期行为。如前所述,行为金融学展示了这样一个事实:股票市场在很大程度上是由非理性投资者决策和经济趋势驱动的;一个恰当的例子是,2020 年 MSFT 股票价格的大幅下跌是由新冠肺炎引起的。因此,在很大程度上,理解股票市场的行为可以被视为一个序列问题。
话说回来,报告的调查结果也有些局限。它只真正调查了一个序列的行为,因此,它不能建立各种其他因素和证券价格之间的关系。因此,如果该模型在未来继续被使用,在面对不可预见的事件时,可能会有许多实例产生完全有缺陷的预测。此外,基于单步时间序列预测模型的研究结果也存在问题。看看多步系列预测模型会产生什么样的结果,以及它将如何回答本报告的研究问题,这将是很有趣的。如果将来要进行任何改进,这两个考虑因素是改进的主要候选因素。
十五天预测(方法到结果)
为了全面总结本报告,从最近的交易日期开始,使用递归多步时间序列预测方法对 MSFT 价格进行十五天预测。选定数字 15 是因为它小于“滚动”(时间步长)值的一半。因此,之前构建的 LSTM 模型使用 MSFT 的所有历史数据进行了重新训练,没有拆分。
***#Creating Inputs/ Outputs Using Whole Test Data**df_final = np.array(scaled_close)x = [] y = []train_amt = 60for i in range(train_amt, len(df_final)): x.append(df_final[i-train_amt:i,0]) y.append(df_final[i,0])x, y = np.array(x), np.array(y)x_shape = x.shape[0]x = np.reshape(x, (x_shape, train_amt, 1))y = np.reshape(y, (-1,1))*
训练完模型后,将创建一个循环,以接受新的单个输出作为未来的输入,并生成后续输出。
***#Projection Set**steps = 15df_final = pd.DataFrame(scaled_close)for x in range (0,steps): data = np.array(df_final[len(df_final)-train_amt + x:]) x_project = np.array(data) x_project_shape = x_project.shape[0] x_project = np.reshape(x_project, (1, -1, 1)) projected_data = pd.DataFrame(lstm_final.predict(x_project)) df_final = df_final.append(projected_data)**#Rescaling the Dataset**df_final = mms.inverse_transform(df_final)*
构造了一个新的函数,增加“n”个新的营业日来预测“n”个价格。
***#Creating a Function For Adding Business Days**import datetimedef add_bdays(from_date, add_days): bdays_add = add_days curr_date = from_date while bdays_add > 0: curr_date += datetime.timedelta(days=1) weekday = curr_date.weekday() if weekday >= 5:
continue bdays_add -= 1return curr_date*
在创建新的远期指数后,将构建一个仅用于价格预测的新数据框架。
***#Creating Date Index With 15 Days Forward**df_date = df[['Date']]start_date = str(df_date['Date'][0])end_date = df_date[‘Date'].iloc[-1]proj_dates = []for x in range(1,steps+1): proj_dates.append(add_bdays(end_date,x))df_proj_dates = pd.DataFrame(proj_dates)df_append_date = df_date['Date'].append(df_proj_dates)date_array = np.array(df_append_date)**#Creating New DataFrame For Forward Dates**df_new = pd.DataFrame(df_final, columns=['Projected Close'])df_new['Date'] = date_arraydf_new.set_index('Date', inplace = True)projected_df = df_new.tail(steps)projected_df*
由此得出的价格预测是:
资源
http://colah.github.io/posts/2015-08-Understanding-
LSTMs/https://machine learning mastery . com/gentle-introduction-long-short-term-memory-networks-experts/
*【http://vision.stanford.edu/pdf/KarpathyICLR2016.pdf *