Web3-的数据科学-全-
Web3 的数据科学(全)
原文:
annas-archive.org/md5/ba7a54fa0e0446c3eff08a0164e548be译者:飞龙
前言
Web3 的到来带来了大量的数据,这些数据具有独特的属性,催生了新概念,并赋予了已有概念新的生命。在广阔的 Web3 生态系统中,数据呈现多样的形式,分布在多个平台和格式上,从链上的交易数据到独立的新闻聚合器、预言机和社交网络等。总的来说,Web3 是一个持续生成与其生态系统直接或间接相关的数据的体系。
Web3 凭借其固有的特性,已在多个领域解锁了价值。去中心化证明了没有中央权威的商业模式是可能的。无信任的互动推动了实体之间的协调,使得即便在陌生人之间、没有中介的情况下,区块链上也能顺利交换商品和服务。这使得价值转移能够以极低的成本覆盖全球的偏远角落,促进了艺术家与收藏家的直接连接,也让众筹得以通过直接支持产品开发者的方式实现,除此之外,还有许多其他应用场景。
然而,Web3 中一个尚未充分探索但却蕴藏巨大价值的方面是透明度。透明度促进了信任,这是大众采用的基石。当普通人能够无缝地与 Web3 互动时,且建立在可信赖的、可验证的信息基础上,这将是行业取得的重要里程碑。为了充分实现透明度的潜力,Web3 的数据科学家和分析师需要具备必要的技能、概念知识、工具,并对数据和商业环境有深刻的理解。这也是本书的目标——赋能你成长为能够理解并从数据中提取价值的 Web3 数据专家。
本书分为三个部分。第一部分涵盖了执行数据分析任务所需的基础概念。你将深入了解链上数据,学习如何访问并提取洞察,探索相关的链外数据源,并解决潜在的障碍。此外,本书还将深入探讨两个产生大量数据的领域——NFT 和 DeFi,它们各自有着独特的业务规则和技术概念。
第二部分将重点转向利用 Web3 数据的机器学习应用场景。我们精选了数据科学家, 无论是自由职业者还是雇佣专业人员,在工作中可能遇到的实际案例。
附录解答了一个问题:我们应该如何利用所获得的知识?它提供了有关如何在去中心化工作环境中导航的指导,帮助理解行业对未来数据员工的期望,并识别成功所需的软技能和硬技能。为了让读者对行业的未来有一瞥,我们与 Web3 数据领域的领袖进行了互动,他们分享了自己的经验、观点和愿景。本部分的目的是缩短找到工作或以其他方式为行业做出贡献所需的时间。
去中心化、无信任交互和贸易透明度的优势不容忽视,这也是该行业年年增长的原因,解锁了新的应用场景并创造了新的就业机会。本书的目的是帮助读者理解 Web3 所产生的数据,使你能够为塑造下一代互联网做好准备。
本书的受众
本书的格式和涵盖的主题使其适合那些对 Web3 生态系统感兴趣的数据专业人士。书中的解释经过简化,面向那些没有数据科学背景但渴望利用数据工具深入分析区块链数据的专业人士。你被鼓励参与共享的代码库,并试验提供的解决方案,从而培养实践学习经验。虽然不是强制要求,但具备基础的统计学、机器学习、SQL 和 Python 知识会更加有利。
本书的内容
第一章,数据与 Web3 的交汇点,介绍了 Web3 和数据科学工具的基本概念。
第二章,使用链上数据,探讨了链上数据的结构。
第三章,使用链外数据,深入探讨了行业相关的链外数据以及如何找到这些数据的指导。
第四章,探索 NFT 的数字独特性——游戏、艺术与身份,研究了 NFT 业务以及如何计算相关指标。
第五章,探索 DeFi 分析,介绍了 DeFi 业务以及如何计算核心指标。
第六章,准备与探索我们的数据,展示了处理 Web3 数据时常用的预处理步骤。
第七章,机器学习与深度学习入门,深入探讨了推进第二部分机器学习案例所需的核心概念。
第八章,情感分析——自然语言处理与加密新闻,探讨了自然语言处理(NLP)在加密情感分析中的应用。
第九章,为 NFT 创作生成艺术,研究了支持 NFT 计划的艺术生成示例。
第十章,安全性与欺诈检测入门,探讨了一种用于欺诈检测的应用。
第十一章,基于时间序列的价格预测,深入探讨了使用时间序列预测价格的应用。
第十二章,使用图表进行营销发现,探讨了一种通过链上数据识别影响者和社区的应用。
第十三章,通过加密数据构建经验 – BUIDL,介绍了 Web3 领域中求职或继续深造的多种选择。
第十四章,与 Web3 数据领袖的访谈,通过深入探讨 Web3 数据领袖对行业及其未来的看法,来总结本书内容。
要充分利用本书
一个 Jupyter 或 Google Colab notebook 就足以覆盖所有示例。在某些情况下,为了访问数据,我们需要注册账户并获得 API 密钥。
| 书中涉及的软件/硬件 | 操作系统要求 |
|---|---|
| Python 3.7+ | Windows、macOS 或 Linux |
| Google Colaboratory 或 Jupyter notebook |
如果您使用的是本书的数字版本,我们建议您自行输入代码或从本书的 GitHub 仓库中获取代码(链接将在下一节提供)。这样可以帮助您避免与复制和粘贴代码相关的潜在错误。
免责声明
本书中所表达的所有观点仅为个人意见,不应视为投资或跟随某一特定策略的诱导。它们仅供参考,不应依赖于做出投资决策。在做出任何投资决策之前,请咨询合格的财务顾问。
下载示例代码文件
您可以从 GitHub 下载本书的示例代码文件,网址为 github.com/PacktPublishing/Data-Science-for-Web3。如果代码有更新,GitHub 仓库会进行更新。
我们还在 github.com/PacktPublishing/ 提供了来自我们丰富的书籍和视频目录中的其他代码包。快去看看吧!
使用的约定
本书中使用了若干文本约定。
文本中的代码:表示文本中的代码词汇、数据库表名、文件夹名称、文件名、文件扩展名、路径名、虚拟 URL、用户输入和 Twitter 用户名。例如:“以下信息来自 CSV 文件,并通过 Betweenness centrality 列进行过滤。”
代码块如下所示:
{'domain': {'id': '131',
'name': 'Unified Twitter Taxonomy',
'description': 'A taxonomy of user interests. '},
'entity': {'id': '913142676819648512',
'name': 'Cryptocurrencies',
'description': 'Cryptocurrency'}},
当我们希望将您的注意力引导到代码块的某个特定部分时,相关的行或项目会以粗体显示:
'annotations': 'annotations': {'start': 10,
'end': 18,
'probability': 0.8568,
'type': 'Organization',
'normalized_text': 'Blackrock'},
任何命令行输入或输出都按以下方式书写:
decompose = seasonal_decompose(df, model= 'additive').plot(observed=True, seasonal=True, trend=True, resid=True, weights=False)
粗体:表示新术语、重要词汇或屏幕上显示的文字。例如,菜单或对话框中的文字通常以粗体显示。以下是一个例子:“一旦我们在 API 页面上填写了必填项,我们就可以按下蓝色的执行按钮,它会返回我们可以使用的 URL。”
提示或重要说明
如此显示。
联系我们
我们始终欢迎读者的反馈。
一般反馈:如果您对本书的任何方面有疑问,请通过邮件联系[customercare@packtpub.com,并在邮件主题中提及书名。
勘误:尽管我们已尽一切努力确保内容的准确性,但错误仍然会发生。如果您发现本书中的任何错误,请报告给我们。请访问www.packtpub.com/support/errata并填写表格。
盗版:如果您在互联网上发现我们作品的任何非法版本,我们将感激您提供相关的链接或网站名称。请通过版权@packt.com 联系我们,并附上该内容的链接。
如果您有兴趣成为作者:如果您在某个领域拥有专业知识,并且有兴趣写书或为书籍贡献内容,请访问authors.packtpub.com。
分享您的想法
阅读完Data Science for Web3后,我们很想听听您的意见!请点击这里直接进入亚马逊的评论页面,分享您的反馈。
您的评价对我们以及技术社区非常重要,帮助我们确保提供优质的内容。
下载本书的免费 PDF 副本
感谢购买本书!
您喜欢随时随地阅读,但又无法随身携带纸质书籍吗?您的电子书购买是否与您选择的设备不兼容?
别担心,现在购买每本 Packt 书籍,您都可以免费获得该书的无 DRM 版 PDF。
在任何地方、任何设备上阅读。直接从您喜爱的技术书籍中搜索、复制并粘贴代码到您的应用程序中。
福利不止这些!您还可以每天通过邮件获取独家折扣、新闻通讯和精彩的免费内容。
按照以下简单步骤获取好处:
- 扫描以下二维码或访问链接:

packt.link/free-ebook/9781837637546
-
提交您的购买凭证。
-
就是这样!我们会直接通过电子邮件将您的免费 PDF 及其他福利发送给您。
第一部分 Web3 数据分析基础
本书的这一部分将探讨 Web3 数据的表现形式,并识别可靠的提取源。在各个章节中,我们将审视最重要协议的业务流程,并学习如何从它们生态系统中生成的数据中获取可操作的洞见。
本部分包括以下章节:
-
第一章**,数据与 Web3 的交汇处
-
第二章**,与链上数据合作
-
第三章**,与链外数据合作
-
第四章**,探索 NFT 的数字独特性——游戏、艺术与身份
-
第五章**,探索 DeFi 中的分析
第一章:数据与 Web3 相遇的地方
由于我们假设读者没有数据或区块链的先验知识,本章将介绍这两个主题的基本概念。充分理解这些概念对于处理 Web3 数据科学项目至关重要,因为我们将在后续内容中提到它们。Web3 数据科学项目旨在通过数据解决商业问题或释放新的价值;它是应用科学的一个例子。它有两个主要组成部分:数据科学成分和区块链成分,这两部分我们将在本章中讲解。
在探索数据成分部分,我们将分析数据科学的概念、可用的数据工具以及我们将遵循的一般步骤,并提供一个轻松的 Python 实践入门。在理解区块链成分部分,我们将介绍区块链是什么,它的主要特性,以及为什么它被称为价值的互联网。
在本章的最后部分,我们将深入探讨一些行业概念及如何使用它们。我们还将分析与数据和概念的质量和标准化相关的挑战。最后,我们将简要回顾 API 的概念,并描述我们将在全书中使用的 API。
在本章中,我们将涵盖以下主题:
-
什么是商业数据科学项目?
-
什么是数据成分?
-
介绍区块链成分
-
接近相关行业指标
-
数据质量和标准化的挑战
-
分类 API
技术要求
我们将使用 Web3.py,这是一款为与基于 EVM 的区块链(如以太坊)交互而设计的库。最初是一个 JavaScript 库,后来它“向着 Python 开发者的需求和习惯舒适度”发展,如其文档所述。Web3.py 是一个简化连接和与区块链交互的库。
如果你以前没有使用过 Web3.py,它可以通过以下代码进行安装:
pip install web3
区块链数据是通过连接到托管在节点上的区块链副本来访问的。Infura 作为云基础设施提供商,简化了我们与以太坊网络的连接,省去了自己运行节点的需求。创建帐户并获取 API 密钥的详细步骤请参见附录 1。
此外,我们将使用Ganache,这是一款能够在计算机上创建本地区块链用于测试和开发的程序。这个工具使我们能够模拟真实区块链的行为,而无需为交互支付真实的加密货币。有关如何使用 Ganache 的详细指南,请参见附录 1\。
你可以在本书的 GitHub 仓库中找到本章的所有数据和代码文件,链接为github.com/PacktPublishing/Data-Science-for-Web3/tree/main/Chapter01。我们建议你通读Chapter01文件夹中的代码文件,以便跟上进度。
探索数据的组成部分
重要提示
如果你有数据科学背景,可以跳过这一部分。
然而,如果你没有相关背景,这一基础介绍对于理解本书中讨论的概念和工具至关重要。
数据科学是一个跨学科领域,它结合了数学、统计学、编程和机器学习与特定学科知识,旨在提取有意义的洞察。
假设你在一家顶级银行工作,该银行正在考虑首次投资区块链协议,他们要求你根据相关指标提出一个投资协议的候选清单。你可能有一些关于应该考虑哪些指标的想法,但你如何知道哪个指标和数值最相关,从而决定哪些协议应该进入候选名单?一旦你确定了指标,如何找到数据并进行计算呢?
这就是数据科学的作用。通过分析交易数据(链上数据)和非链上的数据(链外数据),我们可以识别出有助于我们做出明智决策的模式和洞察。例如,我们可能会发现某些协议在与银行所在时区不同的时间段内更为活跃。在这种情况下,银行可以决定是否准备好投资于服务不同时间区客户的产品。我们还可以检查协议中锁定的价值,以评估普通投资者对该智能合约的信任度,以及其他许多指标。
但数据科学不仅仅是分析过去的数据。我们还可以使用预测建模来预测未来趋势,并将这些趋势纳入我们的评估。例如,我们可以使用机器学习算法基于协议的价格历史预测该协议发行的代币的价格范围。
对于这项数据分析,我们需要合适的工具、技能和业务知识。我们需要知道如何收集和清理数据,如何使用统计技术分析数据,如何分辨哪些数据对业务相关,哪些数据不相关,以及如何将我们的发现可视化以便有效沟通。做出数据驱动的决策是提高所有相关业务指标的最有效方式,而在这个竞争激烈的世界中,这比以往任何时候都更具价值。
由于数据生成速度快且市场上数据科学家稀缺,《哈佛商业评论》将数据科学家称为“21 世纪最性感的职业”。数据经济为多个角色打开了大门,例如数据分析师、数据科学家、数据工程师、数据架构师、商业智能(BI)分析师和机器学习工程师。根据问题的复杂性和数据的规模,我们可以看到他们在一个典型的数据科学项目中扮演着不同的角色。
一个典型的 Web3 数据科学项目包括以下步骤:
-
问题定义:在这个阶段,我们试图回答一个问题,即这个问题是否可以通过数据来解决,如果可以,哪些数据对回答这个问题会有帮助。数据科学家与业务用户之间的协作在定义问题时至关重要,因为后者是专家,是那些将使用数据科学家所产出结果的人。BI 工具,如 Tableau、Looker 和 Power BI,或 Python 数据可视化库,如 Seaborn 和 Matplotlib,在与业务利益相关者的会议中非常有用。值得注意的是,尽管许多 BI 工具目前为常用数据源提供优化包,如 Facebook 广告或 HubSpot,但截至写作时,我尚未看到针对链上数据的优化。因此,最好选择那些高度灵活的数据可视化工具,能够适应任何可视化需求。
-
调查与数据获取:在这个阶段,我们试图回答这样一个问题:我们在哪里可以找到可以用于该项目的必要数据?在本书中,尤其是第二章和第三章,我们将列出多个与 Web3 相关的数据源,帮助回答这个问题。一旦我们找到了数据所在的位置,就需要构建一个数据摄取管道,供数据科学家使用。这个过程被称为ETL,即提取、转换、加载。这些步骤对于将干净且有组织的数据提供给数据分析师或数据科学家是必要的。
数据收集或提取是 ETL 过程的第一步,可以包括手动输入、网页抓取、设备的实时流式传输或与 API 的连接。数据可以以结构化格式呈现,意味着它是以预定义的方式存储的,或以非结构化格式呈现,意味着它没有预定义的存储格式,只是以其本地方式存储。转换包括修改原始数据,以便进行存储或分析。数据转换可能涉及的活动包括数据归一化、数据去重和数据清洗。最后,加载是将转换后的数据移入数据存储并使其可用的过程。在谈到数据可用性时,还需要考虑一些额外的方面,如以正确的格式存储数据、包括所有相关元数据、为合适的团队成员提供正确的访问权限,并确保数据是最新的、准确的或足以满足数据科学家的需求。ETL 过程通常由数据工程师主导,但在确定数据源时,业务所有者和数据科学家也会有发言权。
-
分析/建模:在这个阶段,我们分析数据以提取结论,并可能需要对其建模,尝试预测未来的结果。一旦数据可用,我们可以执行以下操作:
-
描述性分析:这使用数据分析和方法来描述数据展示的内容,深入了解趋势、组成、分布等。例如,对去中心化金融(DeFi)协议的描述性分析可以揭示其客户最活跃的时段以及总价值锁定(TVL)和锁定价值随时间的变化情况。
-
诊断性分析:这使用数据分析解释某些事件发生的原因。这类分析通常采用数据组成、相关性分析和深入挖掘等技术。例如,一位区块链分析师可能会试图理解新地址激增与某些地址活动之间的相关性,以识别这些用户在链上所用的应用。
-
预测性分析:这利用历史数据来预测未来的趋势或事件。技术方法包括机器学习、聚类分析和时间序列预测。例如,一位交易员可能会根据某种加密货币的历史表现,试图预测其未来的走势。
-
规范性分析:这使用预测分析的结果作为输入,建议最佳的响应或最佳行动方案。例如,一个机器人可以建议是否买入或卖出某种加密货币。
-
生成式 AI:这使用机器学习技术和大量数据来学习模式,并生成新的原创输出。人工智能可以创建图像、视频、音频、文本等内容。生成模型的应用包括 ChatGPT、Leonardo AI 和 Midjourney 等。
-
-
评估:在这个阶段,我们的分析或建模结果会被评估和测试,以确认它是否符合项目目标并为企业提供价值。我们会识别出模型中的任何偏差或弱点,如果需要,整个过程将重新开始,以解决这些错误。
-
展示/部署:这个过程的最终阶段取决于问题的性质。如果是一个需要公司做出决策的分析,我们的工作可能会以展示和解释我们的发现为结束。或者,如果我们是作为更大软件管道的一部分工作,我们的模型很可能会被部署或集成到数据管道中。
这是一个迭代过程,这意味着,尤其在步骤 4中,我们常常会从业务团队那里收到有价值的反馈,进而根据反馈调整初步结论。传统数据科学的规律同样适用于 Web3 行业,因为这是一个数据在建立信任、推动投资和一般性地解锁新价值方面发挥关键作用的行业。
尽管数据科学不是一个编程职业,但由于可用的数据量巨大,它在很大程度上依赖于编程。在本书中,我们将使用Python语言和一些SQL来查询数据库。Python 是一种通用编程语言,数据科学社区常用它,它因其简单的语法而容易学习。Python 的替代品是 R,R 是一种统计编程语言,通常用于数据分析、机器学习、科学研究和数据可视化。访问 Python 或 R 及其相关库和工具的一种简单方法是安装 Anaconda 发行版。它包括流行的数据科学库(如 Python 的 NumPy、pandas 和 Matplotlib),并简化了设置环境的过程,以便开始进行数据分析和机器学习项目。
本书中的活动将在三个工作环境中进行:
-
.ipynb格式非常适合用于数据分析或训练模型。在机器学习章节中,我们将使用 Colab 笔记本,因为它为用户提供了免费层次的 GPU 资源。 -
.py格式非常适合用于构建应用程序。大多数 IDE 允许用户下载扩展插件来处理笔记本文件。 -
查询平台:在第二章中,我们将访问具有内置查询系统的链上数据平台。那些平台的例子包括 Dune Analytics、Flipside、Footprint Analytics 和 Increment。
Anaconda Jupyter 笔记本和 IDE 使用我们的计算机资源(如 RAM),而 Google Colaboratory 使用云服务(有关资源的更多信息,请参见附录1)。
请参阅附录1 以安装之前提到的任何环境。
一旦我们有了干净的笔记本,我们将通过Chapter01/Python_warm_up笔记本来热身我们的 Python 技能,该笔记本遵循learnxinyminutes.com/docs/python/的教程。为了更深入学习 Python,我们鼓励你阅读 Packt Publishing 的《Data Science with Python》或《Python Data Science Handbook》,这两本书都列在本章的进一步阅读部分。
一旦我们完成热身练习,我们将使用 Web3.py 库启动 Web3 客户端。让我们在接下来的章节中了解这些概念。
了解区块链成分
如果你有区块链开发背景,可以跳过本节内容。Web3 代表了基于去中心化数据库、无权限和无需信任的互动以及本地支付的下一代万维网。这个互联网的新概念开辟了各种商业可能性,其中一些仍处于早期阶段。

图 1.1 – 网络的演变
目前,我们正处于 Web2 阶段,在这一阶段,集中式公司存储着大量来自我们与应用程序互动的数据。Web3 的承诺是,我们将与去中心化应用(dApps)进行互动,这些应用仅将相关信息存储在区块链上,且所有人都可以访问。
在撰写本文时,Web3 存在一些以以太坊组织为代表的局限性:
-
速度:区块链更新的速度构成了可扩展性挑战。正在测试多个方案以尝试解决这个问题。
-
直觉:与 Web3 互动仍然很难理解。其逻辑和用户体验不如 Web2 直观,且在用户能够大规模使用之前,需要进行大量的教育工作。
-
成本:将整个业务流程记录在链上是昂贵的。作为 dApp 一部分的多个智能合约对开发者和用户来说都花费巨大。
区块链技术是支撑 Web3 的基础技术。它基于分布式账本技术(DLT),该技术在信息经过加密验证后进行存储。一旦记录在账本中,每笔交易都无法修改,并且多个方拥有其完整副本。
该技术的两个结构特征如下:
- 它是由一组区块构成的,每个区块包含关于前一个区块的信息(经过加密哈希处理——我们将在本章进一步了解这一点),使得后期无法修改。每个区块通过这一加密共享机制与前一个区块相链。

图 1.2 – 一组区块的表示
- 它是去中心化的。整个账本的副本分布在多个服务器上,我们称这些服务器为节点。每个节点都有一份完整的账本副本,并且在每次添加新块到区块链上时都会验证一致性。
该结构为双重支付问题提供了解决方案,使得首次通过互联网实现了去中心化的价值转移。这就是为什么 Web3 被称为价值 互联网的原因。
由于完整的账本版本分布在区块链的所有参与者之间,任何与先前存储信息相矛盾的新交易都不会被成功处理(无法达成共识添加它)。这一特性使得不相识的各方能够在无需中介担任担保人角色的情况下进行交易,这就是为什么这项技术被称为无信任技术。
去中心化存储也将控制权从每个服务器中移除,因此,一旦交易被添加到区块链中,就没有单一的权威能够更改任何数据点。由于摧毁一个节点不会影响网络,如果黑客想要攻击数据库,他们将需要极高的计算能力,尝试的成本将变得经济上不可行。这为区块链带来了集中式服务器所没有的安全级别。
三代区块链
第一代区块链是比特币,它基于中本聪的论文《比特币:一种点对点的电子现金系统》。该区块链的主要用途是金融。尽管最初这项技术被视为绕过银行等中介机构的方式,但现在,传统金融系统和加密货币世界开始合作,尤其是在比特币方面,因为它现在被视为一种数字价值储存手段,一种数字黄金。尽管如此,两者系统的整合仍面临许多监管和实际障碍。
第二代区块链在之前描述的数据库结构中加入了智能合约的概念,以太坊是第一个引入这一概念的区块链。通过以太坊,用户可以在交易执行之前就达成协议条款。这个链开启了智能合约的时代,正如尼克·萨博所描述的,智能合约的逻辑就像自动售货机,可以自主执行代码,包括数字资产的管理,这是一场真正的革命。为了实现这一点,网络中有一个以太坊虚拟机(EVM),它可以执行任意代码。
最后,第三代区块链是在前两代区块链的基础上进行构建,旨在解决可扩展性和互操作性问题。本书中提到的链上数据,指的是由第二代和第三代区块链生成的、与 EVM 兼容的数据,因为在本书写作时,这正是大多数开发工作进行的地方(例如,以太坊、BSC 或 Rootstock)。因此,比特币数据和非 EVM 结构不在讨论范围内。
引入区块链要素
现在,让我们来了解一些与区块链相关的重要附加概念。
Gas(燃料)
为了让汽车前进,我们使用汽油作为燃料。这使我们能够到达期望的目的地,但也需要付出代价。汽油价格根据油价和运输成本等因素波动。区块链技术中也有类似的概念。为了在链上保存一个交易,必须支付一定的燃气费用。简而言之,燃气是支付给网络的指令费用,用以执行我们的交易。建立这种费用的目的有两个:一是燃气费用支付给矿工/验证者,作为他们服务的报酬,并激励他们继续融入区块链;二是为用户设定一个费用标准,使他们在使用资源时更加谨慎,鼓励区块链只记录那些价值高于支付燃气费用的内容。本书中我们将学习的所有网络都适用这一概念。
燃气费用具有多重成本含义。由于燃气费用是用网络的原生币支付的,如果价格上涨,使用网络的成本可能变得过于昂贵,从而抑制了其采用。这正是以太坊所经历的情况,导致它对内部规则进行了多次更改,以解决这一问题。
如前所述,每次与区块链的互动都会产生费用。因此,并不是所有内容都需要存储在区块链中,采用这种数据库(区块链)需要根据业务需求进行验证。
加密货币可以被划分为更小的单位,就像美元可以划分为美分一样。比特币的最小单位是 Satoshi,以太坊的最小单位是 Wei。以下是一个单位和面值的表格,便于跟踪燃气费用。
| 单位名称 | Wei | Ether |
|---|---|---|
| Wei | 1 | 10-18 |
| Kwei | 1,000 | 10-15 |
| Mwei | 1,000,000 | 10-12 |
| Gwei | 1,000,000,000 | 10-9 |
| 微以太 | 1,000,000,000,000 | 10-6 |
| Milliether | 1,000,000,000,000,000 | 10-3 |
| Ether | 1,000,000,000,000,000,000 | 1 |
表 1.1 – 单位面值及其数值
地址
当我们使用除现金之外的支付方式时,我们传输一串字母或数字,或两者的组合,以便转移我们的资金。这串字符对于识别收款方的国家、银行和账户,以及持有我们资金的实体至关重要。类似地,地址执行了相似的功能,并作为区块链上的标识号码。它是一串字母和数字,可以发送或接收加密货币。例如,以太坊地址由 42 个十六进制字符组成。地址是一个非对称密钥对的公钥哈希,它包含了第三方转移加密货币所需的所有信息。这个公钥是从私钥派生的,但反向过程(从公钥推导私钥)是不可执行的。私钥用于授权/签署交易或访问存储在账户中的资金。
地址可以分为两类:外部拥有地址(EOA)和合约账户。它们都可以接收、持有和发送资金,并与智能合约交互。EOA 由持有私钥的用户拥有,用户可以根据需要创建任意数量的 EOA。合约账户是部署了智能合约的地址,并由合约代码控制。它们之间的另一个区别是创建成本。创建 EOA 不需要支付 gas 费用,而创建智能合约地址需要支付 gas 费用。只有 EOA 账户能够发起交易。
市场上还有一种产品,叫做智能账户,它利用了账户抽象概念。该开发背后的理念是方便用户在账户中编程更多的安全性和更好的用户体验,例如设置每日消费限额或选择支付 gas 的代币。这些都是可编程的智能合约。
尽管“钱包”和“地址”这两个术语常常互换使用,但它们之间存在技术上的区别。如前所述,地址是非对称密钥对的公钥哈希。另一方面,钱包是存储公钥和私钥的抽象位置。它是一个简化与网络交互的软件接口或应用程序,便于查询账户、签署交易等。
共识协议
当多个方一起合作时,特别是当他们彼此不认识时,需要达成一套可持续工作的规则。在区块链的情况下,需要确定如何将交易添加到区块中并改变其状态。这就是共识协议的作用所在。共识是指区块链所有节点达成一致,通过向链中添加新区块来改变链的状态。协议包含一套参与规则、奖励/惩罚以对齐激励机制等内容。参与的节点越多,网络越去中心化,安全性也越高。
共识可以通过几种方式达成,但在开放网络中存在两个主要概念。
工作量证明(PoW)
这是比特币使用的共识协议。它涉及解决数学方程,方程的难度取决于网络的拥堵程度。
解决这些谜题消耗大量能源,导致硬件密集型竞争。试图解决谜题的各方被称为矿工。
胜利方找到符合方程规则的整数并通知其他节点答案。其他方验证答案是否正确,并将该区块添加到他们的区块链副本中。胜利方因解决谜题而获得奖励,这是一种预定数量的加密货币。这就是系统发行从未被花费的比特币的方式,称为 Coinbase 交易。
在比特币协议中,奖励每 21,000 个区块减半。
权益证明(PoS)
这是以太坊区块链(截至 2022 年 9 月 15 日,共识协议为 PoW)以及许多其他区块链(如 Cardano)目前使用的协议。
PoS 背后的原理是,参与方通过将自己的加密货币抵押在区块链中,获得验证交易、更新区块链并赚取奖励的机会。通常,成为验证者需要抵押一定数量的加密货币。之所以称为“在押”,是因为规则包括对验证者(处理交易并向区块链添加新区块的节点)如果离线或行为不当时的潜在处罚或“削减”。削减意味着失去一部分存入的加密货币。
正如我们所看到的,通过奖励和处罚机制,所有参与者的激励得以对齐,朝着单一版本的区块链发展。
共识协议的列表在不断发展,反映了人们为解决 Web3 中的一些局限性(如速度或成本)而持续努力的过程。一些替代的共识协议包括权威证明(Proof of Authority)——在这种协议下,少数节点有权验证交易并将区块添加到区块链中——以及空间证明(Proof of Space)——它利用磁盘空间来验证交易。
进行第一次交易
有了这些概念后,我们现在将在本地环境中使用 Ganache 中的本地以太坊执行一笔交易。
首先,让我们打开一个本地的 Jupyter 笔记本,并启动 Ganache 的快速入门版本。
这里是我们需要的信息:

图 1.3 – Ganache 主页面及连接所需的相关信息
让我们看一下代码:
-
导入 Web3.py 库:
from web3 import Web3 -
连接到在我们 Ganache 页面(第 1 项)中描述的端口上运行的区块链:
ganache_url= "http://127.0.0.1:8545" web3= Web3(Web3.HTTPProvider(ganache_url)) -
定义接收和发送地址(第 2 项):
from_account="0xd5eAc5e5f45ddFCC698b0aD27C52Ba55b98F5653" to_account= "0xFfd597CE52103B287Efa55a6e6e0933dff314C63" -
定义交易。在这种情况下,我们将在先前定义的账户之间转移 30 个以太币:
transaction= web3.eth.send_transaction({ 'to': to_account, 'from': from_account, 'value': web3.toWei(30, "ether") }) -
我们可以通过以下代码片段查看交易前后的账户余额:
web3.fromWei(web3.eth.getBalance(from_account),'ether')) web3.fromWei (web3.eth.getBalance(to_account), 'ether'))
恭喜!如果你从未在区块链上转移过价值,那么你已经达成了第一个里程碑。完整的代码可以在Chapter01/First_transaction中找到。
关于 CBDC 的说明
什么是CBDC?这个缩写代表中央银行数字货币。它是一种由各国中央银行发行的全新形式的电子货币。
很多国家在这一发展路线图中处于不同的阶段。2022 年 1 月 20 日,美国联邦储备委员会发布了关于 CBDC 的讨论文件,在 COVID-19 疫情之前,他们还通报了关于 CBDC 可能带给系统的益处的持续研究。截至 2022 年 7 月,已有 100 种 CBDC 处于研究和开发阶段。各国正在寻找最佳的基础设施,研究其对社区的影响,并且关注这种新的价值转移方式可能给金融系统带来的新风险,这些系统可能对变革持保守态度。
我们在本章中介绍的一些概念将对 CBDC 时代有用,但根据项目及其特点,并非所有概念都会出现。特别有趣的是,看看它们如何解决集中化问题。以下链接提供了一个非常有用的项目状态追踪器:cbdctracker.org/。
在本节中,我们分析了区块链技术的基础,包括燃气费、地址和共识协议等关键概念,并探讨了 Web3 的演变。我们还使用 Ganache 和 Web3.py 执行了一笔交易。
在对交易流有了基础理解后,我们现在将重点转向分析初始指标,并更好地理解这一行业中的数据挑战。
接近 Web3 行业指标
在本节中,我们回顾了一些在每个 Web3 仪表板中都非常标准的指标。然而,这仅仅是一个基础层次,每个行业参与者都会添加与其相关的额外指标。
为了从以太坊区块链中提取信息,我们需要通过一个节点建立与区块链的连接,该节点持有区块链的副本。有多种方式可以连接到区块链,我们将在第二章中更详细地探讨这个问题。对于以下指标,我们将使用Infura。有关如何连接到 Infura 的逐步指南,请参阅 附录 1。
区块高度
这指的是区块链上的当前区块。创世区块通常被称为区块 0,之后的区块按顺序编号。要检查区块高度,可以使用以下代码片段:
web3.eth.blockNumber
区块号可以作为区块的 ID。追踪它有助于确定交易已获得多少次确认,这相当于在感兴趣的区块之后开采或添加了多少个附加区块。交易在链上的位置越深,安全性和不可逆性越高。
时间
在讨论区块链中的时间时,需要考虑两个概念。第一个是区块之间的时间间隔,这取决于区块链的不同。在以太坊中,经过最近的协议更改,每个时间段为 12 秒。每个验证者都在这段时间内获得一个插槽来提议一个区块,如果所有验证者都在线,将不会有空白插槽,从而每 12 秒就会添加一个新区块。第二个概念是区块被添加到区块链时的时间戳,通常以 Unix 时间戳格式存储。Unix 时间戳是一种追踪时间流逝的方式,记录自 1970 年 1 月 1 日(UTC 时间)以来的秒数总和。
要提取区块时间戳,请使用以下代码片段:
web3.eth.get_block(latest).timestamp
代币经济学
代币经济学指的是区块链上代币项目内部经济的特征,包括供应、需求和通货膨胀。这涉及到确定将发行多少数字资产,是否对总量有所限制,代币的使用场景,以及控制流通资产数量的销毁机制。
代币白皮书通常包含了关于基本代币经济学问题的官方解释。
比特币代币经济学
比特币的供应量被限制为 2100 万个比特币,这一数量不能超过。新的比特币通过挖矿进入流通,矿工每次成功添加一个区块到链上时都会获得奖励。
每个区块大约每 10 分钟挖掘一次,因此到 2140 年,所有 2100 万个比特币将全部流通。
每挖掘 210,000 个区块,获得的比特币奖励数量就会减半,这样每大约四年就会发生一次减半。直到所有 2100 万个比特币被挖掘完毕,矿工将不再收到区块奖励,而将完全依赖交易费用来获得收入。
代币,因此它们的代币经济学,在去中心化金融(DeFi)平台的运作和可持续性中起着基础性作用。受此技术影响最大的行业之一是金融行业,它催生了一个新的概念,即去中心化金融,或称DeFi。DeFi 由建立在公共区块链上的点对点金融解决方案组成。这些计划提供类似银行及其他金融机构的服务,如存款利息、贷款和资产交易,且无需银行或其他中心化金融机构的介入。通过一套开放的智能合约(或协议),任何拥有地址的人都可以参与其中。
DeFi 的一个具体例子是 Aave,这是一个借贷平台,允许用户在没有银行等中介的情况下借贷各种加密货币。例如,如果 Jane 想要借 10 个 ETH,她可以去 Aave,创建借贷请求,并等待智能合约将她的请求与愿意借出 ETH 的可用借款人匹配。借出的 ETH 会按照反映供需水平的利率借出。借出的资金来自一个流动性池,借款人将他们的加密货币存入该池以赚取利息。通过 Aave 的去中心化平台,借款人和贷方可以直接交易,无需通过传统金融机构。
我们将在第五章深入探讨 DeFi。
锁仓总值(TVL)
TVL 是指当前在特定 DeFi 协议中锁仓的资产总值。它通过用户在协议中存入的资金量来衡量某个协议的健康状况。当用户在协议中存入更多资产时,TVL 会增加;反之,当用户取出资产时,TVL 会减少。它的计算方法是将协议中锁仓的资产价值相加,并乘以当前价格。
不同的 DeFi 协议可能有不同的 TVL 计算方式,准确的计算需要了解每个协议的运作方式。一个专门测量 TVL 的网站是 DefiLlama(可访问 defillama.com/)。
TVL 还可以通过将该数字除以该协议发行的代币的市值(或流通中的总供应量)来帮助交易者判断某个代币是否被低估。
这个指标有助于将不同的 DeFi 协议进行比较。
总市值
市值代表某个代币市场的规模,与传统金融概念密切相关。市值的计算方法是将发行的代币数量乘以其当前市场价格。流通供应量是当前由公众持有的代币总和。要获得这个数字,我们需要计算所有不是铸造和销毁地址的地址中的代币,并减去我们已知由协议控制或分配给开发团队或一些投资者的地址所持有的价值。
最大供应量或总供应量是由某个智能合约发行的代币总数。将最大供应量乘以当前价格将得到完全稀释的市值。获取总供应量有两种方法,分别是通过状态数据和交易数据。
在第二章中,我们将学习如何访问状态数据,因为代币的智能合约有一个可以通过 Web3.py 查询的功能。为此,我们需要 Chapter01/Relevant metrics II.ipynb 文件。
另一种访问交易数据库并计算总供应量的方法是通过 SQL 对智能合约的所有铸币事件进行求和,然后减去销毁事件。在第五章中,我们将学习如何做这件事。
市值是动态的,因为随着市场价格和代币供应量的波动,市值也会变化。代币市值在加密货币行业中被广泛用作衡量不同代币表现的基准。
在Chapter01/Relevant metrics II.ipynb中,我们分析了Wrapped BTC(WBTC)代币,这是一个 TVL 和总市值重合的案例,因为该代币与抵押品按 1:1 的比例挂钩。
数据科学家将面临的最大挑战之一是达成共识,定义共同的标准并找到可信的数据源。我们可能对计算复杂金融指标的数学公式有很好的掌握,但如果没有可靠的数据和社区共识的标准,我们传达研究结果的能力将会受到限制。在下一节中,我们将探讨这些挑战并讨论如何克服它们。
数据质量挑战
在本节中,我们将讨论数据质量的挑战,这些挑战不仅仅是 Web3 特有的,而是所有基于数据做出决策的专业人士都需要面对的问题。数据质量的挑战包括从获取不完整、不准确或不一致的数据到数据安全、隐私或治理等问题。然而,Web3 数据分析师将面临的一个最重要的挑战是数据源的可靠性。
例如,市值是通过将两个数据源进行简单乘法运算得出的:区块链数据提供了流通中的代币总供应量,市场价格则提供了相应的价格。然而,这种乘法运算的结果会根据不同的来源而有所不同。让我们以 USDT 的市值为例。在一个来源中,出现了以下信息:

图 1.4 – USDT 市值信息(来源:https://etherscan.io/token/0xdac17f958d2ee523a2206206994597c13d831ec7)
在 CoinMarketCap 网站上,对于同一代币,完全稀释后的市值为 70,158,658,274 美元(https://coinmarketcap.com/currencies/tether/)。
从这个例子中我们可以看到,相同的概念根据我们查看的来源显示方式不同。那么,当我们有多个信息来源时,如何选择呢?
关于区块链活动,最可信和最全面的真实数据来源是节点的完整副本。访问一个节点可以确保我们始终能够访问区块链的最新版本。一些服务会对区块链进行索引,以便方便地访问和查询,比如 Google BigQuery、Covalent 或 Dune,它们会不断更新自己的副本。这些副本是受控制和集中的。
当谈到价格时,有很多来源。获取价格的常见方法是连接到在线加密货币市场,通常称为交易所,如币安或Kraken,以提取它们的市场价格。然而,由于各种原因,这些市场的商业化可能会被暂停。例如,在著名的Terra USD(TUSD)脱钩事件中,当稳定币失去了与美元的 1:1 挂钩时,许多交易所停止了商业化,理由是消费者保护问题。如果我们的工作流程依赖于此类数据,就可能受到干扰或显示不准确的旧价格。为了解决这个问题,建议从多个交易所平均价格的来源获取数据,这样可以提供更强大的信息。
在这一阶段,理解什么构成对我们公司来说的高质量信息至关重要。我们是优先考虑快速且实时更新的信息,还是更注重相对较慢但精准的信息?虽然在每个项目中不一定需要考虑这一点,但决定某些来源并标准化流程将为我们节省未来的时间。
一旦我们确定了要使用的信息质量,我们需要商定我们想要分析的概念。
数据标准挑战
作为一个年轻的行业,许多概念的含义仍没有完全达成共识。让我们来看几个例子。
零售
在加密货币领域,有一个完整的水生生态系统,用于根据地址持有的加密货币数量对其进行分类。较大的地址通常被称为“鲸鱼”,而较小的地址则有自己的名称。请参见以下插图以供参考:

图 1.5 – 加密货币持有量及其水生等价物
尽管在分类中使用的水生等价物有共识,但对于每个类别代表的比特币数量,并没有统一的协议。快速的谷歌搜索会揭示出对于什么构成某一类别的地址标准各不相同。
另一种分类,尤其对于分析师来说非常有价值,是区分零售地址(小投资者)和专业地址。挑战在于确定区分二者的阈值。目前有多种方法可供使用,我们可以遵循前面提到的水生等价物定义,或者采用由一家名为 Chainalysis 的法务公司提出的定义:“零售交易者(…)每次在交易所存入的比特币价值少于 10,000 美元。”
确认
在传统银行或中心化机构中,当用户发送一笔交易时,一旦交易被接收,就会得到确认并视为完成。而在区块链领域,由于网络的去中心化特性,产生了不同的动态,因此,通常需要不同数量的确认,才能将不同金额的交易视为有效。
在去中心化网络中,完全有可能在世界的不同地方同时开采出两个区块。协议会等待下一个区块被挖掘出来,并根据其附加的位置来判断哪条链是最长的(最长的链被视为有效链)。在比特币中,未能成为最长链一部分的区块被称为过时区块,而在以太坊(合并前)中,它们被称为叔块。一旦交易被包含进一个区块,它会被赋予一次确认。如果我们的交易进入了一个过时区块,它将在比特币中被逆转并返回到内存池,或在以太坊中被添加到另一个区块中,重新开始确认计数。
然而,考虑到逆转的可能性,尽管非常小,交易对手方通常会要求在确认交易不可逆转之前,获得一定数量的确认。随着包含我们交易的区块之后链条的增长,交易被逆转的可能性越小。在以太坊合并后(发生在区块15537394),叔块不再生成,但一些做法在市场参与者中依然存在。
对于所需确认数量没有统一标准。建议可能有所不同,有些建议比特币需要六次确认,而小额转账则只需两次确认。对于以太坊,通常的确认次数在 20 次到 40 次之间。值得注意的是,像 Coinbase 这样的中心化交易所仍然可能要求比特币确认两次,或以太坊确认 35 次。

图 1.6 – 过时交易与有效交易
NFT 地板价
NFT 地板价作为一个衡量指标,用于确定集合中任何 NFT 的最低售价,为市场参与者提供有关项目公正定价的宝贵见解。
计算方法没有普遍接受的标准。一个基本的方法是找出在某个集合中,NFT 曾经卖出的最低价格。然而,由于存在多个市场,每个市场有其独特的定价结构,另一种方法是考虑来自最主要艺术市场的价格,或者从多个来源聚合价格,并给重要市场更多的权重。
此外,必须考虑像“洗盘交易”这样的做法,它会人为地夸大所分析的指标。我们将在第四章中进一步分析这一概念。
“丢失”这一概念
假设我们需要计算未来五年内比特币的流通供应量。在这样的计算中,我们不仅要考虑将开采多少比特币,还要考虑有多少比特币可以被视为“丢失”。我们如何确定一定数量的加密货币已丢失?
要在区块链上转移资产,我们需要使用私钥签名该转移。如果该私钥丢失,我们将无法访问这些资产,因此,这些资产必须视为丢失。考虑到这一点,我们可以安全地假设,目前提供的一部分比特币已经丢失或将会丢失。在查看区块链时,我们可以看到某个地址拥有这些资金,但完全有可能该地址无法处置这些资金。由于这是一个伪匿名系统,我们无法联系比特币持有者并询问他们是否可以访问自己的资金;也没有集中式的方式来验证这一点。
名为 Chainalysis 的取证公司提出了“五年内未动过的比特币被视为丢失”这一定义。根据这一定义,20% 的已开采比特币将被视为丢失。这是一个提议的概念,尚需观察它是否成为标准。
总结来说,我们可以达成三种理想的 Web3 数据处理方法:
-
深入了解将在仪表板上展示的指标或将被我们的模型消耗的数据。彻底阅读相关概念和文档。
-
保持开放的心态,寻找同一市场主题的不同处理方式。由于行业还在增长,某些事情还没有固定的做法。
-
准备好见证随着行业成熟和精细化最佳实践,概念的变化。
要了解智能合约的技术方面,OpenZeppelin 文档是一个宝贵的参考。同样,对于市场相关的概念,正如之前提到的,Chainalysis 定义了许多概念,并可以作为起点帮助理解。
API 简要概述
API(应用程序接口)通过一系列请求和响应促进两个软件服务之间的通信。例如,当我们在电话应用中收到有关代币价格下跌的通知时,这意味着我们的应用通过 API 与价格提供者(如 CoinMarketCap)进行通信。为了构造请求以获得所需的响应,我们必须始终参考相关的 API 文档。
为了更全面地理解 API,我们可以参考 Packt 出版社的《Python API 开发基础》一书。由于我们将频繁与 API 交互以提取信息,因此复习不同 API 的主要特性将大有裨益。这将大大帮助我们在编程时访问信息。
为此,我们将重点关注以下内容:
-
远程过程调用(RPC)API:在 RPC API 中,客户端在服务器上启动一个函数,服务器返回输出。实际上,我们将函数的方法(端点)包含在 URL 中,将参数包含在查询字符串中。在这种情况下,客户端需要掌握有关端点的所有信息,有时还需要构建一个包含从其他 URL 查询的信息的工作流。一个用 JSON 格式编码的 RPC API 示例是我们在前面章节中使用的 Infura 套件。
-
GET、POST、PUT或DELETE,服务器响应通常以 JSON 格式返回。一个 REST 请求通常包括 HTTP 方法、端点、头部和主体。端点标识在线资源,头部提供服务器信息,如身份验证,主体包含发送方希望传输到服务器的请求信息。
Facebook 开发了一种替代方法,名为开源查询语言 GraphQL。与前述的 API 最大的区别是,GraphQL 是一种查询语言,而 REST 是一种软件架构概念。GraphQL 是一种数据检索语法,允许客户端指定所需信息,而不像 REST 基础设施那样,查询返回每个端点的固定数据集(有时包括比必要更多的信息)。
GraphQL 的一个显著特点是能够通过单次 API 调用从多个资源中获取数据。Graph 是以 GraphQL 查询的以太坊网络索引器和查询协议,我们将在 第二章 中进一步深入探讨。
总结
在本章中,我们概述了数据科学和 Web3 的概念,涵盖了数据科学项目的典型步骤、Web3 的发展以及共识、地址和 gas 等基本概念。我们还深入探讨了 Web3 这一快速发展的领域中存在的普遍度量和挑战。
在接下来的章节中,我们将深入探讨链上数据,这是 Web3 的主要数据集。我们的探索将包括对区块和交易的详细分析。我们还将讨论访问这些宝贵数据的各种方法。在该章节结束时,你将对链上数据及如何有效地浏览和利用它有一个扎实的理解。
进一步阅读
为了补充本章内容,以下链接可能会有所帮助:
-
数据要素:
-
Python 代码风格指南:
peps.python.org/pep-0008/ -
数据科学与 Python:
www.packtpub.com/product/data-science-with-python/9781789346251 -
Python 数据科学 手册:
jakevdp.github.io/PythonDataScienceHandbook/ -
Web3.py 文档:
web3py.readthedocs.io/en/latest/#
-
-
区块链构成:
-
中本聪的论文:
bitcoin.org/bitcoin.pdf -
Wackerow, P. 等人, 2022. Web2 与 Web3 | ethereum.org. [在线] ethereum.org. 可在
ethereum.org/en/developers/docs/web2-vs-web3/获取 -
Szabo, N., 2022. 智能合约:数字市场的构建模块。 [在线] Fon.hum.uva.nl. 可在
www.fon.hum.uva.nl/rob/Courses/InformationInSpeech/CDROM/Literature/LOTwinterschool2006/szabo.best.vwh.net/smart_contracts_2.xhtml获取 -
Stanley, A., 2022. CBDC 的崛起。 [在线]. 可在 <
www.imf.org/en/Publications/fandd/issues/2022/09/Picture-this-The-ascent-of-CBDCs> 获取 -
Covalent. 2022. Covalent 区块链数据 API 参考 – Covalent [在线]. 可在
www.covalenthq.com/docs/api/#/0/0/USD/1获取。 -
Ethereum-etl.readthedocs.io. 2022. Google BigQuery – Ethereum ETL [在线]. 可在
ethereum-etl.readthedocs.io/en/latest/google-bigquery/获取。
-
相关行业指标:
-
更多关于 gas 费用计算的信息:
growingdata.com.au/how-to-calculate-gas-fees-on-ethereum/ -
智能语料库:以太坊智能合约源代码及 指标的组织化存储库:
arxiv.org/pdf/2011.01723.pdf -
NFT 地板价的演变:
chain.link/education-hub/what-is-an-nft-floor-price -
Team, Chainalysis., 2022. 60%的比特币被长期持有,作为数字黄金。剩下的呢? 可在 <
blog.chainalysis.com/reports/bitcoin-market-data-exchanges-trading/> 获取 [访问时间:2022 年 10 月 12 日] -
Liiv, Innar (2021) 加密货币区块链的数据科学技术。Springer’s Collection on Behaviormetrics: 定量研究人类行为的方法
-
第二章:使用链上数据
在第一章中,我们学习了区块链的基本概念。我们发现区块链是一个分布式账本,由一系列区块组成,每个区块通过加密方式与前一个区块相连。每个区块包含交易信息以及前一个区块的哈希值。此外,交易可以修改以太坊虚拟机(EVM)链上的状态数据。
链上数据代表了每个交易在区块链中的痕迹。它以字节数据的形式存储,需要解析才能变成人类可读的格式。为了说明这一点,下面展示了一段比特币创世区块的原始数据,来源于wiki.bitcoinsv.io/index.php/Genesis_block(许可证:CC BY 3.0):
00000000 01 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
...
00000080 01 04 45 54 68 65 20 54 69 6D 65 73 20 30 33 2F ..Ethe Times 03/
00000090 4A 61 6E 2F 32 30 30 39 20 43 68 61 6E 63 65 6C Jan/2009 Chancel
000000A0 6C 6F 72 20 6F 6E 20 62 72 69 6E 6B 20 6F 66 20 lor on brink of
000000B0 73 65 63 6F 6E 64 20 62 61 69 6C 6F 75 74 20 66 second bailout f
000000C0 s6F 72 20 62 61 6E 6B 73 FF FF FF FF 01 00 F2 05 or banksÿÿÿÿ..ò.
...
00000110 8A 4C 70 2B 6B F1 1D 5F AC 00 00 00 00 ŠLp+kñ._¬
这些数据可以通过提供额外的信息来解析和丰富:
{"hash": "000000000019d6689c085ae165831e934ff763ae46a2a6c172b3f1b60a8ce26f", …, "minerInfo": { "name": "\u0004��\u0000\u001d\u0001\.dat files containing the raw concatenated block data.
Data stored *on-chain* is serialized, so in order to extract valuable insights, we must understand its structure, decode its content, and make it readable. With that in mind, in this chapter, we will delve into blockchain transactions and dissect the anatomy of a transaction. We will examine its essential components, such as sender and recipient addresses, transaction amounts, gas fees, and more. Furthermore, we will focus on the building blocks of a blockchain – the blocks. We will explore the block structure, including the block header, timestamp, difficulty, and nonce.
Additionally, we will delve into blockchain state data, learning how to connect with smart contracts and retrieve contract variables’ values for any block.
Toward the end of the chapter, we will explore popular on-chain data providers and APIs, understanding how to access the exact source that suits our needs, while considering their advantages and disadvantages.
In summary, this chapter will cover the following topics:
* Dissecting a transaction
* Dissecting a block
* Exploring state data
* Reviewing data sources
Technical requirements
In this chapter, we will extensively utilize the `requests` library. This popular and user-friendly Python library simplifies the process of sending HTTP requests and handling responses. HTTP requests form the foundation of client-server communication in web applications and APIs, enabling clients to request specific resources or perform actions on the server, such as data retrieval, creation, modification, and deletion.
If you haven’t installed `requests` yet, you can do so by executing the following command:
pip install requests
The documentation for `requests` is available at the following link: [`requests.readthedocs.io/en/latest/`](https://requests.readthedocs.io/en/latest/).
You can find all the data and code files for this chapter in the book’s GitHub repository, accessible here: [`github.com/PacktPublishing/Data-Science-for-Web3/tree/main/Chapter02`](https://github.com/PacktPublishing/Data-Science-for-Web3/tree/main/Chapter02).
We recommend that you read through the code files in the `Chapter02` folder to follow along with the chapter.
A note on differences between blockchains and databases
Blockchains and databases have architectural differences. We have observed that a blockchain leverages distributed ledger technology while databases operate on a client-server relationship. This fundamental difference has an impact on two aspects: authority and performance. There is no sole server in charge of a blockchain; therefore, to modify anything on it, the nodes will need to reach a consensus, which takes time and results in slower performance. In contrast, databases are highly time-efficient and continue to improve their speed every day.
Another consequence of this relates to the manipulation of stored information. In the case of a blockchain, it is not possible to update a data point that has been added to a block. On the other hand, databases offer **Create, Read, Update, Delete** (**CRUD**) operations, with their only limitation being dependent on admin privileges.
It is worth noting that these characteristics primarily apply to public blockchains. Hybrid blockchains, commonly used for corporate purposes, blur the distinction between traditional databases and blockchains.
Let’s visualize each transaction as a row in the blockchain ledger, and imagine that these rows fill up the pages of a book. Each completed page represents a block containing a collection of transactions. We will start our analysis by studying the data each row contains.
Dissecting a transaction
As data analysts, it’s crucial for us to grasp the unique structure of each blockchain we analyze, as it influences how we search for and interpret information.
For instance, Bitcoin follows a structure based on spent and unspent transactions, while Ethereum operates on an account-based protocol. The underlying structure changes our approach to the data we want to fetch.
In the case of Ethereum, a transaction is a message initiated by an **Externally Owned Account** (**EOA**) that gets recorded on the network. A transaction is the kick-off moment that triggers the Ethereum machinery and leads to a change in its state.
To exemplify the concepts described in the subsequent sections, we will dissect a transaction associated with the `0x1aD91ee08f21bE3dE0BA2ba6918E714dA6B45836` Address. This address belongs to the mining pool named *Hiveon*.
The transaction’s hash is `0x032ed60363beb809a2b9c9790bb7dadd83b743040945a087aeecbe9e6b2dc2af`. By pasting this hash into Etherscan, we can gather more information about the transaction:

Figure 2.1 – Transaction details on Etherscan
Etherscan provides valuable metadata that offers context about when the transaction was executed, helping us understand it with its user-friendly interface.
We will begin by examining the basic transaction data, which consists of the following fields, as extracted in `Chapter01/Transaction.ipynb`:
**Nonce**
|
3460171
|
**Gas Price**
|
0.000000019209576968 Ether (19.209576968 Gwei)
|
**Gas Limit**
|
100000
|
**Recipient**
|
0x3c16183c1C0E28F1a0cB9F8ee4b21D0Db208cA46
|
**Value**
|
48000000000000000000
|
**Data**
|
0x
|
**V,R,S**
|
(1, ‘0x2c1561644259bffe2872ea57690d103b
c57b611c8882ed7f2b5e0bfe40e4c807’, ‘0x4bc9255e7b24d321edd9af354589140 acc7347e35d91fcffde07fb81c27741d8’)
|
Table 2.1 – Transaction information stored on-chain
Let’s delve into the details of each of these fields.
Nonce
A nonce is a cumulative number that keeps track of the total transactions sent by the executing address. Smart contracts also have a nonce that keeps track of the number of contract creations.
The *Ethereum Yellow Paper* defines it as follows: “*nonce: A scalar value equal to the number of transactions sent from this address or, in the case of accounts with associated code, the number of contract-creations made by* *this account.*”
As per the definition, the nonce provides information about the sending address. It serves two purposes:
* It establishes the order of transaction processing for each address. A transaction with a higher nonce number will not be processed until all transactions with smaller nonces have been validated.
* It identifies a transaction. Multiple transactions with the same nonce can be sent to `mempool`, but once a transaction with a particular nonce is added to the blockchain, subsequent transactions with the same nonce will not be processed.
We can extract the next nonce of an address with the following code:
web3.eth.getTransactionCount(address)
The nonce of a specific transaction can be extracted with the following code:
web3.eth.get_transaction(transaction).nonce
The nonce counting starts at zero, so the result of the transaction count always reflects the next available transaction for that specific address. We can refer to the `First transaction` notebook from `Chapter01/First_transaction.ipynb`, specifically the last cell, as a reference:

Figure 2.2 – Screenshot displaying the first nonce of an address
Gas price
Gas price (`gasPrice`, as seen in *Figure 2**.2*) is determined by the sender of the transaction and represents the price they are willing to pay for each unit of gas. Transactions with higher gas prices are prioritized for confirmation. The gas price is denoted in *Wei per unit* *of gas*.
To extract the gas price of a transaction, we can use the following code:
web3.eth.get_transaction(transaction).gasPrice
Gas limit
Gas limit (or `gas`) represents the maximum number of gas units (money invested) that the sender is willing to spend on the transaction. It is the upper limit of gas consumption for a transaction.
To extract the gas limit of a transaction, you can use the following code:
web3.eth.get_transaction(transaction).gas
Recipient
The recipient of a transaction is specified in the `to` parameter, which contains the public address of the recipient. In the case of Ethereum, addresses are 42 characters long (40 hexadecimal characters beginning with `0x`) and can be either an EOA or a smart contract. At the public address level, there is no distinction between the two. On other blockchains, additional information may be required to identify the recipient (for example, a tag ID/memo for EOS transfers).
It is important to note that any combination of characters that meets the technical requirements mentioned in the preceding paragraph will generate a valid transaction. If we send tokens to an address that has no private key, we cannot access those tokens, resulting in them being effectively *burned*. Burning tokens can be a deliberate part of a token’s economy or may occur as a result of a mistake. To address the latter, protocols such as **Ethereum Name Service** (**ENS**) or **RIF Name Service** (**RNS**) have been created, following the idea of traditional DNS. These protocols enable the leasing of human-readable names on the blockchain, which can replace long string addresses.
To extract the `to` field of a transaction, we can use the following code:
web3.eth.get_transaction(transaction).to
Depending on what information this field has, we can classify transactions into these categories:
* **Regular**: A transaction from one address to another address.
* `to` field is `null` and where the `data` field is used for the contract code. In this case, the sender is creating a smart contract.
* `to` field is a smart contract address, and therefore the transaction represents the interaction with a deployed smart contract.
Sender
This is the address that signs the transaction and will be found in the `from` parameter. The address will be an externally-owned account given that contract accounts cannot send transactions.
To extract the `from` field of a transaction, we can use the following code:
web3.eth.get_transaction(transaction).from
The sender address is derived from the signature (the V,R,S letters shown in *Table 2.1*).
Value
The `value` field denotes the quantity of the native currency transferred in the transaction, expressed with the number of decimal places particular to the specific blockchain. In this instance, the value represents Ether and it is expressed with 18 decimal places. In other blockchains, the native currency will vary; for instance, Rootstock Platform (RSK) employs RBTC, while Cardano uses ADA, and so on.
To extract the value and transform it into decimal values, we can use the following code:
value= web3.eth.get_transaction(transaction).value
value*10**-18
The transfer of tokens is not stored in the `value` field; for that information, we need access to the transaction logs.
Input data
The `input data` field contains “*Any extra information required by the transaction*," as defined by the Ethereum documentation. This field is mostly used when interacting with or deploying a smart contract.
When a transaction interacts with a smart contract, the input data comprises the function and parameters necessary for interacting with the contract. This input data adheres to the type format outlined in the smart contract’s **Application Binary Interface** (**ABI**). To decode the data field for our analysis, we will require the ABI.
In the case of a transaction that deploys a contract, the input data field contains the contract bytecode.
To extract the input data of a transaction, we can use the following code:
web3.eth.get_transaction(transaction).input
As you may have noticed, in the transaction we have been analyzing, there is no input data. However, let’s change that for example purposes. Let’s consider a transaction that mints a Bored Ape Yacht Club NFT (“Bored Ape” for future reference). For example, let’s take Bored Ape ID `6633` (as of the day of this writing, held by Neymar Jr.).
We can observe that the minting transaction is hashed as `0xb3827bb3cca1a693ec69edb744755f64d8ff8c90f89f69cbfbfafd17b0083159`.
In this transaction, the `0x9909017A0F637380af916257D05c3e7dD2F6c68a` address interacts with the smart contract at this address: `0xBC4CA0EdA7647A8aB7C2061c2E118A18a936f13D`. This transaction has the following input data: `'input': '``0xa723533e0000000000000000000000000000000000000000000000000000000000000001'`.
This input data holds a meaning in the context of the Bored Ape ABI. An ABI documents the smart contract’s functions, state data, and events. Smart contracts are compiled at the machine code level, and ABIs serve as translators to decode them, as they include each function’s input and return parameters. ABIs enable the readability of all the functions of a smart contract.
In summary, to translate the input data, we need to access the ABI document. One way to do this is by following these steps:
1. Navigate to `https://etherscan.io/address/[smart_contract_address]`; in this case, this is https://etherscan.io/address/0xBC4CA0EdA7647A8aB7C2061c2E118A18a936f13D.
2. Scroll down to the middle of the page and find the horizontal menu. Click on **Contract**:

Figure 2.3 – Contract tab on Etherscan
1. Scroll down and you will find the **Contract** **ABI** Section:

Figure 2.4 – Export ABI option selection
Now, you can copy and paste the ABI in a text or JSON format. Be cautious and delete the initial parts of the text where some metadata from Etherscan’s API is also written, as detailed in the following note. An alternative is to programmatically obtain it by creating a free account with an API key.
Note that, Etherscan adds extra text to the ABI JSON when its official API isn’t used. This text should be removed when incorporating it into our code in Jupyter Notebook.

Figure 2.5 – Text to be deleted from the JSON data
For simplicity purposes, we have also uploaded the Bored Ape ABI to the book’s GitHub repository.
There are alternative tools to retrieve the ABI when the code is not verified. These tools, although still in beta, are listed in the *Further* *reading* section.
With the `decode_function_input` method, we can combine the information from the ABI with the input data text and we will see the decoded version. The step-by-step process can be found in `Chapter02/Transaction`:

Figure 2.6 – The decode_function_input method
As we can see, the `mintApe` function was triggered by this transaction, and Ape 6633 was born. This is a simple function with one parameter, but we need to be prepared for more complex functions, such as swapping contracts, lending, bids, and more.
V,R,S
These are the components of the signature by the `from` address. The digital signature gives validity that the message sent was executed by the originating address. For more on this matter, you can read the *Mastering Ethereum* book. Depending on where we obtain our transaction data, we may not encounter this field (for example, Covalent does not provide it when querying for a specific transaction).
Transaction receipt
Once the transaction is executed, we gain access to a valuable source of information, called a transaction receipt. This receipt stores information that results from executing the transaction.
Of particular interest to us are the following fields: `status`, `gasUsed`, `cumulativeGasUsed`, and `logs`.
Status
The status field can have a value of either 1 or 0\. A value of 1 indicates a successful transaction, while a value of 0 indicates an unsuccessful transaction, leading to the transaction being reverted.
Gas used and Cumulative gas used
The Gas used field represents the amount of gas that was actually consumed by the transaction. This value will be below the gas limit. We can retrieve it with the following code:
web3.eth.getTransactionReceipt (transaction).gasUsed
Additionally, we have the Cumulative gas used field, which provides the total amount of gas consumed by all previous transactions within the same block, including the transaction under analysis.
Gas prices are crucial data points that analysts often consider. These fields represent the actual cost of using the blockchain for a specific transaction. Analyzing gas costs can help answer questions such as: What is the best time of the day to execute a set of transactions? When should we deploy a set of smart contracts to minimize gas expenses?.... and so on.
Logs
Any change on the blockchain can be stored in state data or event logs. The latter is less expensive and provides a very rich source of information. We will analyze state data in the following section.
In the context of smart contract operations, logs are short pieces of information that record specific events at a given point in time.
An event log, or log record, can be created by providing specific instructions to the EVM. These instructions are known as **opcodes**, and there are five opcodes that emit event logs. The *Ethereum Yellow Paper* provides more information about opcodes under the title *Logging operations*.
Log events consist of two components: topics and data. When examining the source code, we will find that log events are preceded by the `event` or `emit` keyword.
**Topics** describe the nature of an event and can include up to a maximum of four topics per log. Typically, topics consist of the event’s signature or name, along with the type of parameters passed.
Topics are searchable but limited in terms of the number of bytes they can include. As a result, the information contained within topics is usually referential. In the context of a Python dictionary, topics can be considered as keys.
**Data**, the other component, has no such limit in terms of number of bytes and is less expensive to store on the blockchain. This allows for more flexibility in the information that can be included, such as larger strings. If we were to compare this with a Python dictionary, data would correspond to the values.
Let’s continue the examination of the minting of Bored Ape 6633\. Depending on the data provider we use to query the blockchain, we may receive the logs already decoded or we might need to decode them ourselves. To be able to decode them, we will need the ABI, as extracted in the previously analyzed *Input data* section. The code essentially compares events from the ABI with events from the log. If there is a match, the code translates the log. In `Chapter02/Transaction.ipynb`, we will see the entire process, which is summarized in the following steps:
1. Creates a list of events from the contract.
2. Generates a hexadecimal value for each event extracted from the ABI.
3. Extracts the receipt for the transaction.
4. Iterates through each log and compares the hexadecimal value of the first parameter of the log (the topic) with the list created in *step 2*. If there is a match, the code uses the name within the `processReceipt` function, and it will return a tuple with the decoded logs.
In the Bored Ape transaction under analysis, the log contains some interesting information. It provides details about the minting of the NFT, the original holder, and the corresponding ID. We can use the ID to view the information in the gallery using the **BY ID** search filter ([`boredapeyachtclub.com/#/gallery`](https://boredapeyachtclub.com/#/gallery)).
We have reviewed the main components of a transaction and the information they provide; we now shift our focus to the next vital element of the blockchain ecosystem: the block. As transactions are the purpose of a blockchain, blocks serve as the foundational units that bring together multiple transactions, creating a comprehensive ledger of activity.
Dissecting a block
A block is formed by combining a list of transactions with a header. As depicted in the flow diagram in *Figure 2**.7*, when transactions are added to a block, they alter the state of the blockchain:

Figure 2.7 – How a blockchain evolves (adapted from https://ethereum.org/en/developers/docs/blocks)
The preceding diagram illustrates the progressive evolution of blockchain state data, one block at a time. Blocks are strictly ordered, allowing us to trace the history of each state variation.
In the *Ethereum Yellow Paper*, a block is defined as “*the collection of relevant pieces of information (known as block header) [...], together with information corresponding to the comprised transactions, [...] and a set of other block headers [...] that are known to have a parent equal to the present’s block’s parent (such blocks are known* *as ommers).*”
Therefore, a block consists of three main components:
* A block header
* A list of transactions
* An uncle block header
Uncle blocks refer to blocks that were mined simultaneously. Since the Merge on September 15, 2022, when the Ethereum network transitioned from **Proof-of-Work** (**PoW**) to **Proof-of-Stake** (**PoS**) consensus, the uncle block header is now empty as uncle blocks no longer occur.
Let’s begin by understanding the information provided by the block header. For explanatory purposes, let’s consider block `15813288`. If we want to review the Etherscan version, we can access it through the following URL: https://etherscan.io/block/15813288.
In `Chapter02/Block.ipynb`, we programmatically access it, and we can observe the following fields:
`parentHash`
|
0x9b930569ef6794eb018d54d6a0768f4445f757d62ddffa79698cd5c1fea04b31
|
`beneficiary`
|
0x690B9A9E9aa1C9dB991C7721a92d351Db4FaC990
|
`stateRoot`
|
0x91c1b2292997a9aa87aa7bf75b387df4bc5a6869fa83b3ce9d4c6793d3acaaa1
|
`transactionsRoot`
|
0x7896f544f241e7aa3bae8e3f70b45d9db34794ddb60187c1d46dd80958ea3e41
|
`receiptsRoot`
|
0x6698a263fd7b24a301e1060c624e7aa7510db8d4d215779ee43ebe8f5c18889a
|
`difficulty`
|
0
|
`totalDifficulty`
|
58750003716598352816469
|
`number`
|
15813288
|
`size`
|
63648
|
`gasLimit`
|
30000000
|
`gasUsed`
|
13247169
|
`baseFeePerGas`
|
15649778689
|
`timestamp`
|
1666557983
|
`extraData`
|
0x406275696c64657230783639
|
`nonce`
|
0x0000000000000000
|
`transactions`
|
List of 112 transactions
|
Table 2.2 – 15813288 block information
Let’s understand what information each field comprises:
* `parentHash`: This is the hash of the previous block, establishing a link between blocks in the blockchain and providing historical order to the network.
* `beneficiary`: This field indicates the address of the miner or validator who successfully added the block to the chain and received rewards and fees.
* `stateRoot`/`transactionRoot`/`receiptsRoot`: These fields provide the hash of the trie structure containing information related to the modified state, transactions, and transaction receipts. A Merkle Patricia Trie is an internal structure utilized by Ethereum to expedite data retrieval.
* `difficulty` and `totalDifficulty`: `difficulty` represents the level of mining difficulty required for this block. `totalDifficulty` denotes the cumulative difficulty of the entire blockchain up to the specific block. These features changed after the Merge as they were associated with the previous PoW consensus. `totalDifficulty` has remained unchanged since the transition, and `difficulty` was set to zero. Refer to block `15537393` to have a look at the last block mined using PoW.
* `number`: This indicates the block height, as discussed in *Chapter 1*, following a sequential order of blocks. The genesis block, mined in July 2015, holds the block number 0.
* `size`: This denotes the data storage capacity of a block in bytes, with the limit imposed by the required gas for validation.
* `gasLimit`/`gasUsed`: `gasLimit` represents the maximum amount of gas allowed to be expended in the block, while `gasUsed` indicates the total gas consumed by all transactions within the analyzed block. If `gasUsed` if below `gasLimit`, we can observe that blocks are not fully utilized, leaving idle space.
* `baseFeePerGas`: This field represents the reserve price or minimum price required for a transaction to ensure its inclusion in a block. The calculation is based on previous blocks, aiming to provide more predictability for gas costs to end users.
* `timestamp`: This denotes the Unix timestamp at the time the block was mined, representing the cumulative number of seconds elapsed since January 1, 1970.
* `extraData`: This arbitrary array contains data relevant to the specific block. It was previously written by miners and is now populated by validators.
* `nonce`: Short for “number used only once,” this field is a number added to the block that must generate a hash meeting the difficulty criteria. It is still used in Bitcoin to regulate difficulty. After the merge in Ethereum, this number was set to 0.
* `transactions`: This field returns a list of transactions added to the block; in the example under analysis, this is 112 transactions. The following code snippet provides a list of each transaction, along with the information reviewed in the previous section:
```
web3.eth.getBlock(block_identifier=15813288).transactions
```py
Analyzing block data is very useful when trying to grasp a general overview of the chain under analysis. Aggregating the data from the fields detailed previously, we are able to answer questions about how a chain is used, the average transaction per block, the time between blocks, how expensive the base fee is, and so on.
Having examined the structure and components of a transaction and a block in detail, we now shift our focus to the state data within the Ethereum blockchain. State data encompasses the current state of all accounts, contracts, and smart contracts on the network, reflecting the outcome of executed transactions and operations. It serves as a fundamental building block for the blockchain’s functionality and provides a comprehensive snapshot of the system at any given point in time.
Exploring state data
In the *Ethereum Yellow Paper*, the state, also known as the world state, is defined as “*a mapping between addresses and account states.*” Up to this point, we have been discussing transactional data that is permanent, meaning that once incorporated into the blockchain, it cannot be changed. Unlike transactional data, the state is dynamic and evolves with each new block.
To ensure accessibility for users interacting with accounts and contracts, Ethereum employs **trie** data structures. Specifically, the state trie contains key-value pairs for every existing account that has engaged in a valid transaction. The key represents the Ethereum account’s address, while the value comprises hashed information encompassing the account balance, nonce, code, and storage root.
The concept of roots leads us to an explanation of tries and the special implementation of the **Merkle Patricia Trie** on Ethereum (that exceeds the scope of this work). We will briefly mention that the trie structure or search tree is used for storing and searching a key in a set. It facilitates the searching, adding, and deleting complexities for sequences of characters. The trie starts with a root and connects characters in its branches. We have seen roots in our previous analysis: the state, transaction, and receipt’s roots hashes are part of the block information. The state root, together with additional information, is stored as the value of the address.
For a more in-depth understanding, please refer to the cited documentation in the *Further* *reading* section.
Why is this useful for data analysis?
The storage of state data in this manner enables us to easily retrieve the blockchain’s status at specific points in time—a capability leveraged by smart contracts.
To illustrate this, let’s consider the Bored Ape smart contract we examined earlier.
On the Jupyter notebook on `Chapter02/State.ipynb`, do the following:
1. Upload the ABI following the instructions outlined in the *Dissecting a* *transaction* section.
2. With the following code, we will gain access to all the contract’s functions:
baContract.all_functions()
We can see that each function tells us which parameter it needs to be able to execute the query. For example, `<Function ownerOf(uint256)>` tells us that it needs an integer, which in the context of this example is the Bored Ape ID under analysis: 6633.
The code will be as follows:
baContract.functions.ownerOf(6633).call()
After executing this cell, we will see that the current owner of the Bored Ape ID is `0xC4505dB8CC490767fA6f4b6f0F2bDd668B357A5D`. If no `block_identifier` parameter is specified, the call retrieves the current state data, assuming `latest` as the default value.
Let’s imagine that we want to know who was the previous owner of the Bored Ape 6633 ID. In that case, we would need to provide in the `block_identifier` parameter the number of the block previous to the transfer to the current owner occurring. In the case of Bored Ape 6633, the transfer took place in block `14044022`, so we query the state of the blockchain at block `14044021` with the following code:
baContract.functions.ownerOf(6633).call(block_identifier=14044021)
The result is that the previous owner was `0xDE2b87d1539904f4b37E98C0d5CE383E890006eF`. An alternative is using Etherscan’s **Read Contract** function, which will only respond with the current state data.
The steps are the following:
1. Paste and search the smart contract address on Etherscan:

Figure 2.8 – Etherscan search bar
1. Navigate to the **Contract** tab, shown in *Figure 2**.3*.
2. Click on the **Read** **Contract** tab:

Figure 2.9 – Read Contract tab
1. Locate the relevant function; in this case, the `ownerOf` function:

Figure 2.10 – ownerOf function
1. Add `6633` to it and click on **Query**. The response provides the current owner of Bored Ape ID 6633:

Figure 2.11 – Response to function execution
This approach is useful for extracting state data really fast.
After studying state data and understanding its significance, the next step is to gain access to on-chain data for practical use. In the following section, we will explore multiple data sources and learn to connect with them.
Reviewing data sources
Alice: Would you tell me, please, which way I ought to go from here?
The Cheshire Cat: That depends a good deal on where you want to get to.- Lewis Carroll, Alice in Wonderland
We will encounter a similar dilemma to Alice’s when trying to access *on-chain* data without context or a clear vision of the needs and resources that are at our disposal.
The choice of a data source relies on various factors, primarily driven by our needs and available resources. As discussed in *Chapter 1*, our approach to blockchain data will be shaped by the problems we aim to solve and the questions we seek to answer. If we need to add to a dashboard aggregated metrics that involve comprehensive scanning of the entire blockchain, we will need access to SQL-based solutions. On the other hand, integrating specific data points, such as balances or token prices, into our platform may lead us toward extracting information from a node with `web3.py`.
Additionally, each data source carries its own set of costs and levels of flexibility. The expertise of the data scientists responsible for managing these resources also influences our decision-making process. Options ranging from traditional SQL-based datasets to MongoDB and GraphQL are at our disposal.
Importantly, our decision must consider whether integration of on-chain data with off-chain data is necessary, and the ease with which it can be achieved. Seamlessly merging these two worlds should be taken into account. A website that gives us continuous updates is [primodata.org/blockchain_data](http://primodata.org/blockchain_data), which is maintained by the X account, [twitter.org/primodata](http://twitter.org/primodata).
Let us now present some available options, bearing in mind that this list requires periodic updates to keep pace with the ever-evolving landscape. We test each of the alternatives in `Chapter02/Data Sources.ipynb`.
Block explorers
A block explorer is a user-friendly tool that provides detailed analytics about a blockchain network. For Ethereum, we have been interacting with Etherscan ([`etherscan.io/`](https://etherscan.io/)), and for RSK, Rootstock ([`rootstock.blockscout.com/`](https://rootstock.blockscout.com/)) among many other examples . A block explorer acts as a search engine and browser where users can find information about individual blocks, public addresses, and transactions associated with a specific cryptocurrency. Each chain has its own block explorer. Of all the sources described here, this is the only one that is widely used by blockchain enthusiasts and everyday users to explore and monitor the activities happening on a blockchain network.
Infura
Infura is one of the providers that we have utilized throughout the book’s exercises and examples. It offers API access over HTTPS and WebSockets to a node, making it accessible for querying through clients such as `web3.py` or `web3.js`.
For more detailed information, please visit [`blog.infura.io/post/getting-started-with-infura-28e41844cc89`](https://blog.infura.io/post/getting-started-with-infura-28e41844cc89).
Additionally, a comprehensive step-by-step guide on how to start interacting with this source can be found in *Appendix 1*. It’s important to note that the node provided by Infura is situated within a developer suite specifically designed for dApp development. Consequently, the most effective approach to accessing this dataset is through programming languages such as Python or Java. The API’s response is in the widely used JSON format.
Moralis
Similar to Infura, Moralis is considered part of a developer suite for blockchain developers. It indexes EVM-based chains and Solana, but what sets it apart is its advanced features, including pre-built queries that enable cross-analysis. Accessing Moralis requires an API key, and the response data is in JSON format.
For more detailed information, please visit [`docs.moralis.io/docs/quickstart`](https://docs.moralis.io/docs/quickstart).
GetBlock
GetBlock is another **node as-a-service** (**NaaS**) provider, similar to Infura. However, Getblock offers access to a broader range of chains compared to Infura and Moralis. To use GetBlock, you’ll need to set up an account, and the response from the API will be in JSON format.
For more detailed information, please visit [`getblock.io/`](https://getblock.io/).
Dune
Dune is an excellent web-based data analysis tool for creating interactive dashboards and charts. It offers both free and premium versions, with the latter allowing the creation of private dashboards. The data is indexed at various stages of decoding, ranging from raw Ethereum data to tables enriched with extensive metadata contributed by the community. One notable aspect is the platform’s commitment to knowledge sharing, as queries and dashboards are openly accessible to everyone.
If we want to see how a query was built, we have to click on the title of the metric, as shown in *Figure 2**.12*, and it will open the query space with the relevant query. Dune Analytics uses the DuneSQL query engine, based on Trino:

Figure 2.12 – Dune Analytics access to query
Additionally, Dune Analytics provides valuable resources such as tutorials, documentation, and a forum to support users on their analytical journey.
For more detailed information, please visit [`dune.com/docs`](https://dune.com/docs).
Covalent
Covalent is another API that necessitates users to create an account and acquire API keys. The company has indexed over 40 chains and consistently updates the data with minimal delay compared to the node. Similar to Infura, interaction with Covalent’s API follows a programmatic approach, and the response is in JSON format. Covalent provides a range of pre-defined basic endpoints that are valuable for data scientists. Furthermore, certain on-chain data endpoints offer enriched information, such as prices or 24-hour aggregations of specific metrics. For more detailed information, please visit [`www.covalenthq.com/platform/#/auth/register/`](https://www.covalenthq.com/platform/#/auth/register/).
Notably, Covalent is currently developing a new **business intelligence** (**BI**) product called **Increment**, which offers greater flexibility. Increment is a comprehensive database encompassing all the indexed chains (EVM compatible), enabling users to query the data using SQL or a simple no-code drag-and-drop system. The database contains all the data generated by all chains collectively, recognizing the growing number of blockchains and the necessity for companies to monitor users and value across multiple chains. Increment’s unified database provides a convenient solution for this purpose. It’s important to note that certain information stored in this database is encoded in hexadecimal format, including addresses, transaction input data, and transaction value. To access Increment, please visit [`www.covalenthq.com/platform/#/increment/`](https://www.covalenthq.com/platform/#/increment/) and create an account.
Once we have access, we will notice that there are dashboards built by the community. If we come across a metric of interest and wish to understand how a query was constructed, click on the dots of the metric, select **Go to SQL**, and it will open the SQL builder on a separate page with the logic:

Figure 2.13 – Increment access to query
Flipside
Flipside is another excellent provider that allows us to query on-chain tables using SQL for multiple chains, including some external tables maintained by market authorities such as DefiLlama for **Total Value** **Locked** (**TVL**).
Flipside offers two main products. The first one is Flipside Data Studio ([`www.flipsidecrypto.xyz/`](https://www.flipsidecrypto.xyz/)), which enables dashboard visualizations in a social network environment with an impressive community. All the queries are open, and analysts compete to create useful dashboards for the community.
The other product is the Flipside API ([`flipsidecrypto.xyz`](http://flipsidecrypto.xyz)), which allows us to submit queries directly from our developer environment. This service, included in the free tier, enables us to query the database and retrieve results that we can ingest in our systems, internal dashboards, and so on.
To use Flipside, we need to create an account and obtain the necessary API keys. For more detailed information, please visit [`docs.flipsidecrypto.com/`](https://docs.flipsidecrypto.com/).
The Graph
The Graph is based on GraphQL and is primarily focused on smart contracts. Currently, subgraphs are limited to the Ethereum blockchain. Subgraphs allow access to the ecosystem created by a specific protocol rather than the entire blockchain. It operates in a decentralized and collaborative manner to index blockchain information, with various roles such as **Developer**, **Indexer**, **Curator**, and **Delegator**, each incentivized to participate.
Queries can be accessed through a URL, making integration into our apps possible. It is particularly interesting that each subgraph comes with its own documentation and a playground where we can test our queries.
Numerous projects are actively developing subgraphs to facilitate decentralized access to their data. At present, I have come across ENS, Sablier, and Superfluid are examples of projects maintaining subgraphs on this service.
To test our queries, we can use the online playground, which requires creating an account and connecting our wallet to obtain the necessary API keys:

Figure 2.14 – Screenshot of The Graph’s playground
For more detailed information, please visit [`thegraph.com/explorer`](https://thegraph.com/explorer).
Google BigQuery
Google BigQuery maintains a table indexing for both the Ethereum and Bitcoin chains. You can access the data using Google Cloud. A limited tier is accessible through the Kaggle website. To access the data, please visit [`bigquery.cloud.google.com/dataset/bigquery-public-data:crypto_ethereum`](https://bigquery.cloud.google.com/dataset/bigquery-public-data:crypto_ethereum).
Lastly, it’s important to note that each product uses its own terminology to refer to the same information. This brings us back to the first part of the chapter, which focuses on how data is presented. The data we observe from the aforementioned providers is subject to translation, and each indexer applies its own criteria. It will be our responsibility to determine the specific information we require.
A note on decentralization
These are information providers. With the exception of The Graph, whose product is a decentralized information protocol, the remaining companies primarily focus on keeping updated their indexes or node points, rather than prioritizing decentralization.
It is important to emphasize this point because, in a decentralized ecosystem, these providers serve as centralized points. Consequently, they can be influenced by regulations, leading to potential exposure of information or censorship, among other possibilities. A recent example involves Infura, which, while attempting to comply with international sanctions in the Ukraine-Russia conflict, also blocked MetaMask access to Venezuela. MetaMask relies on Infura’s suite, and this decision affected all IPs, even those located in countries geographically distant from the sanctioned areas.
It may or may not be relevant for the data area of our company but, as mentioned in *Chapter 1*, our job is typically aligned with a business that may have, as a product feature, respect for decentralization and all its benefits.
Summary
In conclusion, this chapter delved into the world of on-chain data, which serves as the primary data source in Web3\. We started the chapter by dissecting individual transactions and gaining insights into their structure and components. This understanding was further expanded as we explored the anatomy of blocks.
Moving forward, we delved into an analysis of state data. By examining state variables and their significance, we gained a deeper understanding of how data is stored and accessed within a blockchain.
To further enhance our ability to work with on-chain data, we explored a range of data providers. From widely used block explorers such as Etherscan to powerful APIs such as Infura, Moralis, and Covalent, and SQL-accessible tables such us Dune and Flipside, we built a comprehensive list of resources that grant us access to on-chain data. Each provider offers unique features, data formats, and querying capabilities, allowing us to tailor our approach based on the specific needs of our projects.
Throughout this chapter, we have acquired the foundational knowledge necessary to navigate and interact with on-chain data effectively. In the next chapter, we will study how off-chain data can play a key role in Web3.
Further reading
To complement this chapter, the following links may help:
* Dissecting a transaction:
* *Antonopoulos, Andreas*. *Mastering Ethereum* book, *Chapter 6*: Transactions · GitBook, 2018, [cypherpunks-core.github.io/ethereumbook/06transactions.xhtml](http://cypherpunks-core.github.io/ethereumbook/06transactions.xhtml).
* *Piper Merriam* and *Jason Carver*. *Ethereum Name Service — Web3.py documentation*, *2018*, [`web3py.readthedocs.io/en/stable/ens_overview.xhtml`](https://web3py.readthedocs.io/en/stable/ens_overview.xhtml).
* *KLmoney*. *Bitcoin: Dissecting Transactions | CryptoTokens*, *May 26,* *2017*, [`klmoney.wordpress.com/bitcoin-dissecting-transactions`](https://klmoney.wordpress.com/bitcoin-dissecting-transactions).
* A very detailed analysis of the Bitcoin transaction can be found in Nick Furneaux’s book *Investigating Cryptocurrencies*.
* [`abi-parser-nvk.vercel.app/`](https://abi-parser-nvk.vercel.app/) and [`github.com/shazow/whatsabi`](https://github.com/shazow/whatsabi).
* Dissecting a block:
* *Buterin, Vitalik*. *Merkling in Ethereum | Ethereum Foundation Blog*, *2015*, [`blog.ethereum.org/2015/11/15/merkling-in-ethereum`](https://blog.ethereum.org/2015/11/15/merkling-in-ethereum).
* *Furneaux, Nick*. *Investigating Cryptocurrencies,* *Chapter 3**: Understanding, Extracting, and Analyzing Blockchain Evidence*, *Wiley*, *2018*.
* State data:
* *Ethereum.org*. *Merkle Patricia Trie*, , [`ethereum.org/en/developers/docs/data-structures-and-encoding/patricia-merkle-trie/`](https://ethereum.org/en/developers/docs/data-structures-and-encoding/patricia-merkle-trie/).
* *Day, Allen* and *Evgeny Medvedev*. *GitHub - Blockchain-etl/Awesome-bigquery-views: Useful SQL Queries for Blockchain ETL Datasets in BigQuery*, *GitHub*, *October 27,* *2022*, [`github.com/blockchain-etl/awesome-bigquery-views`](https://github.com/blockchain-etl/awesome-bigquery-views).
第三章:使用链下数据
在前一章中,我们了解到链上数据是 Web3 数据分析的主要来源。它是开放的、分布式的且值得信赖的。尽管链上数据对于解答大多数商业数据科学问题至关重要,但必须用链下数据源的相关信息来补充,这也是本章的重点。
假设我们收到一个请求,要求评估一个智能合约的经济相关性。我们可以查询该合约中锁定的代币数量,但要完成分析,我们还需要确定这些代币的货币价值。为了实现这一点,我们必须将链上数据与价格进行整合,而这些价格通常来自链下来源。
价格、新闻和观点不存储在链上,必须从外部来源获取。本章将深入探讨这些来源,并从选定的 API 获取数据。具体而言,我们将讨论获取价格的替代方法,分析一个加密新闻聚合器,并探讨社交媒体,尤其是 X(前 Twitter)的重要性。
链下数据的性质与链上数据不同,因此在处理这些来源时,必须特别注意其可靠性。本章讨论的这些来源通常是集中式的,意味着实体完全控制其数据。这直接影响我们将要使用的数据集,因为数据点可能会被删除、缺失或篡改。相比之下,链上数据交易原则上无法被修改。
本章具体涵盖以下主题:
-
将价格整合到我们的数据集
-
将新闻融入我们的数据集
-
将社交网络数据添加到我们的数据集中
技术要求
我们将使用Tweepy,这是一个 Python 库,允许我们轻松地与 X 进行交互。使用 Tweepy,我们可以获取、发布和检索关于推文、用户以及更多的信息。要开始使用 Tweepy,我们首先需要在 Twitter 开发者网站上注册一个开发者账户,并获取一组 API 密钥,如附录 2所述。Tweepy 的文档可以在docs.tweepy.org/en/stable/找到。
如果你之前没有使用过 Tweepy,可以通过以下代码进行安装:
pip install tweepy
此外,我们将使用 Plotly 图形对象和 Plotly Express,这两个可视化库使我们能够用 Python 创建互动式可视化。Plotly Express 是一个高级库,允许我们用最少的代码行绘制常见类型的图表——如散点图、折线图、地图、饼图等。Plotly Express 的文档可以在plotly.com/python/plotly-express/找到。
Plotly 图形对象提供了更多的灵活性和控制力,使得创建高度自定义的复杂图表成为可能。Plotly 图形对象的文档可以在plotly.com/python/graph-objects/找到。
为了使用这两个库,我们需要安装 Plotly 库。如果你之前没有使用过 Plotly,可以通过以下代码片段安装:
pip install plotly
你可以在本书的 GitHub 仓库中找到包含本章讨论示例的 Jupyter 笔记本,地址为github.com/PacktPublishing/Data-Science-for-Web3/tree/main/Chapter03。我们建议你阅读Chapter03文件夹中的代码文件,以便跟进学习。
入门示例 – 列出数据来源
让我们来看看这个标题:
狗狗币上涨 25%,因为 Elon Musk 确认 Tesla 将接受 DOGE 用于商品购买
(来源 – Cointelegraph: cointelegraph.com/news/dogecoin-gains-25-after-elon-musk-confirms-tesla-will-accept-doge-for-merchandise。)
这个标题引用了三个数据来源:
-
标题(新闻):一份专注于 Web3 行业的在线报纸生成了这个标题。区块链新闻逐渐进入主流平台,类似的信息也可以在传统的金融新闻索引中找到,例如路透社。
-
价格:这个标题提到的是某种特定加密货币的价格波动。价格数据通常不会从链上数据源获取;相反,它是数据科学家认为有用的、需要从第三方数据源集成的信息。
-
X(前身为 Twitter)/社交网络:许多具有市场影响力的事件发生在社交网络上,Web3 生态系统中的关键人物在这些平台上建立了重要的在线声誉。这些有影响力的人物的一条推文可以改变价格,或引起对骗局或失败谈判的关注。大多数 Web3 公司在 X 上保持活跃,通常在创建 LinkedIn 页面之前。在这个案例中,标题中提到的对狗狗币的影响来自于 Elon Musk 的一条推文:“Tesla 将让一些商品用 Doge 购买,看看效果如何”(来源:
twitter.com/elonmusk/status/1470703708677840896)。
我们描述了三个与我们的业务数据科学项目相关的链外数据来源,我们必须学习如何以适合数据科学家使用的格式有效地集成它们。我们将在接下来的章节中讨论每一个数据来源。
向我们的数据集添加价格
价格信息通常存储在链外,多个来源提供对此数据的访问。一些最受欢迎的 API 包括以下几种:
-
CoinGecko
-
CoinMarketCap
-
Binance
-
Chainlink
-
OHLC 数据:Kraken
每个 API 都有其自身的限制,我们需要在决定是否将其集成到项目中时加以考虑。具体细节可以在各自的文档中找到。
关于价格数据,理解它是如何计算的非常重要,如以下示例所示:
-
CoinMarketCap 通过考虑所有交易市场的加权平均价格来计算资产的价格。这种方法基于这样的假设:更具流动性的市场不易受到价格波动或操纵,因此更可靠。
-
Binance 根据其平台上的交易报告价格。根据交易对,它提供市场上最近一次交易的价格。
让我们简要分析一下其中的每一个。
CoinGecko
CoinGecko (www.coingecko.com/)的文档清晰易懂,且提供了一个无需注册的免费层。通过他们的 URL 引擎,可以根据用户需求构建端点 URL,使请求更加高效。
我们可以在www.coingecko.com/api/documentation找到他们的文档。让我们也通过这个链接测试simple/price端点。

图 3.1 – CoinGecko API 视图
如图 3**.2所示,此端点所需的参数是ids和vs_currencies:

图 3.2 – 简单/价格查询参数的部分视图
还有一些可选参数,如下所示:
-
include_market_cap -
include_24hr_vol -
include_24hr_change -
include_last_updated_at -
precision
要获取特定资产的ID,我们可以去 CoinGecko 的主页并按名称搜索该资产。例如,如果我们想获取比特币的当前价格,我们需要在查询中添加比特币的 ID。要查找它,我们只需去 CoinGecko 的主页并在搜索框中输入Bitcoin,如图 3**.3所示:

图 3.3 – CoinGecko 搜索框
这将引导我们进入 CoinGecko 上的比特币信息页面(www.coingecko.com/en/coins/bitcoin),如图 3**.4所示,我们可以找到作为查询参数使用的 API ID:

图 3.4 – CoinGecko 比特币(BTC)页面视图
对于我们的simple/price请求,我们还需要输入vs_currencies参数,它决定了价格的货币类型。在本例中,我们将使用usd。
填写完 API 页面上的必填项后,我们可以点击蓝色的执行按钮,这将返回我们可以使用的 URL:
https://api.coingecko.com/api/v3/simple/price?ids=bitcoin&vs_currencies=usd
让我们来看一下在prices.ipynb中的操作。
CoinMarketCap
CoinMarketCap (coinmarketcap.com/) 提供了广泛的文档,可以通过以下链接访问:coinmarketcap.com/api/documentation/v1/。尽管这些文档可能看起来有些复杂,但对于我们的目的,定位到页面左侧的加密货币类别,通过包含多个与价格相关的端点的下拉菜单可以进行访问:

图 3.5 – CoinMarketCap 左侧栏视图
对于我们的目的,我们将使用以下链接文档中的端点:coinmarketcap.com/api/documentation/v1/#operation/getV2CryptocurrencyQuotesLatest。
CoinMarketCap 提供多个服务层级,API 限制和端点各不相同。对于这次的介绍性说明,我们将依赖免费的层级。
我们通过 CoinMarketCap 的 API 在prices.ipynb笔记本中提取最新的比特币价格。为了识别特定币种的 ID,我们可以执行映射 ID 端点,它显示了所有在 CoinMarketCap 网站上列出的加密货币及其唯一 ID。有关该端点的更多细节可以在文档中访问:coinmarketcap.com/api/documentation/v1/#operation/getV1CryptocurrencyMap。比特币的 ID 是slug参数,它包含了加密货币的字符串名称——在我们的例子中,简单地就是bitcoin。
关于链接和骗局的提示
高度复杂的骗局可以通过搜索引擎欺骗受害者。通过点击搜索引擎中的链接访问项目,特别是我们之前未访问过的小型或不太知名的项目,存在更高的风险,骗子可以通过操控网页将其提升为排名靠前的建议链接。CoinGecko 和 CoinMarketCap 已经证明在提供指向官方网站的真实链接方面非常可靠。关于安全性更深入的探讨将在第十章中提供。
Binance
这是目前活跃的最重要的中心化交易所之一。该交易所提供一个无需注册的基础数据计划。文档根据交易所提供的产品进行组织。

图 3.6 – Binance 主菜单
要提取比特币的现货价格,请导航到现货/保证金/储蓄/挖矿标签,如图 3.6所示。文档和可用端点在页面左侧的下拉菜单中列出。
该端点的 URL 由两部分组成——一个通用的基础端点和查询部分:
- 基础端点位于常规信息部分,可以通过以下链接访问:
binance-docs.github.io/apidocs/spot/en/#general-info

图 3.7 – 币安一般信息视图
-
我们将使用的查询部分如下:
/api/v3/ticker/price
这段代码的文档位于 市场数据端点 部分,可以通过以下链接访问:binance-docs.github.io/apidocs/spot/en/#symbol-price-ticker。
在 prices.ipynb 中,我们从这个来源提取最新的比特币价格。该端点需要一个 symbol 参数,以交易对格式表示,我们使用 BTCUSDT。
要获取可用交易对的列表,有两个选项。第一个是在币安平台上,第二个是在 TradingView 上,可以在 es.tradingview.com/ 创建一个账户。
在 TradingView 的主页上,进入 符号搜索,如 图 3.8 所示:

图 3.8 – TradingView 符号搜索栏
这将打开一个下拉菜单,显示所有的交易对列表。要按交易所进行过滤,修改 所有来源 参数,如 图 3.9 所示:

图 3.9 – TradingView 数据源
当搜索框在 Binance 上打开时,按 Enter 键:

图 3.10 – TradingView 来源选择
这将显示特定交易所的所有交易对,位于 SYMBOL 列中。这个符号是我们将作为参数传递给查询的字符串。

图 3.11 – 在 TradingView 上显示的 Binance 交易对/符号
币安的 API 提供了超越价格信息的全面数据,使其成为一个宝贵的探索资源。
预言机 – Chainlink
预言机 作为智能合约与现实世界数据之间的桥梁。考虑一个为特定气候相关事件(例如雨水)提供保险的智能合约。在其区块链的封闭环境中,智能合约如何判断当前是否下雨?解决方案在于预言机,它们建立了智能合约与外部信息之间的联系,确保必要的数据能在区块链内反映出来。
Chainlink 是最广泛使用的预言机之一。本章重点讨论智能合约的价格数据源,虽然也有其他数据源,例如储备证明数据源或 NFT 价格数据源(将在 第四章 中讨论)。讨论的步骤的文档可在 docs.chain.link/data-feeds/api-reference 找到。
大多数价格共识发生在链外,当需要更新区块链时,经过一致同意的价格会通过价格数据源预言机记录在链上。
例如,比特币价格会持续更新,并可在 data.chain.link/ethereum/mainnet/crypto-usd/btc-usd 查看。价格会基于 触发参数 在链上更新,如 图 3.13 所示:
-
偏差阈值:当链下数据与最后更新的价格偏差超过 0.5% 时触发。
-
心跳:在自上次更新以来经过指定时间后激活。每个价格信息源都有其特定的心跳时间。对于比特币价格信息源,该间隔设置为一小时。因此,价格信息将在一小时后刷新,前提是之前的触发事件没有在此之前发生。
如果我们想从这些智能合约中获取数据,我们需要关注心跳,并检查其时间戳,确保最新的答案足够新,以便将其添加到我们的数据集中。

图 3.12 – Chainlink 价格信息视图
要提取最新价格或 最新回合 的价格,我们需要合约地址,如前面图示中的第二个红框所示。
合约 prices.ipynb。
可用的 read 函数用于价格信息智能合约,包括以下内容:
-
decimals():返回响应中的小数位数。在prices.ipynb示例中,此值为8,通过以下代码片段获取:description(): Returns the description of the data feed. In the prices.ipynb example, this result is BTC / USD, and it is retrieved with the following code snippet:getRoundData(uint80):返回特定回合中的数据。
-
latestRoundData():返回最新的回合数据。 -
version():返回合约版本。
要获取价格,我们需要执行 latestRoundData 函数,如下所示:
contract.functions.latestRoundData().call()
结果是一个由以下元素组成的列表:
roundId |
每次更新预言机时,都会生成一个 roundId 值。要获取历史回合的答案,我们需要调用 getRoundData(uint80) 函数,并提供该数字作为参数。 |
|---|---|
answer |
这是返回的资产价格,即所需的数据点。 |
startedAt |
这是回合开始时间的时间戳。 |
updatedAt |
这是回合更新时间的时间戳。 |
表 3.1 – 预言机响应
响应中还有一个最后的元素(answeredInRound),这是一个遗留变量,现已不再使用。
一旦获取到 answer,根据 decimals() 函数指示的小数位数,将逗号移动相应的位置,转换为传统的小数格式:

图 3.13 – 由 Chainlink 提供的比特币价格
OHLC – Kraken
开盘、最高、最低、收盘 (OHLC) 数据是一种特定的数据集,其中每行包括一个时间戳和四列数据:
-
开盘价 (O):这是该资产在分析期间开始时的价格。
-
最高价格 (H):这是在分析期间该资产的最高价格。
-
最低价格 (L):这是在分析期间该资产的最低价格。
-
收盘价(C):这是分析期间结束时最后的资产价格。
可以在 表 3.2 中看到一个示例:
| 时间戳 | 开盘价 | 最高价 | 最低价 | 收盘价 |
|---|---|---|---|---|
2022-12-06 00:00:00 |
16965.7 |
17089.1 |
16965.7 |
17011.0 |
表 3.2 – OHLC 数据示例
OHLC 列提供了有关资产在特定时间段内价格变化的信息。图 3.14 显示了一个可以使用 OHLC 数据创建的蜡烛图示例。

图 3.14 – 蜡烛图设计
数据集中的每一行可以用来绘制一个蜡烛图。收盘价和开盘价告诉我们,在给定的时间段内,资产的价格是下降(收盘价低于开盘价)还是上升(收盘价高于开盘价)。这些信息用于给蜡烛图的实体上色。
OHLC 数据可以包括额外的列,如成交量或交易数量。请参阅 prices.ipynb 中的示例。
像移动平均线或布林带等技术指标,在交易中非常流行,也可以使用 OHLC 数据进行绘制。
Kraken 集中交易所通过其开放 API 提供 OHLC 数据,并且文档非常完善。正如我们在使用 Binance 时学到的那样,使用交易所时,每个价格查询都必须以交易对的形式表达。
文档可以在 docs.kraken.com/rest/#section/General-Usage 找到。我们将使用的端点在 docs.kraken.com/rest/#tag/Market-Data/operation/getOHLCData 中有详细说明。
在处理 OHLC 数据时,考虑数据的时间间隔或粒度非常重要。在短时间内看似高或低的价格,在较长时间段内分析时可能并不重要。时间粒度将取决于 API。通常,可以提取秒、分钟、小时和天数以及它们的组合。在 Kraken 中,可以使用以下参数进行提取:

图 3.15 – 以秒为单位表示的间隔参数
要绘制蜡烛图,我们可以使用 plotly.graph_objects 库。在 prices.ipynb 中,我们提取了 2023 年 4 月 1 日至 4 月 5 日之间四小时周期的比特币 OHLC 数据集,并使用该库绘制相应的蜡烛图。
关于价格的最终思考
在我们对价格进行了深入讨论后,以下是一些需要记住的关键点:
-
并非所有法定货币都被这些 API 支持。对于不是美元或欧元的货币,API 可能会显示该国中央银行与美元的官方汇率,这可能与实际市场价格有很大差异。特别是对于那些有监管经济或高通货膨胀的国家来说,这一点尤其如此。在将这些价格添加到我们的数据集之前,有必要了解这些 API 数据的来源。
-
代币或硬币的价格并不是我们可能需要跟踪的唯一产品。我们还可能会收到跟踪某个 NFT 系列的地板价格的请求。
-
在写这篇文章时,Web3 资产在短时间内仍然表现出显著的价格波动。在计算平均值时,我们必须注意可能影响这些平均值的异常值。来自低流动性市场(如小型交易所)的数据更容易受到异常值的影响。请阅读这些价格如何计算的说明,并定期与其他来源进行比较,或像 CoinMarketCap 一样创建加权平均值。
新闻常常引发价格波动,因此让我们现在探索一个专门的新闻聚合器,它跟踪 Web3 世界中的相关信息。
将新闻添加到我们的数据集
一位教授曾提到,在加密世界中,新闻只需五分钟就能影响一个资产的价格。
新闻不仅仅对价格产生影响,营销团队也可能要求分析品牌、活动或产品的社会影响,或者可能需要获取某个算法等应用。为了这个目的,数据科学家需要格式化适合分析的新闻数据。
截至目前,已有一个名为CryptoPanic的专门数据聚合源,它专门索引与 Web3 生态系统相关的新闻。网站链接是 cryptopanic.com/。
它的数据可以通过 API 访问,注册后可以获得 API 密钥。
在主页面,点击左侧菜单中的登录选项卡:

图 3.16 – CryptoPanic 主界面概览
如果这是你第一次注册,你需要确认你的电子邮件。之后,你就完成注册了。点击主页上的开发选项卡:

图 3.17 – 开发选项卡
点击新页面上的任一API选项卡:

图 3.18 – API 文档
点击API 密钥,它会打开一个新页面,其中包含凭证:

图 3.19 – API 密钥
文档可通过此链接访问:cryptopanic.com/developers/api/。
我们将使用传统的requests库进行查询,并将 API 密钥添加到文档中列出的端点。获取新闻列表的详细步骤可以在news.ipynb中看到。
我们可以对请求应用过滤器,以限制接收的信息量。这些过滤器包括以下内容:
-
货币:在索引新闻中提到的资产
-
区域:语言
-
UI:包括以下类别——上升、热门、看涨、看跌、重要、保存和笑话
-
类型:这可以是媒体或新闻
过滤器可以组合使用,每个过滤器都可以接受多个参数。例如,可以通过在 URL 中添加以下字符串来获取英文和西班牙文的新闻:
regions=en,es
在news.ipynb中,我们应用了两个过滤器:货币和类型:
url= 'https://cryptopanic.com/api/v1/posts/?auth_token=[YOUR API KEY]¤cies=BTC&kind=news'
response = requests.get(url)
该 API 还提供专业付费选项(在其网站上称为“pro”),这些选项可以访问额外的元数据或获取原始来源的链接。
这个 API 的另一个有趣之处在于,返回的请求内容包括以下内容:
-
社区对头条新闻情绪的看法。这对构建情绪分析算法尤为有用,例如我们将在第八章中构建的算法。
-
发布新闻的时间戳。这样我们就可以将头条新闻与价格结合起来,比较新闻对价格的历史影响。
正如在本章开头的介绍示例中所看到的,社交网络上的事件甚至在记者写文章之前就能对价格产生重大影响。因此,重要的是将社交网络的数据添加到我们的数据集中。
将社交网络添加到我们的数据集中
Web3 是一个在线行业,因此在线发生的所有事件,从意见到互动,都具有重要的影响力。
情绪分析,即衡量对产品或代币的反应,在营销团队、分析师和交易员中都发挥着至关重要的作用。一个突出的例子,说明了这种指标的重要性,就是 CoinStats 的恐惧与贪婪指数。这个指数可以在coinstats.app/fear-and-greed/查看,结合了社交媒体帖子等因素来衡量市场情绪。

图 3.20 – 加密恐惧与贪婪指数
根据 CoinStats 的解释,该指数结合了来自不同来源的数据。为了捕捉心理动能,它们还从 X 上的社交媒体互动中获取见解,专注于具有恐惧和贪婪元素的特定标签,这些因素共同参与了总体计算。根据文档,社交媒体因素在最终指数中占有 15%的权重。
X(前身为 Twitter)
X 可能是目前 Web3 相关对话中最重要的社交媒体平台,而且该服务无需介绍。
注释
我们将X和Twitter交替使用。尽管该平台的用户界面现在使用的是 X 这个名称,但在开发者工具和所有网址中,它仍然保留着原来的名称 Twitter。
一个典型的例子,说明了 X 上发生的事情如何影响行业,是在 Binance 在其官方 X 页面上宣布,“由于公司尽职调查,以及关于客户资金处理不当和美国机构调查的最新新闻报道,我们决定不再追求对 FTX.com 的潜在收购”(来源:twitter.com/binance/status/1590449161069268992)。
X 数据访问自 2023 年 2 月起成为付费服务,订阅详情可通过开发者门户网站 developer.twitter.com/ 获得。本节中的练习使用了基础订阅和 API v2。
要获取具有读取权限的 API 密钥,我们需要创建一个项目并连接一个应用程序,具体步骤请参见 附录 2。
大多数用户的推文是公开的,定制查询允许我们根据用户、主题、语言或位置等多种标准获取推文。在 social.ipynb 中,我们提取了最新的 100 条包含 Bitcoin 和 BTC 的推文,排除了转发,并限制为英文推文,查询如下:
query = 'bitcoin btc -is:retweet lang:en'
有关构建有效查询的更多说明,请参见 developer.twitter.com/en/docs/twitter-api/tweets/search/integrate/build-a-query。
检查点
推文提取流程的逐步版本详见 social.ipynb。或者,生成的 CSV 文件已上传到本书的 GitHub,并可以在 tweets_100.csv 中访问。
使用 v2 端点,可以请求 annotations,为推文添加上下文信息。此功能对数据分析非常有价值,因为它在有限的分类法中对内容进行标准化。例如,考虑 图 3.21 中展示的推文:

图 3.21 – 示例推文(ID: 1731806102101033329)
X 提供了实体识别和上下文注释功能,用于该推文。Person、Place、Product、Organization 和 Other。
推文正文中识别出三个实体。两个是组织 – Blackrock 和 SEC – 第三个属于 Other 类别,指的是 Bitcoin:
'annotations': 'annotations': [{'start': 10,
'end': 18,
'probability': 0.8568,
'type': 'Organization',
'normalized_text': 'Blackrock'},
{'start': 55,
'end': 57,
'probability': 0.7281,
'type': 'Organization',
'normalized_text': 'SEC'},
{'start': 73,
'end': 79,
'probability': 0.9581,
'type': 'Other',
'normalized_text': 'Bitcoin'}]
该推文的完整实体字典可以在 social.ipynb 中查看。
X 通过 上下文注释进一步丰富推文信息,这些注释是从文本的语义、关键词和标签中推断出来的。已经制定了一个全面的关键词、标签和用户名单,并根据具体上下文进行标记。如果这些元素出现在推文中,它们将被适当标记。截至 2022 年 6 月,已有超过 80 个上下文领域。相关文档链接可以在 进一步 阅读 部分找到。
下面是一个示例:
{'domain': {'id': '131',
'name': 'Unified Twitter Taxonomy',
'description': 'A taxonomy of user interests. '},
'entity': {'id': '913142676819648512',
'name': 'Cryptocurrencies',
'description': 'Cryptocurrency'}},
这些信息对于分类和自然语言处理(NLP)机器学习算法非常有价值。
该推文的完整上下文注释列表可在social.ipynb中找到。
营销和产品团队常用的一种方法是分析与产品或品牌相关的词汇,这通常通过分析客户评论、反馈或社交媒体评论来实现。这种方法可以更深入地了解受众及其看法。实现这一目标的图形化方式之一是创建词云,突出显示最常被提到的词汇。这有助于一目了然地识别客户的情感、偏好和痛点。
为了重现词云,我们利用推文作为数据源,特别是提取了 1,000 条针对 NFT 领域中的一个协议(在第四章中介绍)——即 OpenSea 的推文。为了执行此提取,我们使用了以下查询:
new_query = 'opensea -is:retweet lang:en'
检查点
推文提取管道的逐步版本详见social.ipynb。另外,生成的 CSV 文件已上传到本书的 GitHub,并可以通过tweets_df.csv访问。
在笔记本中,我们将找到用于清理推文的库和方法,在计算单词出现频率之前对其进行标准化。这些是传统的 NLP 步骤,我们将在第八章中更详细地描述。OpenSea 的词云结果如图 3.22所示:

图 3.22 – OpenSea 词云
一旦我们学会提取社交链外数据,就可以将其与链上数据结合,扩展我们的分析。推文、Discord 对话、Telegram 互动以及其他社区论坛都有时间戳和地理位置标签,可以用于将链外活动与链上发生的交易进行合并。这有助于分析师推测链或协议的活跃时间、推断客户的地理位置等。这些类型的分析通常是营销团队请求的,以改善他们广告活动的方向。
一个利用这两种世界之间连接的公司例子是 Spindl,该公司正在努力将 Web2 营销数据源与链上数据合并,以构建 Web3 领域的第一个营销漏斗工具。
一个关于 Twitter 个人资料的说明
这里有一些有趣的个人资料可以关注,以进行 Web3 数据分析/内容创作,除此之外还有许多其他有趣的个人资料:
@``0xGembus: twitter.com/0xGembus
@``0xAtomist: twitter.com/0xAtomist
@``hildobby_: twitter.com/hildobby_
其他值得探索的社交媒体数据源如下:
-
Reddit:该平台托管了许多与 Web3 相关的对话,形式为 Subreddits。Subreddit 中的帖子和评论提供了宝贵的信息。
-
BitcoinTalk.org 论坛:该论坛上的公开帖子也是一个有趣的信息来源。
摘要
在本章中,我们考察了与 Web3 经济相关的各种链外数据来源,并将分析分为三个主要领域。对于价格,我们探索了来自传统来源到交易所的多个 API,以及一个预言机。关于新闻,我们学习了如何提取实时头条,这些头条来自当时最优秀的专门新闻索引器——CryptoPanic。至于 X(前身为 Twitter),我们利用其 API 来衡量围绕 NFT 协议的情绪。这个资源清单并不详尽,我们只触及了我们能够为这些数据提供的所有用途的表面。
在下一章中,我们将深入探讨 NFT 及其在游戏、艺术和命名服务行业中的应用。
进一步阅读
为了补充本章,以下链接可能对你有所帮助:
-
价格:
-
支持 CoinMarketCap。(2020)。安全检查。如何计算 CoinMarketCap 上的价格?
support.coinmarketcap.com/hc/en-us/articles/360015968632-How-are-prices-calculated-on-CoinMarketCap- -
加密 API 文档。(无日期)。CoinGecko。
www.coingecko.com/api/documentation -
账户。(无日期)。加密货币价格、图表与市值 | CoinMarketCap。
coinmarketcap.com/api/documentation/v1/ -
CoinMarketCap。(无日期)。最受信任的加密货币市场数据 API | CoinMarketCap。coinmarketcap.com。
coinmarketcap.com/api/faq -
有用的 Chainlink 教程。Chainlink。(2022)。学习资源。Chainlink 文档:
docs.chain.link/getting-started/other-tutorials/ -
进一步扩展关于预言机的内容。Chainlink,区块链中的预言机是什么? » 解释。Chainlink: 混合智能合约的区块链预言机:
chain.link/education/blockchain-oracles -
数据流 API 参考。(无日期)。Chainlink 文档。
docs.chain.link/data-feeds/api-reference -
价格信息合约地址。(无日期)。Chainlink 文档。
docs.chain.link/data-feeds/price-feeds/addresses/
-
-
新闻:
- 下载网站的逐步过程。Furneaux, Nick。“调查加密货币。理解、提取与分析区块链证据” Wiley,2018。第八章。- 第 125 至 130 页。
-
社交网络:
-
安装 — Tweepy 4.13.0 文档。(无日期)。Tweepy 文档 — tweepy 4.13.0 文档。
docs.tweepy.org/en/stable/install.xhtml -
Getting-started-with-the-twitter-api-v2-for-academic-research/5-how-to-write-search-queries.md at main · twitterdev/getting-started-with-the-twitter-api-v2-for-academic-research. (n.d.). GitHub.
github.com/twitterdev/getting-started-with-the-twitter-api-v2-for-academic-research/blob/main/modules/5-how-to-write-search-queries.md -
概述. (n.d.). 用例、教程和文档 | Twitter 开发者平台.
developer.twitter.com/en/docs/twitter-api/annotations/overview和developer.twitter.com/en/docs/twitter-api/annotations/faq
-
第四章:探索 NFT 的数字独特性——游戏、艺术与身份
在本章中,我们将探讨非同质化代币(NFT)及其各种经济应用场景。我们将从了解 NFT 是什么开始,如何在交易数据中记录相关信息,以及获取这些信息的替代方式。此外,我们还将分析游戏、艺术和身份行业如何利用这项技术,并探讨一些与各行各业相关的指标。
商业举措通过一组智能合约执行,我们称之为“协议”。我们将深入了解基本的协议指标,快速了解每个协议的结构和用户构成。为此,我们可以选择使用数据框架,这对于商业分析师来说是一项非常有价值的工具,帮助我们组织分析并在展示结果时构建有力的叙述。此类结构的一个例子是覆盖率、留存率和 收入框架。
覆盖率指标帮助我们了解增长的来源、客户获取成本、目标市场等;留存率指标为评估产品效果提供了衡量标准,涵盖客户使用频率、流失率和群体分析等因素;收入指标则提供有关产品盈利能力的见解。值得注意的是,Covalent 团队设计了一项数据分析师培训计划,详情我们将在第十三章中进行更详细的介绍,该计划将链上分析学习与这一框架结构结合。
在本章中,我们将探索每个类别的具体指标示例。
本章将深入探讨以下主题:
-
NFT 数据简介
-
游戏、艺术与身份行业的协议和数据库探索
-
游戏、艺术与身份行业相关指标
本章结束时,我们将能够自信地处理数据分析师在处理 NFT 时通常研究的各项指标。
技术要求
我们将使用在Dune Analytics、Increment、Footprint Analytics 和 Flipside 等平台上可用的索引数据。为了跟上进度,请在这些平台上开设账户,并通过第二章提供的链接进行操作。交易数据是通过 SQL 服务查询的,语法因查询引擎的不同而有所差异。
我们还将使用 web3.py 中包含的 ens 模块,web3.py 是我们在第一章中安装的。要使用它,只需通过以下代码片段导入:
from ens import ENS
你可以在本书的 GitHub 仓库中找到包含本章讨论示例的 Jupyter notebook,链接为github.com/PacktPublishing/Data-Science-for-Web3/tree/main/Chapter04。
此外,Dune 上有一个实时仪表板,展示了本章中解释的许多查询,网址为 dune.com/gabriela/chapter-4-nft。对于所有 Dune 仪表板,查询可以通过点击相关图表的标题来访问。以下是一个示例:

图 4.1 – 点击此处打开查询。Dune 仪表板 @hildobby (https://dune.com/hildobby/NFTs)
我们建议同时探索这两个资源,以获得全面的理解。
通过使用 NFT 在区块链上实现独特资产追踪
本节包括两个主要部分:业务需求,将揭示这一解决方案起源的具体需求;以及技术解决方案,将提供标准智能合约的结构性概述,包括其方法和事件。
业务需求
当一个资产与另一个相同性质的资产具有相同的质量和价值,可以互换时,该资产被视为可替代的。例如,一美元可以与另一美元互换,同样适用于本地加密货币和代币,如 DAI 或 USDT。
相反,如果一个资产是不可替代的,这意味着它是独一无二的,无法被另一个相同的资产替代,因为没有等价物。考虑索罗拉的《海滩散步》画作,它是独特的,尽管我们可以通过 Google 复制它因为我们欣赏它,但我们并不真正拥有它,也无法证明拥有权:

图 4.2 – 索罗拉的画作《海滩散步》
数字艺术面临着类似甚至更为尖锐的困境。一旦一件艺术作品被上传到互联网,它就可以被无限复制,而不恰当地承认其作者或所有权,更不用说支付版税了。
使用区块链技术追踪独特资产的所有权为解决这一问题提供了方案,并且已经彻底改变了那些以独特性为交易价值的行业,如艺术、游戏或身份认证。
技术解决方案
以太坊评论请求 721,或称为ERC 721标准,包括一组合约,允许以太坊实现一个 API,为区块链上的某些资产提供不可变的身份。一旦身份被赋予,这些资产就可以被追踪、估值、出售等。NFT 的身份由一对数据点组成:

图 4.3 – NFT 的身份
合约地址可能根据所考虑的行业有不同的名称。例如,在处理 ENS 时,它可能被称为注册人合约,在研究艺术时,则可能被称为收藏合约。
需要注意的是,使用此标准时,Ethereum 支持连接外部资源,智能合约会引用第三方服务器来获取关于 NFT 的信息。这意味着,如果智能合约指向的 URI 发生变化,NFT 的信息可能无法再访问,或者发生变化。以太坊开发者曾考虑将所有资产的元数据存储在区块链上,但由于注册在区块链上的 gas 费用非常昂贵,这会妨碍可用性。
本解决方案的基本合约方法和事件在 2018 年由 William Entriken、Dieter Shirley、Jacob Evans 和 Nastassia Sachs 提出的 ERC 721 中进行了详细说明。另一个有价值的信息来源是 Open Zeppelin 实现,它详细描述了每个函数和方法。
我们将遇到的read方法如下:
-
balanceOf(address _owner):该方法告诉我们特定地址拥有多少 NFT。 -
ownerOf(uint256 _tokenId):该方法告诉我们拥有特定 NFT 的地址。
可选地,我们将看到元数据扩展:
-
name():集合的名称 -
symbol() -
tokenURI(uint256 _tokenId)
枚举扩展是可选的,它启用以下方法,提供对集合的全面视图:
-
totalSupply() -
tokenByIndex(uint256 _index) -
tokenOfOwnerByIndex(_owner, uint256 _index)
以下是一些重要事件:
-
Transfer(address indexed _from, address indexed _to, uint256 indexed _tokenId):当 NFT 的所有权发生变化时,会触发此事件。该事件签名的哈希为0xddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef,我们将在许多查询中看到它。 -
Approval(address indexed _owner, address indexed _approved, uint256 indexed _tokenId)。 -
ApprovalForAll(address indexed _owner, address indexed _operator, bool _approved)。
NFTs 的应用,尤其是在游戏中,突显了最初提出的 NFT 的高成本。随后,另一组作者在 2018 年提出了 ERC 1155 多代币标准。ERC-1155 用于在同一合约中组合可替代代币和 NFT,节省时间和 gas 费用,同时减少以太坊上的冗余代码。
我们将遇到以下相关的读取函数方法:
balanceOfBatch(address[] calldata _owners, uint256[] calldata _ids):该方法允许你查询多个地址在某些代币 ID 上的所有权。
事件如下:
-
TransferSingle -
TransferBatch -
ApprovalForAll -
URI
到目前为止,我们已经列出了在分析 NFT 数据时将遇到的事件和函数。我们在第二章中学习了如何与它们交互,因此现在直接进行更多使用 NFT 生成数据的案例研究,并为其构建度量标准。
区块链游戏 – GameFi 提案
对于每个行业,我们将简要回顾目前活跃的企业、玩家以及相关的指标。
根据商业案例的不同,这些指标可以进一步扩展。进一步阅读部分包含了额外的资源。
商业格局介绍
游戏产业在区块链发展史中占有一席之地,在推动该技术的采用方面取得了显著成功,同时重塑了奖励和所有权的格局。
游戏产业经历了重大的变革,从“付费游玩”模式转变为“免费游玩”在线格式。在“付费游玩”模式下,玩家需要购买实物游戏卡带、光盘或订阅服务才能访问游戏内容。而区块链技术的出现进一步推动了边界,引入了玩赚(P2E)模式。P2E 赋予玩家财产权,让他们真正拥有游戏内资产。过去,玩家可能获得过游戏内的奖励或物品,但他们并不拥有这些物品的真正所有权,无法出售或交换这些资产。NFT 的引入为游戏生态系统带来了真正的改变,为玩家提供了真正的所有权感,并通过区块链技术铺平了游戏与金融融合的道路。这一转变不仅仅发生在游戏本身,还影响了玩家在虚拟世界之外的生活。因此,出现了一种新的商业结构,称为游戏公会,它们旨在将相关的游戏内资产租赁给玩家,同时为成员提供培训和社区支持。
区块链支持的游戏兴起始于 2018 年,当时推出了《加密猫》这款游戏,玩家可以繁育和交易数字猫。这款游戏引入了可交易的数字收藏品的概念。随之而来的是《Axie Infinity》的重大里程碑,它吸引了大量非加密货币用户加入生态系统,创下了行业前所未有的数字。Axie Infinity 为区块链游戏带来了主流采用。在本书撰写时,许多游戏正在不断推出,不断推动创新的边界。
这些区块链游戏创造了一个不断发展的生态系统,经济模式超越了玩家,甚至涉及到非玩家,为他们提供了角色,甚至推广了跨境奖学金,以通过游戏公会组织玩家并得到投资者的支持。游戏与金融在这一市场细分中的融合被称为 GameFi,并且是由区块链技术实现的。金融概念和激励措施已经被整合到游戏产业中,例如收益耕作、质押或治理代币等。
GameFi 还使得游戏数据的获取变得更加民主化,以前这些数据完全由大型游戏公司控制。现在,通过正确的知识,我们可以通过查询区块链跟踪资产、玩家以及整个游戏内经济。
分析
现在,让我们分析一款声称其所有数据集都存储在以太坊网络上的游戏,该游戏被称为$Wool,是该生态系统的货币。
要参与游戏,玩家必须拥有一只羊或一只狼。这些角色可以在 NFT 市场如 OpenSea 上购买,稍后我们将在本章的通过区块链重新定义艺术产业一节中进一步定义。以下是 Wolf Game 收藏品的链接:opensea.io/collection/wolf-game。我们可以通过识别 Wolf Game 收藏品的智能合约0x7f36182dee28c45de6072a34d29855bae76dbe2f开始我们的分析。
方法论说明
在首次处理一个项目时,尤其是当这个项目较为陌生时,我们可以按照以下步骤进行:
-
确定我们想要通过数据回答的具体问题。
-
找到一个交易示例,能够体现回答问题所需的信息。
-
分析交易,正如我们在《第二章》中学到的那样,了解智能合约如何记录数据。
让我们应用这一方法论:
-
假设我们想要确定 Wolf Game 中铸造的羊和狼的数量。铸造的 NFT 数量是 NFT 稀缺性的一个重要指标。
-
要理解智能合约如何记录铸造数据,我们将搜索一个铸造交易。例如,考虑
0xc7fa87b19a6cc7735c49753442fc034fd6ed5d5c1b5250c56eebed428376272e这个交易哈希。
在 Etherscan 上,交易显示如下:

图 4.4 – Etherscan 视图中的交易哈希概览
交易回执日志显示如下:

图 4.5 – Etherscan 视图中的交易日志概览
我们也可以在Chapter4/Games.ipynb中探索日志,同时遵循《第二章》中描述的方法论,在该章节中,我们获取交易回执并解码日志。解码后的日志显示了以下数据结构:
| 事件名称或 Topic [0] | Transfer |
|---|---|
| From - Topic [1] | 0x0000000000000000000000000000000000000000 |
| To - Topic [2] | 0x0a2542a170aA02B96B588aA3AF8B09AB22a9D7ac(发起交易的 EOA) |
| tokenID - Topic [3] | 4618 |
表 4.1 – 解码日志的数据结构
从这些结果中,我们可以推导出以下信息:
-
我们所寻找的数据位于以太坊地址
0x7f36182dee28c45de6072a34d29855bae76dbe2f中。 -
在这些日志中,我们需要查找“Transfer”事件,其中“from”地址是
0x0000000000000000000000000000000000000000。 -
最后,我们需要统计唯一的
tokenID值。
如果我们将这些步骤转化为 SQL 查询,我们可以得出结论,共铸造了 13,737 个 NFTs。SQL 查询如下:
SELECT count (distinct ("topic3")) as total_nfts
FROM ethereum.logs
WHERE "contract_address" = 0x7f36182dee28c45de6072a34d29855bae76dbe2f
AND "topic0" = 0xddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef
AND "topic1" = 0x0000000000000000000000000000000000000000000000000000000000000000
值得注意的是,如果转移来源地址为 0x0000,我们可以将其解读为铸造事件。如果该地址或 0x000dEad 出现在交易的“to”部分,则可以认为是销毁转移。与加密货币类似,铸造 NFT 表示其创建,而 销毁 则意味着它们被发送到不可恢复的地址,实际上将其从流通中移除。这可以用来控制供应量或淘汰不再市场化的游戏资产。
另一个常见的度量标准是识别主要持有者。该度量标准告诉我们哪些地址持有最多的代币以及它们拥有的数量。基于我们之前检查的数据结构,我们可以使用以下 SQL 查询来计算该指标:
WITH cte as (
select address, nftid, sum (indicator) as indicator
from
(select "topic1" as address, "topic3" as nftid, -1 as indicator
from ethereum.logs
where "contract_address" = 0x7f36182dee28c45de6072a34d29855bae76dbe2f
AND "topic0" = 0xddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef
union all
select "topic2" as address, "topic3" as nftid, 1 as indicator
from ethereum.logs
where "contract_address" = 0x7f36182dee28c45de6072a34d29855bae76dbe2f
AND "topic0" = 0xddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef)
GROUP BY address, nftid
HAVING SUM(indicator) > 0)
select address, sum (indicator) as total_holdings
from cte
group by address
order by total_holdings DESC
limit 10
该查询生成了一个包含两列的表格——一列列出主要持有者的十六进制地址,另一列指示它们持有的 NFTs 数量:

图 4.6 – NFTs 的主要持有者
我们可以在 OpenSea 分析平台上验证此信息(opensea.io/collection/wolf-game/analytics?tab=items),以确保检索到的数据与地址和持有量的准确性一致:

图 4.7 – OpenSea 分析平台的主要持有者
通过选择以下功能,也可以用状态数据验证此结果:
contract.functions.balanceOf(address).call()
在Chapter4/Games.ipynb中,我们将这个函数应用于列出的地址;结果与我们查询的交易数据相同。
要访问状态数据,我们必须按照以下步骤操作:
-
在 Etherscan 上搜索相关的 ABI。对于 Wolf Game,我们已经在本书的 GitHub 仓库中提供了 ABI。
-
使用 Infura 连接以太坊网络。
-
使用
web3.eth.contract()方法连接智能合约地址和 ABI。 -
执行
balanceOf()读取函数查询智能合约。在这种情况下,我们传递一个地址列表来检查持有量。结果与我们查询的交易数据相同:

图 4.8 – 每个地址的持有状态数据
若要获取更多度量标准和见解,考虑探索基于 Dune 构建的 Wolf Game 仪表板:dune.com/gabriela/chapter-4。
值得注意的是,Axie Infinity 在其专用链 Ronin 上运营,已经对 NFT 领域产生了重大影响,直到 2022 年 3 月发生了一起黑客事件,损失了 6 亿美元的 ETH。Ronin 有自己的区块链浏览器,其交易数据被我们在第二章中分析的所有数据提供商进行索引。其中一个数据提供商 Flipside 在flipsidecrypto.xyz/dumplings/axie-infinity-axie-infinity-r5iPOK上维护了一个有趣的仪表盘。
Ronin 社区也非常活跃,许多开发者已加入该生态系统。官方 Axie Infinity Discord 服务器(https://discord.gg/axie)设有一个“tools-api-etc”频道,提供帮助和信息。开发者创建了特定的端点来访问游戏数据。例如,我们可以探索 REST API(https://documenter.getpostman.com/view/23367645/2s7YfPfEGh#intro),还可以使用以下 GraphQL 端点:axie-graphql.web.app/。
Sky Mavis 还提供了一个官方 API 来获取游戏数据。要访问该 API,我们必须先注册并获取 API 密钥。相关文档可以在docs.skymavis.com/reference/general找到。我们可以使用此 API 来提取游戏领袖在Chapter4/Games.ipynb笔记本中所拥有的物品数据。这对于竞争玩家来说是非常有价值的信息。
在分析了游戏垂直领域后,我们将深入探讨另一个行业,NFT 在其中被用于与身份相关的目的。
区块链中的身份
正如我们在上一节中所做的,我们将简要回顾一些在身份业务中活跃的项目,并了解其中的参与者和相关指标。
行业格局简介
身份一直是 Web3 项目的重点领域。在线领域面临着与身份相关的各种挑战,如解决身份盗窃、国际信用评分转移以及防止 Sybil 攻击等问题。
一个值得关注的项目是“人类证明”,该项目旨在创建一个基于以太坊网络启动的防 Sybil 的个人列表。要加入该项目,已经注册的个人必须为你的个人资料担保,从而扩展信任网络。注册有效期为 2 年,以确保注册表持续更新,从而将已故个人或曾经进入列表的机器人移除。身份拥有者可以注销或更新他们的信息。该项目的主页突出了通过验证身份可以提供显著好处的各种用例,包括信用评分、反垃圾邮件工具和自我主权身份。
鼓励更多个人加入这个信任网络的一个强有力的激励是基本收入(UBI)的概念。在链外世界中,UBI 是一种福利政策,国家通过这一政策为每个公民提供固定的、无条件的收入。“人类证明”通过向所有成功注册的身份发放一个名为\(UBI 的代币,模拟这一政策。我们可以在这个网页上找到相关地址:https://kleros.gitbook.io/docs/developer/deployment-addresses。一个有趣的\)UBI 仪表盘可以在dune.com/jeremyarbid/Proof-of-Humanity-Universal-Basic-Income-(UBI)找到。
关于 Sybil 攻击的说明
Sybil 攻击是对在线系统的一种安全威胁,其中一个实体通过创建多个账户、节点或计算机来试图控制网络。一个简单的例子是一个人创建多个社交媒体账户来操控民意调查的结果。
在这一领域,利用 NFT 的主要产品是区块链名称服务。在第二章中,我们介绍了以太坊名称服务(ENS)和RIF 名称服务(RNS)的协议名称。这些项目遵循传统的域名服务(DNS)概念,后者用易读的名称替代 IP 地址,以便访问网站。以同样的方式,这些协议在区块链上租赁或出售易读的名称,这些名称帮助替代用于标识地址的长十六进制字符串,使得与品牌和个人的互动更加便捷。一个额外的优势是,这些名称服务是去中心化的,因此不受中央权威的审查。
几个项目积极参与解决这一用例,每个项目都提出了独特的价值主张。有些协议提供名称服务的销售,而其他一些则提供租赁选项,包括子域等变体。这些项目大多数都是基于 ERC-721 标准的共同基础构建的。
若要从这些项目中提取数据,首先要定位文档和构成整个项目的智能合约列表。成熟的项目通常会提供透明的合约地址列表,如这里所示:
| 网络 | 合约地址 |
|---|---|
| 以太坊主网 | 0x… |
| 以太坊测试网(Goerli) | 0x… |
| Polygon 主网 | 0x… |
| Rootstock 主网 | 0x… |
表 4.2 – 项目地址的典型参考表
这种透明性简化了访问和验证。对于 ENS,已部署的智能合约可以在docs.ens.domains/ens-deployments找到。
分析
ENS 库简化了与协议的互动,部分应用程序可以在Chapter04/Identity.ipynb中找到。以下代码片段帮助我们获取特定 ENS 的所有者地址:
from ens import ENS
ns = ENS.fromWeb3(web3)
ns.owner("COMPLETE WITH THE ENS OF CHOICE")
该协议由两种类型的智能合约组成:
-
注册表,管理已铸造的名称
-
注册商,处理新域名的采购
每个域名的注册商地址如下:
| 域名 | 合约地址 |
|---|---|
.``eth |
0x57f1887a8BF19b14fC0dF6Fd9B2acc9Af147eA85 |
.``art |
0x828D6e836e586B53f1da3403FEda923AEd431019 |
.``xyz |
0x58774Bb8acD458A640aF0B88238369A167546ef2 |
表 4.3 – 注册商地址。来源: https://docs.ens.domains/ens-deployments
在本书的 GitHub 仓库中,我们已添加来自 Etherscan 的永久注册 ABI,帮助获取有关特定代币持有者或特定 ENS 的状态数据。以下代码片段提供了有关地址持有多少 NFTs 的信息:
ethregContract.functions.balanceOf(owner_address).call()
Chapter04/Identity.ipynb 展示了如何提取其他代币信息,如代币 ID 和到期日期。代币 ID 对应于构成域名的规范化名称或标签的哈希值。有了这些信息,就可以从 ENS API 获取代币的元数据,例如关联的图像(如果存在),可以访问 metadata.ens.domains/docs。
值得注意的是,ENS 文档中包含一个特别的“ENS 数据指南”,列出了相关资源。该协议已经在 The Graph 服务上启用了子图,并且在 Dune 的 SQL 服务上有许多可用的表格。请考虑探索 dune.com/makoto/ens,该页面提供了 ENS 生态的度量概述,包括创建的 ENS 名称总数、参与地址以及这些指标的月度变化。
我邀请您探索这些列出的其他项目或网络的度量数据。以下是其中的一些:
-
不可阻挡的 域名:
unstoppabledomains.com/ -
RIF 名称 服务:
dev.rootstock.io/rif/rns/mainnet/ -
比特币名称 服务:
btc.us/
到此为止,我们已经解释了区块链名称服务是什么,并分析了数据来源和 ENS 的主要度量指标,ENS 是利用与身份相关的数字唯一性的一种产品。目前,只有 2% 在过去一年中活跃的地址持有 ENS,这表明在 Web3 空间内身份领域仍有许多工作要做。
在下一部分中,我们将探讨数字唯一性在艺术领域的影响。
用区块链重新定义艺术商业
在这一部分中,我们将简要回顾 Web3 生态环境,谁是活跃的参与者,以及一些相关的度量指标。
商业环境介绍
ERC-721 协议背后最重要的应用之一,就是艺术领域,特别是在交易量方面。区块链技术通过实现唯一作品的交易和追踪其真实性,对艺术行业产生了深远影响。投资者和画廊为保证艺术品的真实性投入了大量的时间和精力。传统艺术界玩家已经通过多种方式活跃在这一领域,从涉足数字艺术世界(例如贝尔维德尔博物馆展示了 10,000 件数字版的克林姆特名作《接吻》)到在 Web3 原生平台上提供传统艺术,扩展他们的服务到新的观众群体。
此外,原本与艺术无关的公司也开始探索这一领域。Covalent 最近分析了耐克通过发行 NFT 推广其标志性运动鞋所带来的收入。这一举措通过首次和二次销售,产生了近 2 亿美元的收入,占这家价值十亿美元公司的 Web3 初次尝试收入的 0.4%。
新的 0xCB8399D84e17fD5B4e955C716647c7BB2C35Ab63 合约,根据艺术家的收入向持有者提供版税。
该生态系统庞大、动态且持续扩展,给数据调查者带来了许多待解答的问题。
这个行业的参与者可以按以下方式分类:
-
艺术家
-
市场(可能存在,也可能不存在)
-
客户/收藏家
艺术家 可以是一个个人或公司,创作稀有且独特的艺术作品,无论是画作、音乐作品,还是任何可以在线上传并注册的文件。艺术家可以选择出售作品,并在某些情况下,建立版税结构,从每笔销售中获得一定比例的收入(次级销售)。
市场 是一个平台,通常是一个去中心化应用(dApp),在这里,想要出售艺术品的艺术品所有者和有意购买的客户可以相互连接。它促进了藏品的创建,并通过视觉方式组织展示艺术作品,提供所有必要的信息并促进资金转移。这些市场已经发展成美丽的在线画廊,展示着成千上万件艺术作品。它们的收入来自平台上每笔销售所获得的部分收益,并且它们可能会收取创建或展示藏品的费用。相关的市场包括 Open Sea、Rarible、Blur 和 X2Y2。
客户,无论是收藏家还是艺术交易者,都是愿意购买艺术品以供个人欣赏或投机的个体。如果他们拥有一件艺术品,他们可能会将其出售,如果智能合约允许,二次销售价格的一部分会作为版税转给艺术家。
在这个结构中,市场是可选的。艺术家可以直接铸造他们的系列并进行销售,尽管这种方式需要大量的专业工作来吸引潜在买家。市场在这一过程中扮演了这个角色。
艺术市场在不断发展,未来可能会有新的参与者出现。
数据提取
让我们通过考虑两个案例来讨论数据提取过程。
无聊猿系列案例
最著名的数字艺术作品之一是无聊猿游艇俱乐部(BAYC)NFT。截至本文撰写时,它已产生了 1,307,484 个以太坊的交易量。这个 NFT 的用途是作为游艇俱乐部的会员卡,授予持有者专享的会员福利。创建这一系列作品的公司叫做 Yugga Labs,并发行了一种名为 Ape Coin 的代币。基于这一系列作品在数字艺术市场中的重要性,我们将通过它来了解 NFT 艺术世界中的数据。
根据无聊猿系列网页(boredapeyachtclub.com/#/provenance),该系列地址是0xBC4CA0EdA7647A8aB7C2061c2E118A18a936f13D:

图 4.10 – BAYC 的地址网页
每个无聊猿都会通过其代币 ID 来标识。让我们以代币 ID 6633 作为研究样本进行进一步分析——这可以在Chapter04/Art.ipynb中找到。
使用以下脚本,我们可以找到持有者的地址:
baContract.functions.ownerOf(6633).call())
我们可以使用任何支持查询特定地址的 API,来搜索 Bored Ape 6633 到当前持有者的转账历史。在笔记本中,我们已经回顾了从 Covalent API 获取的响应的快速搜索。
关于区块链调查的说明
Nick Furneaux 在提供区块链调查提示时建议:“在做笔记时,使用地址的前五或六个字符。比特币、以太坊或任何使用私钥作为地址系统的加密货币的长地址,对于人眼来说是复杂的。只使用前五或六个字符,使得字符串更容易处理,如果你再次看到它时也更容易识别。”
请参阅示意图,展示 Bored Ape 6633 到当前持有者(内马尔·儒尼奥尔)的最后三次转移。请注意,我们使用了地址和哈希的所有字符,出于编辑目的,但 Nick Furneaux 的建议已被证明非常有用:

图 4.11 – BAYC 代币 6633 的最后三笔交易总结
如果我们搜索该代币的最后一次转移,将得到以下交易哈希和详细信息(如在 Etherscan 上所示):

图 4.12 – 分析中的交易在 Etherscan 的视图
在市场平台中可以找到一个非常用户友好的代币资料页面。例如,对于该代币,我们可以通过以下链接访问 OpenSea 的网站:opensea.io/assets/ethereum/0xbc4ca0eda7647a8ab7c2061c2e118a18a936f13d/6633。
相关信息如支付价格、代币的交易次数等,可以通过交易的日志提取,方式与我们在 区块链游戏 – GameFi 提案 部分分析的相同。
在接下来的部分,我们将探讨在这一新兴行业中发挥重要作用的市场平台。
市场平台
正如预期的那样,市场平台目前在数字艺术生态系统中扮演着重要角色,这导致了与市场相关的数据分析需求激增。为了满足这一需求,数据服务逐步加入了更多数据点,并预处理原始日志表格,简化信息处理,方便分析师更轻松、更快捷地获取信息。
在 Dune 中,有一个名为 nft.trades 的特定表格,索引了主要市场平台的交易。根据其文档(dune.com/docs/data-tables/spellbook/top-tables/nft.trades/),可以找到以下市场平台的交易数据:
-
OpenSea
-
Rarible
-
SuperRare
-
CryptoPunks
-
基础
-
LooksRare
此外,在 Increment 中,有一个名为 reports.nft_sales_all_chains 的特定表格,涵盖了它所索引的 20 条不同区块链上的 46 个市场平台。NFT 活动不仅限于以太坊。根据每条链的优势,用户会将资产从一条链转移到另一条链上,企业也会构建产品,充分利用每条链的优势。作为分析师,我们必须准备好进行或解读多链分析,这时这个 Increment 工具尤其有用。
区块链带来的另一个额外功能是能够直接分配版税到二级市场的销售中。由于艺术家的地址是已知的,并且永远与该艺术作品相连接,像 OpenSea 或 Rarible 这样的市场平台在其智能合约中设置了将艺术品二级销售部分收入支付给作者的功能。这在物理世界中通常通过一个中介解决,中介通常会收取艺术家收入的相当一部分。在 Web3 中,这一过程是通过智能合约来设计的。
每个市场平台都有自己的规则,而且这些规则可能会根据市场环境的变化而有所不同。有些市场平台将版税分配功能标记为可选项,因此某些收藏品可能在二级销售中无法为作者带来收入。但平台始终会生成收入。
相关的百分比信息可以在每个市场平台的文档中找到,因此需要仔细查阅文档以做出正确的查询:
-
OpenSea:
docs.opensea.io/docs/10-setting-fees-on-secondary-sales -
Rarible:
docs.rarible.org/overview/tokens-fees-royalties/#royalties
Dune 有一个fees表格,我们可以使用以下 SQL 片段进行查询:
select count (distinct (tx_hash)) as transactions,
sum (platform_fee_amount_usd) as platform_fee,
sum (royalty_fee_amount_usd) as authors_royalty,
sum(royalty_fee_amount) as total_royalties
from nft.fees
where blockchain='ethereum'
and nft_contract_address= '0xbc4ca0eda7647a8ab7c2061c2e118a18a936f13d'
and project = 'opensea'
另一种方法是查询trades表,并根据销售价格计算fees百分比:
select count (distinct ("tx_hash")) as transactions,
sum ("original_amount")*0.025 as platform_fee
from nft.trades
where nft_contract_address= 0xbc4ca0eda7647a8ab7c2061c2e118a18a936f13d
and platform = 'OpenSea'
这些查询的结果,和许多其他指标一样,可以在 Dune 仪表板上找到,网址为dune.com/gabriela/chapter-4-nft。
最低价和洗盘交易
让我们来看一些对艺术行业中的 NFT 相关的其他指标。
最低价:如在第一章中所预测,某一集合的最低价可以定义为在某一时刻该集合中任一 NFT 的最低价格。这个价格回答了一个问题:以买家的身份进入该集合需要多少资金,同时不考虑可能增加价格的其他因素,如稀有性、卖方身份等。
这个数值可能会受到异常值的较大影响,并且在集中式所有权的集合中可能会被操控,也就是说,如果一个小团体拥有该集合的大量 NFT,并且流动性较低,这个数值可能会受到很大影响。流动性资产可以快速转化为现金,并保持其市场价值。避免受到异常值影响的一个方法是,将多个市场的价格进行比较,或在一定时间内计算中位数。
获取 BAYC 集合中位价格的查询可能如下所示:
with cte1 as (select min ("amount_original") as min_price,
"project" as platform, ----platform
"block_time"
from nft.trades
where nft_contract_address= 0xbc4ca0eda7647a8ab7c2061c2e118a18a936f13d
and block_time > timestamp '2022-01-31 00:00:00'
and block_time < timestamp '2023-01-31 00:00:00'
and blockchain= 'ethereum'
and project in ('looksrare','opensea')
group by project, block_time)
select approx_percentile(min_price, 0.5) as floor_price , platform ------ avg (min_price)
from cte1
group by platform
查询的结果可以在以下图表中查看。该图表的实时版本可以在本章节的 Dune 仪表板上找到,网址为dune.com/gabriela/chapter-4-nft:

图 4.13 – 2022 年最低价
该指标的另一个信息来源是专门的网页,如 NFT Bank (nftbank.ai/),以及从各种来源汇总数据的预言机,这些数据来源包括链上和链下数据。尽管我们无法控制这些来源如何计算价格,但它们可以作为我们计算的有用对比点。关于 Chainlink 对最低价格的回应,您可以参考Chapter4/Art.ipynb。
洗钱交易:洗钱交易是人为地围绕某个资产创造交易,以抬高其价格。这是一种市场操纵行为,在许多司法管辖区内,非加密金融市场中的洗钱交易被视为非法。如果我们应用相同的标准,洗钱交易可以被视为一种欺诈行为,因为价格并不反映真实需求,而是项目方的操控结果。项目方的目标之一是围绕某个收藏品制造错失恐惧症(FOMO)。例如,通过提高某个收藏品的地板价格并使其出现在市场排名中,可以在潜在买家中营造一种紧迫感。另一个目标可能是从市场推出的激励计划中获利,以吸引用户。
@hildobby 撰写的两篇优秀文章强调了洗钱交易在 NFT 世界中的广泛存在,并且它可能在分析过程中对我们的指标产生重大影响。作者提出了一些基本检查方法来识别洗钱交易:
- 当买方和卖方地址相同:

图 4.14 – 洗钱交易前提 1
- 当两个地址的所有者在这两个地址之间重复转移相同的 NFT 时:

图 4.15 – 洗钱交易前提 2
- 如果相同的地址购买或出售相同的 NFT 超过三次:

图 4.16 – 洗钱交易前提 3
- 如果买方和卖方是由同一个“母”地址提供资金:

图 4.17 – 洗钱交易前提 4
相关文章可以在 Dune 社区博客中找到。你可以通过点击仪表板标题获取查询:dune.com/hildobby/nfts-wash-trading。
Dune 还有一个名为 nft.wash_trades 的表,专门根据前面描述的洗钱交易标准,详细列出每一笔交易。该表的列说明可以在这里查看:
| 标准 | 列名 | |
|---|---|---|
| 1 | 当买方和卖方地址相同 | filter_1_same_buyer_seller |
| 2 | 当两个地址的所有者在这两个地址之间重复转移相同的 NFT | Filter_2_back_and_forth_trade |
| 3 | 如果相同的地址购买或出售相同的 NFT 超过三次 | Filter_3_bought_or_sold_3x |
| 4 | 如果买方和卖方由同一个“母”地址提供资金 | filter_4_first_funded_by_same_wallet |
表 4.4 – nft.wash_trades 相关列
最后一列包含了 is_wash_trade 标志,该标志可以是 true 或 false。通过简单的查询,我们可以检查任何项目是否存在洗盘交易,或者计算项目中洗盘交易的百分比。例如,以下查询用于查看 BAYC 项目的洗盘交易百分比:
with is_wash as (select count (distinct tx_hash) as wash_trades, nft_contract_address
from nft.wash_trades
where is_wash_trade = true
and nft_contract_address= 0xBC4CA0EdA7647A8aB7C2061c2E118A18a936f13D
group by nft_contract_address),
total_tx as (
select count (distinct tx_hash) as wash_trades_total, nft_contract_address
from nft.wash_trades
where nft_contract_address=0xBC4CA0EdA7647A8aB7C2061c2E118A18a936f13D
group by nft_contract_address)
select wash_trades, wash_trades_total, (CAST(wash_trades AS double) / CAST(wash_trades_total AS double))*100 as wash_trading_percentage
from total_tx t
left join is_wash i
on t.nft_contract_address=i.nft_contract_address
结果显示,13% 的交易符合此处列出的一个或多个洗盘交易条件:

图 4.18 – BAYC 项目的洗盘交易
Dune 提供的这个数据库是研究项目投资前的绝佳来源。
由 Mayukh Mukhopadhyay 和 Kaushik Ghosh 撰写的论文《非同质化代币的市场微观结构》提供了完整的附加动机和模式列表,并对洗盘交易模式的复杂程度进行了分类,参考文献中有更多阅读内容。
反洗钱(AML)措施的相关说明
洗钱和恐怖融资可能与我们的工作看似无关,但识别异常资金流动在很大程度上依赖于数据分析,政府对 Web3 世界的关注日益增加。
艺术品在过去曾被用作洗钱的渠道。在传统艺术市场中,画廊、拍卖行、经销商等不同实体互动并拥有支持定价的知识,形成一个相对受控的环境。然而,Web3 市场故意更加开放,任何人都可以创建并销售一个收藏品,而无需中介。价格由供需关系决定,价值主观波动。反洗钱从业者看到在这一环境中可能会发生洗钱的风险。
反洗钱(AML)条款试图避免的犯罪行为是严重的,当出现一些异常模式时,分析师应该保持警觉。可疑模式的例子可能包括某些 NFT 的地板价格持续异常,或洗盘交易的情况。美国政府最近发布的一份名为《通过艺术品交易促进洗钱和恐怖融资研究》的报告提到了洗盘交易,作为一种自我洗钱的方式,文中提到:“此外,NFT 可以用于进行自我洗钱,犯罪分子可能使用非法资金购买 NFT,并与自己进行交易,以在区块链上创建销售记录。然后,该 NFT 可以卖给一个不知情的个人,后者用与先前犯罪无关的干净资金支付给犯罪分子。”
总结
在本章中,我们深入探讨了 NFT 的世界,研究了其结构,并深入了解了获取数据的三种关键应用场景。我们对游戏应用场景进行了深度分析,特别是《狼游戏》的案例分析。此外,我们还研究了 ENS,阐明了其在在线身份中的作用。最后,我们进入了广阔且不断发展的艺术生态系统,涵盖了艺术家和市场的活动,并生成了与地板价和洗盘交易相关的指标。在所有这些案例中,我们结合了从交易数据中提取的指标,并在 Dune 仪表板(https://dune.com/gabriela/chapter-4-nft)上展示,以及本书 Jupyter 笔记本中的状态数据。
需要注意的是,我们在这里探讨的应用程序只是冰山一角。NFT 的生态系统极为多样,我们可能会遇到要求分析 NFT 在其他各种领域中的应用,比如时尚、特定事件的出席证明协议(POAPs)、正在迁移的政府注册信息,甚至是非命名的机票,如 TravelX 所示。
能够理解这些不同的 NFT 产品提出了有趣的问题,开启了新的探索路径。如果我们将链上数据与 Web2 数据结合起来,就像一些项目正在做的那样(例如,www.spindl.xyz/),我们可以增强特定 NFT 集合参与者的用户基础画像,提升社区参与度,开发更有针对性的功能,并根据数据驱动的决策来改进我们的产品。
在即将到来的章节中,我们将把重点转向去中心化金融(DeFi)行业,在那里我们将探索其产品及其影响。
进一步阅读
为了补充本章内容,以下链接可能会有所帮助:
-
技术介绍
-
了解更多关于 EIP 1155 提案的信息:
ethereum.org/en/developers/docs/standards/tokens/erc-1155/ -
了解更多关于 EIP 721 提案的信息:
eips.ethereum.org/EIPS/eip-721 -
Open Zeppelin 的实现:
docs.openzeppelin.com/contracts/3.x/api/token/erc721#ERC721 -
如何在 Google Colab 中使用 Web3.py 构建、部署和铸造 NFT。请查看以下四个视频:
-
构建 Solidity 0.8.12 NFT 智能合约 2022:
www.youtube.com/watch?v=SQ-chPSNgGw&list=PLw-9a9yL-pt0tD7ZBci5ybHy-T2XuHBtV&index=41 -
用 Python 编译 NFT 智能合约:
www.youtube.com/watch?v=HOJ-Xl9_FYg&list=PLw-9a9yL-pt0tD7ZBci5ybHy-T2XuHBtV&index=42 -
使用 Python 部署 NFT 智能合约:
www.youtube.com/watch?v=lL5s9FDYo64&list=PLw-9a9yL-pt0tD7ZBci5ybHy-T2XuHBtV&index=44 -
使用 Python 与 NFT 智能合约交互:
www.youtube.com/watch?v=DjMoJEnnvXs&list=PLw-9a9yL-pt0tD7ZBci5ybHy-T2XuHBtV&index=45
-
-
-
游戏:
-
Covalent 对 Game Fi 领域的有趣分析:
www.covalenthq.com/blog/gamefi-ebook/ -
对游戏 NFT 的有趣分析:
dune.com/sunflower_land/analytics
-
-
身份
-
艺术:
-
耐克如何通过 NFT 获得成功。(n.d.)。新经济的区块链数据 | Covalent:
www.covalenthq.com/blog/how-nike-won-with-nfts/ -
耐克公司报告 2022 财年第四季度及全年财务结果。(2022 年 6 月 27 日)。NIKE, Inc. - 投资者关系:
investors.nike.com/investors/news-events-and-reports/investor-news/investor-news-details/2022/NIKE-Inc.-Reports-Fiscal-2022-Fourth-Quarter-and-Full-Year-Results/default.aspx -
传统的贝尔维德尔博物馆与克里姆特的 NFT:一份数字爱情宣言。(n.d.)。贝尔维德尔博物馆维也纳 | 首页:
www.belvedere.at/en/digital-declaration-love -
Rihanna 的歌曲:
cdn.anotherblock.io/payouts/2.0/bbhmm.pdf -
Rihanna 歌曲的 Etherscan 页面:
etherscan.io/address/0xCB8399D84e17fD5B4e955C716647c7BB2C35Ab63 -
nft.trades表的文档:dune.com/docs/tables/spells/nft.trades/ -
关于洗盘交易的更多信息,Dune 社区博客中的链接:
community.dune.com/blog/nft-wash-trading-on-ethereum和dune.com/blog/wash-trading-2-blur -
Mukhopadhyay, Mayukh 和 Ghosh, Kaushik. (2021). 非同质化代币的市场微观结构。SSRN 电子期刊。10.2139/ssrn.3934676。网址:
www.researchgate.net/publication/356192381_Market_Microstructure_of_Non_Fungible_Tokens -
通过艺术品交易促进洗钱和恐怖融资的研究:
home.treasury.gov/system/files/136/Treasury_Study_WoA.pdf第 25 页 -
Furneaux, Nick. 调查加密货币,第十章。区块链证据的理解、提取与分析,Wiley,2018
-
一些最佳的用户覆盖、用户保持和收入分析可以在
0xatomist.notion.site/找到。 -
一个优秀的 Dune 用户,值得关注进行 NFT 分析的是
@``hildobby:dune.com/hildobby
-
第五章:探索 DeFi 分析
当前 Web3 领域中,推动交易最多的有两类产品:我们在第四章中讨论过的 NFT,以及在本章中将深入探讨的去中心化金融(DeFi)。
DeFi 这个名字来源于与当前金融系统的中心化特征相对立。根据 CoinGecko 的书籍《如何参与 DeFi:初学者指南》,"去中心化金融(DeFi)是一项允许用户利用金融服务,如借贷、借款和交易,而不依赖中心化实体的运动。" DeFi 并非单一的产品,而是一系列旨在满足 Web3 领域金融需求的项目。
这些项目利用了可组合性的概念,即在其他方创建的部分基础上进行构建。这个概念通常被形象地比喻为用乐高积木搭建,在这里开发者将不同的组件组合起来,构建新的基础设施。
DeFi 引入了曾经是中央银行专属的产品,例如新币的铸造。目前,一些协议通过收取费用使资金的借贷和借款成为可能,这些费用完全依赖于池子的流动性,而非外部因素。这些项目提供不同程度的去中心化。例如,在之前提到的铸币服务中,我们可以遇到由一个名为 Tether 的中心化实体发行的稳定币,或一个去中心化的选项,如 DAI,这是一个由一组智能合约组成、没有中央权威的协议。
DeFi 还扩展了它的产品范围,涵盖了其他原生 Web3 业务,如链间桥接和闪电贷款。我们将在后续部分详细解释这些内容:

图 5.1 – 银行服务与区块链服务
金融服务在不同人群中的差异并不新鲜,许多 DeFi 项目旨在扩大金融服务的覆盖面,凡是有互联网接入的地方,就可以实现这些服务。作为 Web3 分析师,我们可以利用 Web3 的主要特点之一——透明性——来解锁更多的价值,并帮助这些项目实现可持续发展。传统上只有 VIP 分析师能够接触到的金融数据,或者那些在不同时间释放到市场的数据,现在可以公开供我们阅读、结合并提取出有价值的洞察,供我们使用。区块链已经使信息获取变得民主化;剩下的任务是我们学习如何解读这些信息并提取出可操作的洞察。
要通过我们的工作创造价值,理解不仅仅是生成的数据,还有 DeFi 的业务流程至关重要。就像我们在第四章中做的那样,我们将深入探讨基础协议的指标,提供关于每个协议结构和用户组成的快速见解,同时还会讲解那些解释一个项目如何产生收入、吸引客户、应对潜在威胁以及其他相关方面的指标。
本章将探讨以下内容的数据结构和业务逻辑:
-
ERC-20 代币和稳定币
-
去中心化交易所(DEX)和聚合器
-
借贷(并附有关于闪电贷的评论)
-
桥接
这份产品清单并未涵盖所有的去中心化金融(DeFi)领域。还有许多其他的产品,如去中心化衍生品、保险、治理、彩票等。
技术要求
第四章中列出的技术要求同样适用于本章。我们将使用 SQL 表格服务中的索引数据,如Dune Analytics、Increment和Flipside。为了跟进,请通过 第二章中的链接,在这些平台中开设账户。交易数据通过 SQL 服务查询,具体语法取决于查询引擎。
你可以在本书的 GitHub 仓库中找到包含本章讨论示例的 Jupyter 笔记本,地址为 github.com/PacktPublishing/Data-Science-for-Web3/tree/main/Chapter05。我们建议阅读 Chapter05 文件夹中的代码文件以跟进学习。
稳定币和其他代币
根据 Coinbase 的说法,“稳定币是一种与‘稳定’储备资产(如美元或黄金)挂钩的数字货币。” 由于比特币或以太坊等未挂钩的加密货币波动性较大,稳定币已成为可靠的交换媒介。根据撰写时的市值,主要的稳定币列在图 5.2中:

图 5.2 – 加密货币恐慌稳定币排名
稳定币是与外部资产的价值挂钩的特定类别代币,提供价格稳定性。稳定币有多种类型,包括那些价值与政府发行的货币(如美元,称为法定货币)、加密货币和商品(如黄金)挂钩的稳定币。为了保持“挂钩”,稳定币团队探索了多种路径。可以在图 5.2中的“机制”一栏看到这一点。
主要的稳定币是与法定货币挂钩(“法定支持”),意味着发行此类代币的公司只有在其存有备用资金的金融机构中时,才会发行这些代币。USDT 和 USDC 就是这样的稳定币的例子。
加密货币支持的稳定币依赖于智能合约协议,这些协议发行由一篮子其他加密货币支持的稳定币。这些协议通过控制利率来平衡供需,从而确保价格稳定,并影响买卖双方的行为。系统通常是过度抵押的,以确保在高波动时价格稳定,主要作为借贷系统运作。此机制的主要例子是名为 DAI 的代币,它由 MakerDAO 发行,目前由一系列中心化和去中心化资产支持,如 USDC、以太坊、包装比特币等。
稳定币可以被创建以反映支持它们的加密货币的价值,或模仿法定货币的价值。前者的一个例子是包装版本的资产,通常称为“包装代币”,它是基础资产的表示,通常是加密货币或数字资产,已被代币化并使其与特定区块链或网络兼容。“包装”过程涉及将原始资产(例如,比特币)锁定在其原生区块链上,然后在另一个区块链上发行相应的等值代币,如以太坊。这就是Wrapped Bitcoin(WBTC)的运作方式,它在以太坊区块链上代表比特币,使得比特币能够在以太坊生态系统内用于去中心化应用、DeFi 平台和其他目的。
尽管非稳定代币在历史上早于稳定币出现,但通过学习稳定币,更容易理解代币的概念。代币仅仅是区块链上的一种价值表示,这种价值可以来源于任何理由。例如,有些代币代表着对特定项目的所有权、服务的访问权限,甚至作为一种迷因或文化运动的一部分。值得注意的是,一些代币,如始于迷因的狗狗币,已经取得了显著的市值,展示了加密货币领域代币的多样性。如今,这种迷因币已经是市值排名第八的加密货币。
现在我们已经了解了业务案例,让我们深入探讨数据结构。
了解代币、原生资产以及 ERC-20 数据结构
加密货币作为区块链的原生资产,如比特币链中的 BTC、以太坊链中的 ETH 和 Rootstock 链中的 RBTC。其主要功能通常是支付网络上的交易费用(gas 费用),并激励验证者/节点维持加密货币网络的安全性。
相比之下,代币是在现有区块链上创建的,并不是区块链本身的原生资产。稳定币、池代币以及以太坊生态系统中的所有 ERC-20 代币都是代币的例子。
开发者利用 ERC-20 标准及其后续演进来构建代币,该标准为功能性代币提供了标准化框架,并确保它们的可替代性。回顾一下,可替代性是指资产或代币在价值上相同,可以一对一交换,且同类型的代币单位之间没有区别。ERC-20 标准最初于 2015 年推出,并在 2017 年通过以太坊创始人 Vitalik Buterin 和以太坊开发者 Fabian Vogelsteller 撰写的以太坊改进提案(EIP)获得官方认可。
跟随这些方法和事件的智能合约被称为 ERC-20 兼容合约,它将维护已发出代币的注册信息,因此分析师了解其基本特征非常重要。
我们将遇到的函数方法如下:
-
totalSupply(): 返回合约中的代币总供应量。 -
balanceOf(): 用于读取地址余额。 -
transfer(): 将代币从发送者的账户转移到另一个账户。 -
transferFrom(): 用于消耗授权额度。该函数由支出者调用,意味着进行两个操作——即转账支出的金额并减少相应的授权额度。 -
approve(): 允许支出者从代币持有者账户中多次提取资金,最多为授权的金额。 -
allowance(): 返回代币持有者账户中允许提取的金额。
可以找到mint和burn函数,它们根据特定的业务逻辑修改代币的总供应量。以下是一些可选的函数:
-
name(): 返回代币的名称 -
symbol(): 返回代币的符号。 -
decimals(): 返回代币使用的十进制位数。
这里是一些重要的事件:
-
transfer: 该事件由transfer()函数触发。关于铸造和销毁的相同考虑适用于第四章,如果转账来源地址为0x0000,,我们可以将其解释为铸造事件。如果该地址或0x000dEad出现在交易的to部分,则可以视为销毁转账。铸造意味着代币的创建,而销毁则意味着将代币发送到不可恢复的地址,将其从流通中移除。该函数的哈希值为0xddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df5``23b3ef。 -
approval: 该事件由approve()函数触发,包含授权值和支出者地址。
实际操作示例
现在我们了解了基础知识,接下来进入 Jupyter notebook(Chapter05/Stablecoins.ipynb),在其中我们将连接到 DAI 合约(0x6B175474E89094C44Da98b954EedeAC495271d0F)并提取公共视图信息。
视图函数意味着它不会改变状态数据,因此可以在单个节点上执行,而不需要每个区块链节点都运行它。这种函数不会生成交易,也不会消耗 Gas。
要检查 DAI 合约,我们将使用 DAI 的 ABI,它可以在本书的仓库中找到。首先,使用以下代码片段提取某个地址的余额:
daiContract.functions.balanceOf('0x60FaAe176336dAb62e284Fe19B885B095d29fB7F').call()*10**-18
相关的 ERC-20 事件存储在交易日志中。让我们分析 0x2a9317882853dc5e0193a76dab76b29e4dc8045718af7925d8d166cdb0eec637 交易,该交易涉及两地址之间转账 120 DAI:

图 5.3 – DAI 转账交易(来源:https://etherscan.io/tx/0x2a9317882853dc5e0193a76dab76b29e4dc8045718af7925d8d166cdb0eec637)
如果我们搜索交易日志,我们将获得以下信息:

图 5.4 – DAI 转账交易日志(来源:https://etherscan.io/tx/0x2a9317882853dc5e0193a76dab76b29e4dc8045718af7925d8d166cdb0eec637)
我们在这里看到的数据属于以太坊0x6b175474e89094c44da98b954eedeac495271d0f。
原始日志结构如下所示:
| 事件名称或主题 [0] | 转账(或0xddf252ad1be2c89b69c2b068fc 378daa952ba7f163c4a11628f55a``4df523b3ef) |
|---|---|
| 来源 - 主题 [1] | 0xc6DA6f76a389Df871fffad8bb5049cbcF6b7015F |
| 目标 - 主题 [2] | 0x762EcaaF67097b3eb66a9a6904f42b835b52DC15 |
| wad - 主题 [3] | 0x0000000000000000000000000000000000000000000000068155a43676e00000(或 120000000000000000000) |
表 5.1 – 原始日志结构
wad 是一个具有 18 位精度的十进制数字,它被表示为整数。在此交易中,它表示转账的代币数量,即 120。如果我们将 wad 值粘贴到一个十六进制到十进制的转换器中,如 www.rapidtables.com/convert/number/hex-to-decimal.xhtml,它将显示带有 18 位数字的十进制表示。
我们研究的所有数据供应商在 第二章 中都有特殊的表格,用于存储具有不同预处理级别的交易日志。最基本的版本是原始日志,经过更多筛选的版本只显示 ERC 20 代币转账和转账时代币的价格。其中一个例子是 Flipside,它有一个名为 core__fact_token_transfers 的特定表格,包含以 'Transfer' 为名称的所有以太坊区块链事件;这指代代币地址。类似地,Dune Analytics 也提供了一个类似的表格,名为 erc20_ethereum.evt_Transfer,Increment 有一个名为 token balance 的模型。
通过聚合这些数据,我们可以得出各种各样的指标。让我们通过利用 erc20_ethereum.evt_Transfer 表格来看一下 DAI 当前供应量的计算:
WITH current_supply AS
(
SELECT
cast (tr.value as double)/ 1e18 AS supply
FROM erc20_ethereum.evt_Transfer tr
WHERE "contract_address" = 0x6b175474e89094c44da98b954eedeac495271d0f -- DAI
and tr."from" = 0x0000000000000000000000000000000000000000
UNION ALL
SELECT
- cast (tr.value as double)/ 1e18 AS supply
FROM erc20_ethereum.evt_Transfer tr
WHERE "contract_address" = 0x6b175474e89094c44da98b954eedeac495271d0f -- DAI
and tr."to" = 0x0000000000000000000000000000000000000000
)
select sum (supply)/1000000000 as supply
from current_supply
在这个查询中,我们通过聚合 DAI 合约地址内的转账来计算 DAI 当前的供应量。这里,我们执行以下操作:
-
查询使用
current_supply来构建数据。 -
CTE 的第一部分通过将转移的金额(从 wei 转换为 DAI)相加来计算总供应量的增加,其中 DAI 被转移 从 零地址(
0x0000000000000000000000000000000000000000)。这代表了新 DAI 代币的创建。 -
CTE 的第二部分通过将转移的金额(也从 wei 转换为 DAI)相加来计算总供应量的减少,其中 DAI 被转移 到 零地址。这代表了 DAI 代币的销毁或从流通中移除。
-
主查询通过将总供应量的减少从总供应量的增加中减去(即供应增加 - 供应减少)来计算最终的总供应量。
-
结果除以 1,000,000,000 以将其转换为十亿 DAI。
总结来说,这个查询通过考虑铸造和销毁交易,计算 DAI 代币总供应量的净变化,然后将结果转换为十亿 DAI。
我们在以下仪表盘中提出了额外的指标逻辑:dune.com/gabriela/dai-cockpit。此外,还有一个很棒的开源稳定币仪表盘,网址是 https://dune.com/hagaetc/stablecoins。
这个相同的分析可以应用于任何 ERC-20 代币;它不仅限于稳定币。例如,如果我们以 MKR 代币为例,可以在 dune.com/livethelife/mkr 找到一个出色的开源仪表盘。
ERC-20 代币的一个关键特点是它们在以太坊网络中可以无缝互换。这一特点在去中心化交易所(DEX)的运行中发挥着重要作用。DEX 利用 ERC-20 标准,允许用户直接从他们的钱包中交易各种代币,无需中介。ERC-20 代币与 DEX 之间的联系构成了去中心化金融(DeFi)空间的基石,使用户能够进行交易、投资并参与金融活动。
理解 DEX
加密货币可以通过多种方式进行交换,包括点对点(P2P)交易、中心化交易所(CEX)和 DEX。每种方式都有其优势和特点:
-
P2P:在这种方式中,双方直接在彼此之间买卖加密货币,不涉及中介。它优先考虑隐私,并且提供多种支付选项,使全球用户都能使用。然而,为了确保交易的完成,出现了一些角色,他们可能作为中介收取少量费用,例如托管服务、评价平台或争议解决服务。
-
CEX:该方式为在其平台上拥有账户的用户提供加密货币交换服务。它主要通过订单簿匹配买家和卖家,市场做市商和交易者在其中下单。CEX 通过每笔交易收取交易费用来获得收入。主要的 CEX 包括 Binance、OKX、Coinbase 和 Crypto.com。CEX 还会验证每个开户人的身份,遵循相关国家的法规。这些交易所用户友好,提供流动性和丰富的交易对。它们通常是许多进入加密市场用户的起点。“中心化”一词指的是交易所对其中交换的资金的控制。这有几个含义:由于用户并不掌管自己的资产,如果 CEX 遭到攻击或因任何原因(如银行挤兑)破产,就有资金丧失的风险。
-
DEX:DEX 通过智能合约运行,不涉及第三方实体,优先考虑用户控制、隐私和安全性。它允许用户在交易完成之前,保持对钱包中资金的控制,从而进行资产交换。DEX 在加密市场中越来越受欢迎,在 2021 年牛市中,其交易量甚至超过了 CEX。然而,相比 CEX,DEX 的流动性通常较低。
现在,让我们进一步分析一下 DEX 的一些特点:
-
资产托管:用户不将资产托管给第三方。
-
无需身份验证:用户可以自由地与去中心化交易所(DEX)互动,无需任何形式的身份验证。所需的仅仅是一个地址来连接到 DEX。
-
高额的矿工费:与 CEX 交易相比,DEX 交易通常会产生更高的区块链矿工费。
-
流动性问题与滑点:滑点是指资产的预期价格与交易执行时实际价格之间的差异。由于流动性由用户提供而非集中式实体,交易的大小可能会影响资产的价格。当大宗交易执行时,它可能导致价格朝不利方向波动,从而导致滑点。这意味着交易者在购买时支付的价格稍微高于预期,或在卖出时收到的价格稍微低于预期。滑点是去中心化金融(DeFi)交易中的现实,尤其是在流动性较差的市场中。
-
无常损失:这是流动性提供者在自动化市场制造商(AMM)平台中面临的潜在风险。当流动性提供者向流动性池中添加资金时,他们贡献了用于在平台上交易的资产。随着交易的进行,池中资产的相对价值可能会因市场波动而变化。如果池中某一资产的价格相对于另一资产发生显著变化,流动性提供者可能会经历无常损失。这种损失是“无常的”,因为只有当流动性提供者决定从池中提取资金时,它才会真正体现。
-
复杂的用户体验与学习曲线:与 DEX 协议的交互对于 DeFi 用户来说仍然具有挑战性,整体用户体验可能需要改进。诸如滑点或无常损失等概念仍然会影响交易体验。
-
漏洞与利用:与任何基于智能合约的系统一样,DEX 也可能容易受到漏洞和安全利用的影响。
要分析一个 DEX 的分析数据,我们需要理解流动性锁定的位置、交易对是如何组织的,以及智能合约是如何生成收益的。这样,我们就能迅速接近相关的智能合约。
实际操作示例 – 流动性池与 AMM
为了理解去中心化交易所(DEX),需要引入两个重要概念:流动性池和 AMM。DEX 使用流动性池和 AMM 来促进交易活动,也称为交换。
流动性池是允许用户与其交换代币的代币储备。任何人都可以通过提供必要的资金来开设一个池,而无需寻求任何中央权威的许可。流动性在曲线价格中进行分配,算法根据该曲线放置买单和卖单以执行交换。Chainlink 将AMM定义为“算法化的‘货币机器人’,让个人交易者轻松买卖加密资产。与传统订单簿直接与其他人交易不同,用户通过 AMM直接进行交易*。”
一个突出的去中心化交易所(DEX)是Uniswap,它使用流动性池和 AMM。其登录页面如下所示:

图 5.5 – Uniswap 的首页(来源:https://app.uniswap.org/#/swap)
Uniswap 有一个池仪表盘,网址为info.uniswap.org/#/pools,其中包含一些关于活跃流动性池的基本分析。在撰写时,TVL和交易量排名第一的池是 USDC/ETH 交易对(https://info.uniswap.org/#/pools/0x88e6a0c2ddd26feeb64f039a2c41296fcb3f5640):

图 5.6 – 所有池仪表盘
该池的智能合约地址是etherscan.io/address/0x88e6a0c2ddd26feeb64f039a2c41296fcb3f5640。
通过在Chapter05/Liquidity_pool.ipynb中以编程方式探索池的状态数据,我们可以使用池的 ABI 并通过以下代码片段读取智能合约数据,从而识别出构成该池的代币:
poolContract.functions.token0().call()
poolContract.functions.token1().call()
结果如下:
-
代币 0:
0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48,即 USDC -
代币 1:
0xC02aaA39b223FE8D0A0e5C4F27eAD9083C756Cc2,即 wETH
这两者都是稳定币,其中一个与美元挂钩,另一个则是以包装形式存在的原生以太坊资产。
要获取每个代币的锁仓余额,我们可以使用erc_20.abi,它可以在本书的 GitHub 仓库中找到,并使用以下代码片段查询池:
web3.eth.contract(address=token0, abi=erc_abi)
更多关于可用视图函数的信息可以在文档中找到:docs.uniswap.org/contracts/v3/reference/core/interfaces/pool/IUniswapV3PoolState。
为了从交易数据中提取信息,我们需要深入分析日志。让我们回顾一次交换交易,尝试理解我们需要的信息是如何记录的。要分析的交换交易是0x78490143b8a80b23752bd305b51c7796add5373af089059beb3920c8e431ae78,它在0x3041cbd36888becc7bbcbc0045e3b1f144466f5f池中执行,池内的交换是 USDC 和 USDT 之间的兑换。
在 Etherscan(https://etherscan.io/tx/0x78490143b8a80b23752bd305b51c7796add5373af089059beb3920c8e431ae78/)上,我们可以看到以下内容:
-
来源或发送方:
0xaDAf0dA2F42bf54E2Ccf455F795A04ECD744138B -
目标地址:
0x3fC91A3afd70395Cd496C647d5a6CC9D4B2b7FAD(Uniswap: Universal Router)
如今,大多数交换并不会直接影响池智能合约,而是与路由器智能合约交互,例如 Uniswap 的 Universal 智能合约。路由器的任务是接收用户定义的参数(如最大滑点或交换接收方),并执行必要的交换以达成交易者的目标。路由器可以组合多个池,甚至包括 NFT 市场,并且经过优化,能找到最低价格和最低的燃气费。
交易摘要如下:

图 5.7 – 交易交换
从图 5.7中,我们可以解读出用户在一次交易中进行了 XPR 换 USDT 的操作,并随后与正在分析的池交互,将 USDT 换成 USDC。
图 5.8 显示了交易日志页面的部分快照。特别是最后一条日志包含了宝贵的信息:

图 5.8 – 交换日志
图 5.8 显示了与交换相关的信息位于池子地址的日志中。正如你在第二章中回忆的那样,topic_0是函数签名。在这种情况下,0xd78ad95fa46c994b6551d0da85fc275fe613ce37657fb8d5e3d130840159d822 是交换函数。
其他相关函数包括铸造或添加流动性功能,它的签名为0x4c209b5fc8ad50758f13e2e1088ba56a560dff690a1c6fef26394f4c03821c4f,以及销毁或移除流动性功能,它的签名为0xdccd412f0b1252819cb1fd330b93224ca42612892bb3f4f789976e6d81936496。
当流动性被添加或移除时,流动性提供者(LPs)会收到代表其在池子中份额的 LP 代币。这些 LP 代币可以在二级市场上进行交易,产生利息,并在你希望将流动性提取回 LP 时再次发送到池子中。
如果我们在 Dune 中与ethereum.logs表进行交互,就可以提取池子执行的交换次数,如下所示:
select count (*) as n_trades
from ethereum.logs
where contract_address= 0x3041cbd36888becc7bbcbc0045e3b1f144466f5f
and topic0=0xd78ad95fa46c994b6551d0da85fc275fe613ce37657fb8d5e3d13 0840159d822
另一个重要的信息是,比较一个池子与另一个可能提供相同代币交换的池子时,要考虑池子的流动性强度,特别是在进行大额交易时。当大宗交易影响到池子的储备时,就会出现滑点问题,正如我们所看到的,这会影响最终支付的价格。在这里,研究与 TVL、池子流动性等相关的指标非常重要。这些指标通常是从聚合的交易数据中计算出来的。我们在以下仪表盘中提出了一些指标逻辑:dune.com/gabriela/pool-basic-metrics。
正如我们在第二章中提到的,我们研究了存储交易日志的特殊表格,这些表格有不同程度的预处理,能够满足分析师的需求。一些链上数据提供者甚至提供了可以让我们在不编写代码的情况下查询区块链的模型。此类解码服务的例子包括 Dune 上的dex.trades表或 Covalent 上的 Increment 平台,它提供了一个拖拽式分析服务。Dune 和 Footprint 都在开发自然语言查询,以简化交易数据的基本分析。
这些表格和解码数据在不同的提供商之间可能有所不同,但最重要的是理解每个查询背后的逻辑,并熟悉日志数据的结构。这将帮助我们提取信息或根据需要将查询适应不同的表格格式,甚至在使用不同平台时,也能确保 NLP 模型返回的结果是正确的。如果我们了解业务逻辑以及数据如何在区块链上记录,我们就能够使用每个平台解决数据问题。
利用我们已经学到的知识和此处列出的 Dune Analytics 表格,我们可以创建用于跟踪所分析的 USDC/USDT 池的活动和收入的指标。表格如下:
-
一个名为
ethereum.logs的原始数据表格 -
一个名为
erc20_ethereum.evt_Transfer的中级处理表格,其中包含被签名为转账的日志 -
一个名为
dex.trades的高级解码表格
以下是位于 https://dune.com/gabriela/pool-basic-metrics 仪表盘上展示的指标背后的逻辑简要说明:
| 仪表盘中的名称 | 逻辑 |
|---|---|
| 交易数量 | 统计池智能合约日志中具有指定签名的交换数量。 |
| 交易者日志 24 小时 | 统计在池智能合约日志中,主题 0 为“swap”的主题 2 中出现的不同地址数量。 |
| 平均交换量 24 小时 | 使用 dex.trades 表格,求出池智能合约中以美元计的总量,并将其除以 24 小时内执行的交易数量。 |
| 池 TVL | 将所有池作为接收方的存款转账相加,并减去所有资金离开池的转账。 |
| 池收入 | 池的收入由手续费产生。手续费从交易对的交换量中扣除。 |
表 5.2 – Dune 仪表盘查询逻辑
历史上,DEX 通过更高的收益来激励资金流入,这导致了寻找这些优势的专业基金的出现。此外,为了避免高滑点,大额交易可能需要通过不同的池进行路由,以实现更具成本效益的交易。在单个交易中路由多个流动性池可以节省 gas 并最小化滑点。总之,聚合器作为流动性路由器和交换器而建立。
DEX 聚合器
DEX 聚合器从不同的 DEX 获取流动性,为用户提供比单一 DEX 更好的代币交换汇率。这些聚合器可以优化由滑点、交换费用和代币价格产生的成本,从而为用户提供更有利的汇率,前提是能够有效执行。DEX 通常希望与 DEX 聚合器进行集成,因为这有助于吸引更多用户和交易量。1Inch 是一个著名的 DEX 聚合器例子。
由 1Inch 团队维护的构成协议的智能合约地图可以在 dune.com/queries/2238512 查看。一个包含聚合指标的优秀仪表盘可以在 dune.com/1inch/token 查看。
此外,Increment 是由 Covalent 构建的无代码产品,拥有一个名为 Dex 的模型,其中包含跨不同链的所有 1Inch 智能合约,使分析变得更加容易。该产品的一个有价值的特点是“规范化”事件,它包括将事件签名转换为人类可读的词汇并进行标准化。每个智能合约可能会为类似的事件使用不同的名称,知道准确的名称对于查询它们是必要的。然而,Increment 对这些名称进行了标准化,从而使查询变得更加简便且具有跨平台性。另一个值得注意的特点是,它公开了由模型生成的查询,允许定制化并且便于向第三方解释模型中的逻辑。
在传统金融中,信贷、贷款和基于担保的金融服务长期以来一直是该行业的基石。去中心化金融(DeFi)也有一个关于信用和担保化的章节,现在用户可以在无需银行等中介的情况下获取信贷。我们将在下一节中进行分析。
Web3 上的借贷服务
银行接收存款,将其中一部分存储以便在所有者需要取回现金时能够偿还,另一部分则以一定的利率作为贷款提供给市场。贷款可以是有担保的或无担保的,这取决于借款人的风险。利率设置得足够高,以便为银行和存款人产生收益。某些链上协议复现了类似的机制,正如我们将在本节中描述的那样。
截至目前,主要的借贷协议仅支持有担保的贷款。这个过程类似于抵押贷款,用户提供房屋作为贷款偿还的担保。如果贷款未能全部偿还,银行将保留房屋。在这种情况下,如果贷款的担保比例未得到维持,协议将会清算担保物。
假设 Alice 想要投资一个以 USD 稳定币为基础的项目,但她的担保物是 ETH。她确信 ETH 会增值,因此宁愿不将其出售为稳定币。解决方案是一个协议,它接受 Alice 的 ETH 并借给她一个与美元挂钩的稳定币,如 DAI。一个正是如此运作的协议是 Maker,我们之前已经提到过。为了发行 DAI,协议需要提供 1.5 倍于所发行 DAI 的担保物(ETH);这就是所谓的超额担保。担保物与借出资产之间的比例被称为担保比例。通常,这些协议会收取清算费,以减少被清算的可能性。
另一个成熟的协议是Compound,它类似于一个流动性池,流动性提供者将资金供给池中以换取利息,而借款人则以债务的利息为代价借款。利率被称为年化收益率(APY),并且根据池中的流动性和需求在不同池之间有所变化。
当资金存入 Compound 时,市场制造商会收到 cTokens,这些 cTokens 代表了资金池中资金的比例,并会累积利息。cToken 是一种在生态系统内使用的加密货币代币。它们是带有利息的代币,代表用户存入 Compound 平台的加密货币金额。cToken 合约列表可以在docs.compound.finance/#developer-resources找到。
让我们探索协议0xF25212E676D1F7F89Cd72fFEe66158f541246445,它被称为cUSDCv3。
该合约有许多视图函数,所有这些函数在Lending_borrowing.ipynb笔记本中都有探讨。
一些主要函数如下:
-
numAssets(): 可用于作为抵押品的资产数量。在当前分析的情况下,有三种资产,即 ETH、wBTC 和 Matic。 -
baseToken(): 可以以抵押品为担保借贷的代币——在我们这个例子中是 USDC。 -
getAssetInfo(): 返回抵押资产的信息,例如抵押地址或 Chainlink 上的价格源地址。 -
Totalsupply(): 基础代币的总供应量加上已积累的利息。 -
getReserves(): 基础或抵押资产的余额,保护用户免受坏账的影响。我们稍后将分析坏账。 -
getUtilization(): 基础资产(即 USDC)的协议利用率。此计算的函数为TotalBorrows/TotalSupply。
还可以查询更多用于状态数据的函数;更多详细信息请参阅文档。
交易数据也非常有用,可以用来提取洞察。例如,可以通过查询抵押资产的日志来计算 TVL 和进一步的抵押信息。语法与我们在理解 DEX部分回顾过的一致。仪表板示例如下:dune.com/datanut/Compound-Finance-Deposits-and-Loans。
借贷协议通过借款人支付的利息产生收入。衡量收入生成的重要指标是协议的利用率,该指标是借款量/总价值(TVL)的结果。该比例告诉我们协议在将锁定的价值投入使用时的效率。利用率越高,效果越好。
具体来说,在 Compound 协议中,部分利息会进入其储备金,作为保险,但这种收入分配可以由协议的治理方修改,治理方是 COMP 代币的持有者。COMP 是一个 ERC-20 代币,使社区能够治理 Compound 协议。COMP 代币持有者可以参与讨论、提案并投票决定协议的变更。
在这个行业中,有一种加密原生产品应运而生,它使得零抵押的快速贷款成为可能:闪电贷。
闪电贷
闪电贷是加密原生产品,AAVE是这一领域中最著名的协议之一。闪电贷允许借款人以零抵押的方式获得贷款,前提是贷款及其利息必须在同一笔交易中偿还。如果借款人在交易中未能按时偿还贷款,整个交易将被撤销。闪电贷主要有两种用途:套利和清算。
套利涉及在不同市场中同时购买和出售相同或不同的资产,在这些市场中价格存在差异。套利者从小的价格差异中获利,但通常需要相当大的资金量才能产生显著的差异。这种做法有助于将市场恢复到平衡状态,确保相同资产的价格在多个市场中保持稳定。
在抵押品比率丧失并且贷款违约的情况下,第三方清算者可以获取抵押品进行清算。清算者代表借款人将抵押品出售给市场,偿还债务,并因完成清算工作获得清算奖金。所有这些步骤可以通过闪电贷在一笔交易中执行,并且无需任何抵押品。这些复杂的交易通常由机器人执行,机器人有助于维持 DeFi 生态系统中的流动性,并保持市场价格的稳定。
如需进一步了解闪电贷交易数据,请查看以下仪表板中的查询:https://dune.com/hildobby/flashloans。
关于协议坏账的说明
闪电贷曾被用于攻击 DeFi 协议,导致这些协议出现坏账。坏账发生在向某个交易对提供流动性的用户决定退出池时,无法取回其资金。我们来看一个例子:
-
攻击者获取了代币 A 的闪电贷。
-
攻击者将代币 A 存入去中心化交易所(DEX)或中心化交易所(CEX),并将其兑换为代币 B,这导致代币 A 的供应增加,代币 B 的流动性下降,进而推动代币 B 的价格上涨。
-
重新估值后的代币 B 随后作为抵押品用于借贷协议,以借入代币 A。由于抵押品 B 的价格被人为抬高,协议借出的代币 A 数量超过了抵押品处于均衡价格时的借贷额度。
-
攻击者以 A 代币的形式偿还贷款,保留 A 代币的盈余。当价格回归正常时,清算人试图以市场价格清算 B 代币,但这不足以覆盖 A 代币的贷款。因此,产生了坏账,最后的 A 代币供应商承担了损失。
当价格来源于单一预言机时,攻击容易得手,因为它容易受到操控。此外,闪电贷的低成本特性(不需要抵押品)使得此类攻击更加可行。
Risk DAO 创建了一个有趣的仪表盘,跟踪协议的坏账情况,使用链上数据进行监控。你可以在这里探索:bad-debt.riskdao.org/。
世界正在朝着多链环境发展,成功的链条提供差异化的产品,吸引不同的创意,这些创意最终形成了 去中心化应用(dApps)。例如,Near 以低手续费发展了 Sweat 经济,而 Avalanche 的子网使游戏能够构建自己的链上生态系统,而不需要与主链争夺 gas 插槽。随着更多协议在多个链上开放其服务,它们旨在利用每个链的优势,覆盖更广泛的用户群体。
随着不同区块链之间资金转移需求的增加,出现了被称为桥接的加密原生产品,我们将在下一节中进行探讨。
多链协议和跨链桥接
桥接是一个结构,它促进了不同区块链之间的资金和信息转移。市场将区块链分为三类:
-
L1 链是广为人知的区块链,例如比特币和以太坊。之所以被称为 Layer 1,是因为核心团队在基础层上生成了一层解决方案,以增加可扩展性。L1 的演变例子是以太坊的合并,这一事件发生在 2022 年 9 月。
-
L2 链是运行在区块链上的集成系统,旨在改善特定方面,通常专注于可扩展性。这些扩展解决方案允许主链将数据卸载到并行架构上,在那里进行处理,并将结果保存到主链上。成功的 L2 链包括 Optimism、Arbitrum 和 Polygon zkEVM。
-
侧链是连接到主区块链的新区块链。例如,Rootstock与比特币相连,允许使用以太坊虚拟机(EVM)智能合约编程,同时保持比特币的去中心化和安全性。侧链是独立的链,意味着共识方法、燃料规则和其他方面可能有所不同。
鉴于各类区块链产品的持续涌现以及这一趋势看似没有停止的迹象,用户将继续探索从一个区块链过渡到另一个区块链,以利用每个区块链所提供的独特优势。这也凸显了区块链之间桥接连接的持续需求,预计这一需求将继续保持强劲。
根据桥接的运作方式,交易结构和需要分析的数据点可能会有所不同。通常,桥接主要分为两种类型:中心化桥和无信任桥。中心化桥由一个中心实体负责桥接安全性。例如,Ronin 桥和 Multichain 桥。另一方面,无信任桥完全依赖智能合约,比如 Near 桥和 Hop 桥。
实操示例 – Hop 桥
让我们深入了解像 Hop 这样的多链桥是如何工作的。Hop 在hop.exchange/中自我描述为“可扩展的 rollup 到 rollup 的通用代币桥”。它支持 ETH 与其 L2 解决方案之间的桥接,比如 Polygon、Gnosis、Optimism 和 Arbitrum。
Hop 桥有三个核心产品:
-
Hop 代币与在每个链中铸造的底层资产的价值挂钩,其中 Hop 在 L1 链中处于活跃状态并可以兑换。
-
一个 bonder 或流动性提供者
-
自动化做市商使我们能够在 Hop 代币和目标链中的本地代币之间进行交换。
让我们考虑一个示例交易:
-
Alice 希望使用在 Optimism 上活跃的 dApp,但她的资金是 ETH。所以,为了与 dApp 互动,她需要oETH,即 Optimism 上的封装 ETH。
-
Alice 通过以下方式将她的 ETH 桥接到 Optimism:
-
桥接交易在 ETH 上发起,并将在等待时间和退出时间过后在本地桥上执行。
-
作为桥接操作的一部分,bonder 将 hop-ETH 或hETH存入 Alice 在 Optimism 上的地址,金额为桥接金额减去费用和油费。
-
-
Alice 可以将 hETH 兑换为 oETH,并与 dApp 进行交互。
-
在退出时间过去后,bonder 将收回之前提供给 Alice 的资金,并附加一小部分费用。
这是一笔桥接交易,用户可以在链之间迅速转移资金,发送一种资产到一个链中,并在另一个链中收到等价物(减去费用)。在这个示例中,我们提到了像 oETH 和 hETH 这样的代币,这些代币在每条链上被铸造和销毁,用于表示链之间的资金流动。这被称为锁定和铸造类型的桥接。
要分析桥接合约,请参考github.com/hop-protocol/hop/blob/develop/packages/core/src/addresses/mainnet.ts中提供的完整列表。该列表中包含了一些view函数。
一个有用的视图函数是l1CanonicalToken(),它提供有关桥接中锁定代币的信息。通过了解这些信息,我们可以计算 TVL,正如Bridges.ipynb笔记本中所解释的。
对于汇总的交易数据分析,了解交易结构至关重要。例如,分析0xaf6089e3d7377b5b0c4ad86e486406a19e29280410402aab71195b0995608e81哈希下的交易,涉及将 0.4378 ETH 转账到 Optimism 上的相同地址:

图 5.9 – 交易详情(来源:etherscan.io/tx/0xaf6089e3d7377b5b0c4ad86e486406a19e29280410402aab71195b0995608e81)
若要在任何数据提供商的 raw_transactions 表中找到此数据,请参考 第二章,查找签名或 TransferSentToL2 事件,该事件包括转账金额、担保人和用户:

图 5.10 – 桥接跨链交易日志 – ETH 侧
该交易与 Optimism 链有关。相关信息位于 l2canonical 代币的日志中,按照文档,wETH 的地址是 '0x4200000000000000000000000000000000000006'。在 Optimism 上的交易是:optimistic.etherscan.io/tx/0x4e76ee9b997868ba894ea9362347bfa9ed64c2aaf5b4482d6482940efbe3e738,相关日志如下所示:

图 5.11 – 桥接跨链交易日志 – OPT 侧
这些主要协议中的大多数已经被主要数据提供商索引并翻译,使得分析变得更加容易。例如,可以探索一个非常有趣的仪表板,dune.com/rchen8/Hop-Exchange,该仪表板利用了经过审查的智能合约中的事件。
Hop 还提供了一个子图,查询示例可以在文档中找到:docs.hop.exchange/v/developer-docs/subgraphs/queries。
关于 DeFi 风险和挑战的说明
DeFi 是一个年轻且不断发展的行业,面临许多挑战。数据从业者在防止黑客攻击、识别异常活动、衡量与某些决策相关的风险以及处理损失控制方面发挥着关键作用。
可能会有一些情况,我们发现自己支持政府的努力,以建立一个监管框架,为资金向该生态系统的流入铺平道路。到目前为止,监管不确定性和多样的规则仍然占主导地位。尽管有多个倡议旨在创造立法的一致性,但这仍然是一个进行中的工作。这种情况直接影响着行业,其中像存款担保这样的概念并未得到应用,导致许多用户在遭遇黑客攻击后不可恢复地失去了他们的资金。
DeFi 体验仍处于初期阶段,数据从业者可能会发现自己也在研究产品体验,以增强用户互动或教育用户如何更好地与这些产品互动。诸如 SAFE 钱包等举措旨在弥合 Web2 和 Web3 体验之间的差距。这家公司在扩展钱包功能以匹配传统家庭银行体验方面处于领先地位。
这个领域的创造机会非常广阔,数据驱动的决策至关重要。
摘要
在本章中,我们深入探讨了 DeFi 的世界,探索了该领域的核心组件和主要产品。我们的分析涵盖了多个领域,包括代币、稳定币、以及以池和 DEX 聚合为重点的去中心化交易所(DEX)、借贷协议和桥梁在促进跨链交易中的重要性。
在每种情况下,我们分析了业务流程及其如何产生收入,并利用一些数据提供者生成汇总指标。
虽然 DeFi 领域不断发展,新的参与者不断涌现并推出创新服务,但我们的重点依然是理解其基本的商业模型和机制。了解这些协议的本质使我们能够有效地追踪交易细节,并构建有用的指标以供进一步分析。
分析公司在简化这一领域中发挥着至关重要的作用。通过利用链上和链下数据,并与协议开发者合作,这些公司提供了宝贵的洞察力。通过从一些成熟的分析公司开始我们的分析,我们可以加速理解 DeFi 领域。然而,我们在本章获得的知识使我们能够建立自己的标准,深入研究代码和数学原理,并根据我们独特的需求定制指标。这种灵活性使我们能够深入了解 DeFi 领域,并根据特定需求做出明智决策。
在下一章中,我们将深入探讨数据准备的细节。
进一步阅读
为了补充本章,以下资源可能对您有所帮助:
-
Lau, D., Lau, D., Jin, T. S., Kho, K., Azmi, E., Fang, L., Hor, B., & Win, K. W. (2021). 如何进行 DeFi: 初学者指南。CoinGecko。
-
Fang, L., Hor, B., Azmi, E., Khor, W. W., & Gecko, C. (2021). 如何进行 DeFi: 进阶篇。CoinGecko。
-
深入探讨自动化市场制造商去中心化交易所(Uniswap v1)。(n.d.)。LearnWeb3:
learnWeb3.io/degrees/ethereum-developer-degree/sophomore/a-deep-dive-into-automated-market-maker-decentralized-exchanges-uniswap-v1/。 -
Maker 协议白皮书 | 2020 年 2 月。 (n.d.)。MakerDAO | 一个无偏的全球金融系统:
makerdao.com/en/whitepaper#abstract。 -
Fabian Vogelsteller fabian@ethereum.org, Vitalik Buterin vitalik.buterin@ethereum.org, ERC-20: 代币标准, 以太坊改进提案,第 20 号,2015 年 11 月。[在线系列]. 可在
eips.ethereum.org/EIPS/eip-20查看。 -
Ori Pomerantz. (n.d.). ERC-20 合约讲解. ethereum.org:
ethereum.org/developers/tutorials/erc20-annotated-code/#the-actual-contract. -
介绍 Permit2 和通用路由器. (2022 年 11 月 17 日). Uniswap 协议:
blog.uniswap.org/permit2-and-universal-router#universal-router-unified-token-and-nft-swaps. -
Finematics. (n.d.). 什么是 DeFi?去中心化金融解释(以太坊,MakerDAO,Compound,Uniswap,Kyber)[视频]. YouTube:
www.youtube.com/watch?v=k9HYC0EJU6E. -
助手函数. (n.d.). Compound III 文档:
docs.compound.finance/helper-functions/. -
Dune Analytics. (n.d.). 如何编写 SQL 获取 TVL 和多样化指标,如 HHI 和加权波动率 [第四部分] [视频]. YouTube:
www.youtube.com/watch?v=UiETadtYaLY. -
Jp12. (2022 年 6 月 17 日). Optimism 桥接比较. Medium:
jp12.medium.com/optimism-bridge-comparison-453fa1f476f6. -
Dogecoin. (n.d.). 每天只做好的事. Dogecoin – 一个开源的点对点数字货币:
dogecoin.com/#what-is-dogecoin. -
更多 Hop 统计数据:
-
Hop Bridge. (n.d.). Hop 转移示意图. GitHub:
github.com/hop-exchange/contracts/blob/master/assets/Hop_Transfer_Diagrams.jpg. -
以下是一些非常有价值的仪表盘和分析资源列表:
CoinStats coinstats.app/DeFillama DeFillama.com/Debank debank.com/DeFiPulse www.DeFipulse.com/LoanScan linen.app/interest-rates/Nansen www.nansen.ai/Token Terminal tokenterminal.com/terminal/markets/lendingZapper zapper.xyz/dashboardZerion zerion.io/DEXTools www.dextools.io/app/enGeckoTerminal www.geckoterminal.com/Into the Block www.intotheblock.com/Messari messari.io/稳定币仪表板 stablecoins.wtf/
表 5.3 – 有价值的仪表板列表
第二部分 Web3 机器学习案例
在本书的这一部分,我们将应用常见的人工智能任务于 Web3 相关数据。这一方法为我们提供了 Web3 领域常用工具的概述,并基于书中第一部分探索的数据和来源进行扩展。
本部分包括以下章节:
-
第六章, 数据准备与探索
-
第七章, 机器学习与深度学习概论
-
第八章, 情感分析——自然语言处理与加密新闻
-
第九章, NFT 的生成艺术
-
第十章, 安全性与欺诈检测概论
-
第十一章, 时间序列预测价格
-
第十二章, 利用图表进行市场营销发现
第六章:准备和探索我们的数据
数据准备是数据科学中的一个常见主题,超出了与机器学习流程的关联。它有各种不同的名称,如数据整理、数据清洗和特征工程的数据预处理。
在这里,我们强调将会投入大量时间进行数据清洗、特征工程和探索性分析,并且我们认识到强有力的预处理对结果的积极影响,无论是面向业务利益相关者的展示,还是与机器学习模型的整合。
数据清洗包括专注于识别和修正数据问题的任务,特别是错误和伪影。错误通常是由于在获取过程中数据丢失,而伪影则来源于生成数据的系统。清洗的工作涉及处理缺失数据、处理异常值、去除重复数据,以及为数据的可读性和转换执行必要的翻译。
数据准备涵盖了理解和转化接收到的数据,以使其与后续的流程步骤对接。这一章节深入探讨了在理解、预处理和从链上数据中提取信息时常见的情景。具体话题包括十进制处理、智能合约演变的方法和校验和验证。此外,本章还介绍了探索性数据分析(EDA)的概念,并利用汇总统计和异常值检测技术来展示其优势和见解。
本章探讨了准备链上数据的复杂性,并引入了 EDA 概念,促进了从分析到机器学习的过渡。由于这个数据科学领域的广泛性,本章并不旨在提供所有工具和方法的详尽概述。
总结来说,本章将涵盖以下主题:
-
链上数据准备
-
探索性数据分析介绍
技术要求
我们广泛使用 Pandas 库,它是一个流行且实用的 Python 库,用于处理 DataFrame 和系列。Pandas 提供了众多函数来分析、总结、探索、归一化和操作它们。系列是一个一维的类似数组的对象,而 DataFrame 是一个二维的表格结构,包含行和列。本书中的所有练习都将使用 Pandas 来执行上述活动。
如果你还没有安装 Pandas,可以通过以下代码片段来安装:
pip install pandas.
Pandas 的文档可以在 pandas.pydata.org/docs/ 查阅。
对于数据可视化,我们使用 Matplotlib 和 Seaborn 库。Matplotlib 提供了广泛的工具和对我们构建图像的控制,而 Seaborn 构建在 Matplotlib 之上,更加用户友好,但灵活性较差。
两个库的文档分别可以在seaborn.pydata.org/和matplotlib.org/找到。
你可以在本书的 GitHub 仓库中找到本章的所有数据和代码文件,网址为github.com/PacktPublishing/Data-Science-for-Web3/tree/main/Chapter06。我们建议你阅读Chapter06文件夹中的代码文件,以便跟随学习。
数据准备
在处理来自不同数据源的信息时,确保所有记录和字段的一致性和统一性非常关键,这样才能提取出有价值的见解或将数据输入到机器学习模型中。在这一部分,我们将探索与链上数据特别相关的各种数据准备任务。
十六进制值
十六进制表示法是一个基于 16 的系统,使用符号表示从 0 到 9 的数字值和从 A 到 F 的字母值。相比之下,我们日常使用的十进制表示法使用 10 个符号表示数字值(0-9)。十六进制表示法通过包括 A 到 F,将范围扩展到 10 到 15。这种表示法通常用于数据存储,因为它能够高效地表示二进制数字,每个十六进制数字表示 4 位二进制数。
在Chapter06/Preparation中的示例中,我们通过遵循developers.rsk.co/rsk/public-nodes/提供的文档,从 Rootstock 公共节点检索最新的区块编号。
结果值以十六进制数字的形式呈现,例如0x4e07d0:

图 6.1 – 十六进制区块编号
这个十六进制数字可以通过以下代码片段解码为十进制数字,基数为(16):

图 6.2 – 解码后的十六进制区块编号
按照这些步骤,我们能够将 RSK 节点返回的十六进制响应转换为我们的十进制系统。为了验证转换后的信息的准确性,我们可以将结果与链上浏览器中的数据进行对比,浏览器网址为explorer.rsk.co/blocks或rootstock.blockscout.com/。我们会看到该区块刚刚被添加到链上:

图 6.3 – 区块浏览器
某些 SQL 数据库引擎具备将十六进制值直接转换为人类可读格式的能力。例如,Covalent 使用的 ClickHouse 系统提供了unhex方法。你可以在clickhouse.com/docs/en/sql-reference/functions/encoding-functions#unhex的文档中找到更多详情。
校验和
校验和是一种哈希地址的算法,使得以太坊可以验证地址是否有效。在以太坊中,校验和地址包含了特定模式的大小写字母。
| 校验和地址 | 非校验和地址 |
|---|---|
0x95222290DD7278Aa3Ddd389Cc1E1d 165CC4BAfe5 |
0x95222290dd7278aa3ddd389cc1e1 d165cc4bafe5 |
表 6.1 – 地址之间的区别
以太坊将小写字母和校验和地址视为有效地址,发送到任一版本的资金将会被定向到同一接收者。然而,使用校验和地址能提供额外的安全层,防止意外地将资金发送到不存在的地址。
本节有两个重要的意义。首先,Python 和许多 SQL 引擎一样,区分大小写。因此,在比较或合并来自不同源的数据时,管理小写和校验和地址之间的差异变得至关重要。这可以保证数据分析的兼容性和精确性。第二个方面是区分有效和无效地址,这在保持数据完整性和加速查询方面非常关键。
在 Chapter06/Preparation 中,我们测试一个地址是否是有效的校验和以太坊地址。为此,我们利用 test() 函数将一个小写字母地址转换为其校验和版本。
另一个例子请参见Chapter10/EDA,在该章节中我们演示了如何在过滤器中应用校验和地址,以移除无效的以太坊地址。
小数处理
Solidity 是 EVM 区块链中最常用的智能合约编程语言,但它不支持浮动数值。为了在 Solidity 中表示小数,我们使用整数。在 Jupyter Notebook 中的 Chapter04/Art 部分,在 Chainlink 小节中,我们可以看到来自预言机的响应是以以下方式表示的:

图 6.4 – Chainlink 底价响应
这样大的数字在经济学背景下没有意义,无法直接包含在仪表盘或报告中。因此,有必要将其转换为我们的十进制系统,使其更具实用性。
智能合约通过特定的函数提供小数位数。在 Chainlink 的数据馈送智能合约中,decimals() 函数告知我们定点数,或者在实际应用中,告诉我们应该将小数点向左移动多少位才能将响应转换为我们的十进制系统。在第二章 探索状态数据 一节中解释了如何查询智能合约,正如 Jupyter Notebook 中所展示的,结果是 18:

图 6.5 – 数据馈送小数
以下图展示了我们可以在数据管道后续部分使用的转换后的数字:

图 6.6 – 结果
通过应用fromWei()函数,可以按照以下代码片段实现相同的结果:
Web3.fromWei(latestData), 'ether')
我们刚刚探讨的小数处理方法对于代币也同样适用。decimal(),它返回代币使用的小数位数,例如 8,这意味着将代币数量除以 100000000(10 的 8 次方)来获得其 用户表示。
更多标准内容已在第五章中进行了分析。
小数位说明
以太坊智能合约最常见的十进制基数是 18,而比特币使用 8,USDT 则使用 6 个小数位。
在本节中,我们了解到,消费链上数据通常需要进行大量转换。如果我们的数据集包含过于庞大的字符串且缺乏经济意义,我们可能需要查找智能合约的十进制值,以正确定位小数点位置。此外,如果我们的数据集包含十六进制值,我们需要将其解码为十进制系统。最后,我们还发现了如何将小写地址转换为校验和地址,以确保与区分大小写的编程语言兼容。
从 Unix 时间戳到日期时间格式
Unix 时间戳在数据分析中常被使用,但为了在仪表盘和报告中进行可视化,需要将其转换为人类可读的格式。Unix 时间表示自 1970 年 1 月 1 日以来已过去的秒数,提供了一种通过单一整数值来追踪时间的系统。
在大多数 SQL 引擎中,可以利用truncate函数从时间戳中提取相关的日期部分。
在 Python 中,我们可以使用datetime模块的fromtimestamp()函数,将 Unix 时间戳转换为本地日期时间,使用utcfromtimestamp()函数,将其转换为 UTC 日期时间。
在 Jupyter Notebook 的Chapter06/Preparation部分,我们使用以下代码将 Unix 时间戳转换为日期时间:

图 6.7 – 日期时间转换
为了验证我们的结果,我们可以将其与www.unixtimestamp.com/网站上的数据进行对比,该工具展示了相同的信息:

图 6.8 – Unix 时间戳转换器
智能合约的演变
智能合约和任何软件产品一样,可能会因为业务需求、安全事件或减少燃气费用等多种原因而发生变化和需要升级。然而,根据设计,区块链上部署的一切都是不可变的。以下信息来自Ethereum.org,概述了多种实现升级的方法。内容引用自创意共享署名 4.0 国际(CC BY 4.0)许可协议,符合使用条款。原文可以在本章的进一步阅读部分找到。
智能合约的升级可以通过以下方式实现:
-
创建多个版本的智能合约,并将状态(即数据)从旧合约迁移到新合约实例
-
创建独立的合约来存储业务逻辑和状态
-
使用代理模式将函数调用从不可变的代理合约委托给可修改的逻辑合约
-
创建一个不可变的主合约,该合约通过灵活的卫星合约执行特定功能
-
使用钻石模式将代理合约的函数调用委托给逻辑合约
总之,升级智能合约的方法并不涉及修改已部署的代码,而是用一个合约替代另一个。目前,升级智能合约最流行的方法是代理模式。这种模式将代理合约和包含逻辑的执行合约分离。代理合约代表逻辑智能合约,将前端的交易重定向到后端正确的智能合约。可以在后端交换逻辑智能合约,并更新代理合约,使其开始将交易重定向到新部署的智能合约,该合约包含最新的逻辑。
合约可能发生变化,这意味着我们的查询需要适应这些变化。例如,如果一个智能合约在某个区块开始触发事件,我们需要意识到这一点,以便捕捉新的信息。正如我们在第二章中看到的,我们需要应用程序二进制接口(ABI)来解码智能合约,这些合约需要在升级后适当地更新以解码交易。如果我们没有意识到正在解析的合约已经发生了变化,可能会错过某些事件,并且可能对我们的分析产生负面影响。
在分析具体项目时,重要的是要关注新闻发布、项目代表和官方信息渠道,了解是否有任何新开发,这样我们可以将查询指向更不容易变动的智能合约。
总之,尽管智能合约设计为不可更改,但在某些情况下,升级和更改变得必要,我们需要做好准备,调整我们的查询或代码以适应这些变化。例如,如果我们正在分析以太坊,我们需要意识到整个区块链在 2022 年 9 月的合并(Merge)后发生了变化,并且这种变化会在数据层面产生影响。
探索性数据分析
在数据清洗阶段和建模或正式统计分析之间,存在一个中间步骤,称为 EDA,这是数据科学的一个基本方面。EDA 作为理解和解释数据集的主要方法,提供了关于“样本之外的总体”的洞察,并将原始数据转化为可供企业使用的可操作信息。EDA 可以包括多种技术和方法:
-
数据摘要或描述性统计:用于总结数据集中的中心趋势。
-
数据可视化:采用直方图、箱形图、散点图和折线图等图形技术来可视化数据,帮助识别模式、检测异常值,并理解变量之间的关系。此外,数据可视化在向非技术性观众展示结论时特别有效。
-
数据探索:帮助我们理解变量的分布,评估其形态和偏斜度,识别异常的存在。
-
处理缺失数据:这使我们能够识别缺失的行并评估它们对结果的影响。它有助于确定缺失值的模式,并制定有效处理它们的策略。
-
异常值检测:识别与数据集其他部分显著偏离的值,并评估其对分析的影响。这些异常值可能来自多种原因,我们将在后续部分讨论这些原因。
-
相关性和模式:通过相关分析和散点图等技术,探索变量之间的关系。此外,它们有助于识别数据随时间变化的趋势或季节性。
有关 EDA 的简要描述可以在towardsdatascience.com/exploratory-data-analysis-8fc1cb20fd15找到:“探索性数据分析是指对数据进行初步调查,以发现模式、识别异常、测试假设和检查假设,借助于汇总统计和 图形表示法。"
在本章中,我们将简要介绍汇总统计和利用图形表示法进行异常值检测。我们选择这两个主题,因为它们可能适用于我们在旅程中遇到的所有数据集。有关 EDA 主题的进一步探索,欢迎参考进一步阅读部分中的书籍,它们非常有用。
为了举例说明本节中学到的概念,我们将使用 Kaggle 上提供的Witches数据集(www.kaggle.com/datasets/harrywang/crypto-coven?select=witches.csv)。该数据集包含关于 Crypto Coven NFT 项目的信息,每一行代表一个女巫 NFT。Witches 项目的主页可以在www.cryptocoven.xyz/找到。
数据汇总
我们的数据集将包含分类变量或定量变量。分类变量是指可以分为组的变量,例如颜色或品牌。另一方面,定量变量代表数值量,例如价格或销售数量。df.describe()代码片段返回定量变量及其分布情况。
计算分类数据的分布涉及确定每个类别的频率。这种分析可以提供有意义的见解。例如,在市场营销中,理解年龄组、收入水平或消费者偏好等分类变量的分布可以帮助企业有效地细分目标受众,并制定更具针对性和成功的营销活动。另一个例子是在欺诈检测中,分类变量如交易类型或用户行为模式在识别欺诈活动中至关重要。通过研究这些变量的分布,可以识别出异常或不寻常的模式,从而使组织能够开发出有效的欺诈检测模型和策略。
在 NFT 领域中的一个应用是帮助确定一个系列是由零售公众拥有,还是由少数收藏者(集中化)持有。关于艺术品收藏的所有权特征的了解,可以帮助投资者评估项目价格是否与市场价值一致,或者是否容易受到操控。更加去中心化的所有权结构意味着价格更接近市场价值。
在Chapter06/EDA.ipynb中,我们通过创建两类持有者来研究 NFT 的分布:那些拥有超过三个同系列 NFT 的地址,我们称之为收藏者,以及那些持有少于三个 NFT 的地址,也就是普通公众。我们遵循三个步骤:
-
我们统计每个地址持有的 NFT 数量,相当于 SQL 查询中的
GROUP BY操作。这使我们能够了解每个地址的持有情况。 -
我们创建了一个地址列表,这些地址持有来自同一系列的超过三个 NFT。每个地址持有的 NFT 数量是我们分析的一部分,也是我们在 EDA 过程中做出的决策。这些微小的决策会影响最终结果,文档化它们是一个良好的实践。
-
我们根据地址是否在步骤 2 的列表中,分别构建
collectors_df和distributed_df数据集。
通过这些简单的步骤,我们可以计算项目中收藏者和分布所有者的百分比。图 6.9 显示,收藏者的百分比只有 32%,而其余的 68% 是由公众持有的。

图 6.9 – 收藏者和分布百分比
为了总结定量变量,我们引入了均值、平均值、偏差、异常值等概念。我们从集中趋势或总结性统计量开始,它们用于用单一的数值来描述一组值。这些统计量包括均值、中位数和众数。
平均数,即算术平均数,是最常用的度量方式。它是通过将数据集中所有值相加,并除以值的个数来计算的:
Formula: Mean = (Sum of all values) / (Total number of values)
例如:如果我们的值是 5、7、2、10 和 6,则平均数为 (5 + 7 + 2 + 10 + 6) / 5 = 6。
Pandas 提供了 mean() 函数,它返回传递给列的均值。如果我们计算 Witch 数据集中的价格均值,我们将所有价格相加,然后将结果除以行数。请参见 Chapter06/EDA.ipynb 中的以下代码片段,我们在其中计算了 price 列的均值:
df['price'].mean()
计算均值时,所有值都会被考虑在内,但计算出的数值可能不在分析的样本中。另一个重要的方面是,均值受到异常值的强烈影响。因此,在计算均值之前,需要清理数据集并删除异常值。
当数据存在偏斜时,均值并不是集中趋势的完美度量。一个更好的替代方案是中位数。
中位数被定义为按大小顺序排列后的列的中间值,从最小到最大。要手动计算中位数,我们可以按照以下步骤进行:
-
将
price列中的所有值从小到大排序。 -
找到位于数据集中心的数值,将数据集分成两部分:
公式(奇数个值):中位数 =中间值公式(偶数个值):中位数 = (两个中间值的总和)/ 2例如:对于数据集
5、7、2、10和6,当按升序排列时,中位数将是 6。
Pandas 提供了 median() 函数来执行这个计算。例如,要计算 price 列的中位数,我们可以使用以下代码片段,这也显示在 Chapter06/EDA.ipynb 中:
df['price'].median()
在处理偏斜数据或存在异常值的数据时,中位数通常优于均值。
在 Chapter04/Art.ipynb 中,当总结数据以寻找多个市场在一段时间内的最低价格时,我们选择显示中位数而不是平均值,结果如下:

图 6.10 – 按市场划分的中位数最低价格
如果我们使用平均值,图形将显示市场之间的显著差异,如图 6.11 所示。基于平均值分析地板价格并不准确,特别是当我们提到 OpenSea 报价时。

图 6.11 – 各市场的平均地板价格
众数是另一种集中趋势的度量,表示数据集中最频繁出现的值。从图形上讲,它由直方图中最高的柱形表示。它也可以与分类变量一起使用。要手动计算众数,我们需要识别数据集中最常出现的价格:
Formula: No specific formula
例如,在 15、20、18、22、15、20、18、20、22 和 25 的数据集中,出现频率最高的值是 20\。它出现了三次。
Pandas 提供了 mode() 函数来计算某列的众数,如 Chapter06/EDA.ipynb 中的以下代码片段所示:
df['price'].mode()[0]
缺失价格的说明
集中趋势的度量不仅有助于总结我们的数据集,还能帮助解决数据集中的缺失值问题。
例如,在极端波动期间,某些交易所可能会暂停商业化。这适用于传统市场和集中化的加密货币交易所。如果我们的数据库恰好从这种交易所获取价格数据,可能会出现缺失的数据行。在这种情况下,可以使用 pandas 函数,如 fillna() 或 interpolate(),来填充缺失值。使用 fillna() 函数,我们可以指定是否用均值或中位数来填充 NaN 值。
总之,在我们的 EDA 中,我们探讨了集中趋势的度量方法,如均值、中位数和众数,这些方法提供了关于我们数据分布和特征的洞察。
在我们探讨集中趋势的基础上,现在我们将注意力转向异常值检测。异常值是偏离数据集整体模式的数据点,它们可能对我们的分析和解释产生重大影响。在接下来的部分中,我们将深入研究识别异常值的各种技术和方法。
异常值检测
根据 Rafael A. Irizarry 的《数据科学导论》一书,异常值被定义为 “与集中趋势相差较远的数据样本”。虽然异常值本身既不一定是好也不一定是坏的,但它们可以显著影响我们的分析,并导致不正确的结论。特别是在处理价格时,市场波动性可能会扭曲交易资产的真实价值。价格作为价值的代理,但重要的是要认识到,有些价格显著偏离实际价值,成为异常值。
在某些情况下,主要目标是识别和分析异常值,这通常是异常检测技术的重点,例如在第四章中讨论的技术,特别是用于揭露欺诈或洗钱。
异常值出现的原因有多种:
-
仪器测量误差,如 API 断开或不平衡的秤
-
数据录入错误
-
处理的样本或群体比最初假设的要不均匀
让我们探索一些识别数据集异常值的技巧:
- 箱线图(胡须图):这种图形表示法通过五个重要数字总结数据:最小值、第一个四分位数、中位数、第三个四分位数和最大值。我们可以将远离箱体的数据点识别为异常值:

图 6.12 – 箱线图的部分
这张图像可以通过以下代码片段由 Pandas 自动生成:
Chapter06/Outliers).
* `df.quantile()` function. Once we have them, we can calculate other parts of this formula.
In `Chapter05/Outliers`, we calculate the IQR, bottom, and upper limits in this part of the code:

Figure 6.13 – Calculation of IQR and limits
The 1.5 multiplier is common practice but can be adjusted to adapt to our case.
* **Three-sigma rule** (**Z-score**): The three-sigma rule states that 99.7% of data falls within three standard deviations (three-sigma) of the mean in a normal distribution. This rule is used for outlier detection because data points outside the three sigmas can be considered outliers.
This method uses the mean as a starting point, which can be influenced by outliers. A more robust modified Z-score method can be employed, which incorporates the median and median absolute deviation in its formula. The metric is a statistical measure that helps identify outliers in a dataset by comparing each data point to the median and median absolute deviation. It provides a robust way to detect extreme values, especially in datasets with skewed distributions.
Summary
This chapter has addressed various preparation methods applicable to on-chain data scenarios. We explored techniques such as unhexing data, decimal treatment, handling checksum addresses, and converting Unix timestamps to datetime formats. These methods have proven foundational in preparing the on-chain data for subsequent analysis.
Moreover, we introduced the concept of EDA as a crucial step in understanding and summarizing datasets, with a specific focus on central tendency metrics. Additionally, we delved into outlier detection techniques, such as box plots and the IQR method, aiding in the identification of extreme observations deviating significantly from the majority of the data.
By applying these cleaning and EDA techniques, we have equipped ourselves with essential tools for the effective analysis and interpretation of on-chain data. These foundational concepts serve as building blocks for more advanced techniques and methodologies as we continue this journey. For more insights into these methodologies, please refer to the *Further* *reading* section.
Further reading
The following links may help to complement this chapter:
* Technical requirements:
* *10 minutes to pandas, pandas 1.5.3 documentation, pandas - Python Data Analysis* *Library:* https://pandas.pydata.org/docs/user_guide/10min.xhtml#min
* Evolution of smart contracts:
* *Upgrading Smart Contracts,* *ethereum.org:* [`ethereum.org/en/developers/docs/smart-contracts/upgrading/`](https://ethereum.org/en/developers/docs/smart-contracts/upgrading/)
* Exploratory Data Analysis:
* *Introduction to Data Science: A Python Approach to Concepts, Techniques and Applications,* Laura Igual, Santi Seguí, Springer
* *Three Ways to Detect Outliers, Colin Gorrie, Colin Gorrie’s Data* *Story:* [`colingorrie.github.io/outlier-detection.xhtml#modified-z-score-method`](https://colingorrie.github.io/outlier-detection.xhtml#modified-z-score-method)
* *Python for Data Analysis: Data Wrangling With Pandas, NumPy, and Jupyter,* Wes McKinney, O’Reilly Media
* *Box Plot Review, Khan* *Academy:* [`www.khanacademy.org/math/statistics-probability/summarizing-quantitative-data/box-whisker-plots/a/box-plot-review`](https://www.khanacademy.org/math/statistics-probability/summarizing-quantitative-data/box-whisker-plots/a/box-plot-review)
* *Hands-On Exploratory Data Analysis With Python: Perform EDA Techniques to Understand, Summarize, and Investigate Your Data,* Usman Ahmed, Suresh Kumar Mukhiya, O’Reilly Media*:* [`www.packtpub.com/product/hands-on-exploratory-data-analysis-with-python/9781789537253`](https://www.packtpub.com/product/hands-on-exploratory-data-analysis-with-python/9781789537253)
* *The Data Science Design Manual,* Steven Skiena, Springer
* Cleaning:
* *RSK* *Explorer*: [`explorer.rsk.co/blocks`](https://explorer.rsk.co/blocks)
* *More on Time on the Blockchain, Nick Furneaux, Wiley*, *Chapter 9*, Investigating Cryptocurrencies, Understanding, Extracting, and Analyzing Blockchain Evidence, Page 156 to Page 161
第七章:机器学习与深度学习入门
在应用任何机器学习算法之前,全面理解数据集及其关键特征至关重要。这种理解通常通过探索性数据分析(EDA)得出。一旦熟悉了数据,我们必须投入时间进行特征工程,这包括选择、转换和创建新的特征(如果需要),以使所选模型能够使用或提升其性能。特征工程可能包括将类别转换为数值、对特征进行缩放或标准化、从现有特征中创建新特征等任务。这个过程针对每个特定的模型和数据集进行定制。一旦这个过程完成,我们就可以开始建模。
本章的目标是回顾机器学习和深度学习的基础概念,为本书的第二部分奠定基础。在第二部分中,我们将深入探讨人工智能在 Web3 数据中的各种应用案例。尽管不会详细介绍每一种可能的模型,但我们将简要描述项目的动机、模型本身以及使用的工具,并提供有价值的参考资料以供进一步阅读。
我们将探讨机器学习和深度学习的主要概念,讨论两个典型的机器学习管道——一个使用 scikit-learn,另一个使用 Keras。此外,我们为本章涵盖的每个主题编写了广泛的进一步阅读部分,以鼓励持续学习。
具体来说,以下主题将被讨论:
-
机器学习和深度学习的基本概念
-
使用 scikit-learn 和 Keras 的机器学习管道
技术要求
我们将使用scikit-learn,这是一个专为机器学习任务设计的流行 Python 库。它提供了数据预处理、特征选择、模型选择和模型评估的算法和工具。
如果你之前没有使用过 scikit-learn,可以通过以下代码片段进行安装:
pip install scikit-learn
scikit-learn 的文档可以在 https://scikit-learn.org/stable/找到。
对于深度学习,我们可以选择使用TensorFlow或Keras。TensorFlow 是一个强大的开源数值计算库,提供训练、测试和部署各种深度学习神经网络的解决方案。它作为基础设施层,使得在 CPU、TPU 和 GPU 上进行低级张量操作成为可能。另一方面,Keras 是一个建立在 TensorFlow 之上的高级 Python API。它专为快速实验而设计,并在发现错误时提供有用的反馈。根据 Kaggle 的 2022 年数据科学与机器学习现状调查,Keras 在机器学习开发者和数据科学家中达到了 61%的采用率。
如果你之前没有使用过 TensorFlow 或 Keras,可以使用以下代码片段进行安装:
pip install tensorflow
pip install keras
对于深度学习来说,需要大量的计算能力;我们的普通 CPU 可能无法完全胜任任务,导致训练和推理速度较慢。另一种选择是本地或云端运行 GPU——可以通过 Kaggle Kernel 或 Google Colab 进行托管。它们有类似的用户界面,结构上类似于 Jupyter notebook,使得在这些平台上运行仓库中的代码变得更加容易。
你可以在本书的 GitHub 仓库中找到本章的所有数据和代码文件,地址为github.com/PacktPublishing/Data-Science-for-Web3/tree/main/Chapter07。我们建议你阅读Chapter07文件夹中的代码文件,跟随学习。
引入机器学习
计算机科学维基提供的机器学习定义是“一个致力于理解和构建能够‘学习’的方法的研究领域——也就是利用数据来提高某些任务表现的方法。它被视为人工智能的一部分。机器学习算法基于样本数据(称为训练数据)构建模型,从而在没有明确编程指令的情况下进行预测或决策。”
(来源:computersciencewiki.org/index.php/Machine_learning)
杰森·布朗利教授将深度学习定义为“一种受大脑结构和功能启发的机器学习子领域,称为人工神经网络。”深度学习与其他机器学习方法的区别在于,它以人工神经网络为基础进行方法设计。
这两个领域之间的关系通常表示如下:

图 7.1 – 人工智能的维恩图
让我们进一步分析机器学习的定义:
-
机器学习模型根据我们提供的数据创建自己的规则,正如“理解并构建能够学习的方法”以及“在没有明确编程指令的情况下进行预测或决策”这两句话所述。之前,我们在查询中使用了过滤器,或在程序中使用了if 语句。使用机器学习,特别是监督学习时,我们输入数据,让模型推断出规则。在《Python 数据科学手册》中,作者挑战了模型自动学习的观点,而是建议模型通过适应观察到的数据来调节我们提供的参数。一旦它将这些参数与已知数据进行拟合,就能根据未见过的数据推断出结果。
-
“机器学习算法基于样本数据构建模型,这些数据称为训练数据。” 传递给机器学习算法的数据需要至少分为两部分:训练数据和测试数据。训练数据集用于构建模型,测试数据集用于评估模型在未见过的数据上进行预测的能力。然后将模型的预测与真实数据进行比较,并计算评估指标。
机器学习技术可以分为监督学习、无监督学习和强化学习。通过机器学习技术解决的常见任务如图 7.2所示:

图 7.2 – 机器学习应用
监督学习的目标是创建一个可以将输入映射到输出的函数,从而使模型能够根据未见过或相似的输入推断输出。在这个过程中,我们使用特征来描述变量的特性,标签或标记来识别预测的变量。通过这一过程,我们的模型能够学习特征与标签或标记之间的关系。
在 Web3 分析中,标签起着至关重要的作用,因为它使我们能够为那些由数字和字母组成、与外部世界没有直接联系的地址赋予身份。然而,创建一个标记地址库可能是一个挑战,最近,这已经成为一家名为 Arkham 的公司的业务,该公司通过公开数据激励“去匿名化区块链”。标记地址是像 Nansen 这样的公司主要的杠杆之一,它们在以太坊及其他链上标记了数百个地址,推动了机器学习技术和数据分析报告的进展。
标签也可以在 Etherscan 中找到,重要的项目会标记其地址以便进行公开审计。此外,Dune 和 Flipside 也有带标签的表格,研究团队在其中添加了相关信息,以帮助查询。如果你想了解更多关于身份归属的知识,可以参考 Nick Fourneaux 在《调查加密货币》一书中的方法,教你如何从论坛或软件下载网站提取地址,下载 HTML 原始文本,并执行正则表达式分析。
监督学习可以进一步分为回归和分类技术。在分类技术中,我们有一组离散的类别作为标签(例如欺诈交易或非欺诈交易)。在回归中,我们有定量标签,例如 NFT 艺术品或代币的价格。
无监督学习的目标是尝试识别数据集中可能不显式的结构或模式。无监督学习下的任务通常包括以下几种:
-
聚类 – 即在给定的数据集中识别出不同的群体
-
降维 —— 即,尝试用更少的特征表示数据集
-
新颖性检测 —— 即,尝试识别数据中何时发生变化
强化学习通过利用模型已知的信息以及通过与环境互动后获得的累计奖励来教导模型寻找问题的最佳解决方案。模型通过环境反馈(奖励或惩罚)来进行调整,目标是最大化总奖励。强化学习的核心思想是模仿人类通过试错学习的方式:

图 7.3 – 智能体-环境循环(改编自 gymnasium.farama.org/content/basic_usage/)
为了使一个项目变得生动起来,必须执行一些初步的业务/数据步骤:
-
定义一个 Web3 数据科学问题意味着精确地阐明我们希望用现有数据解决的问题。在这样的定义中,我们必须能够描述我们要解决的问题,为什么要解决它,以及我们所考虑的假设。
-
获取数据意味着获取我们将要处理的数据集。数据集可能已经包含了所有相关的行和列,或者我们需要通过结合多个数据源来构建它。初步的数据源列表列在第二章和第三章中。根据我们要解决的问题,可能需要更多的数据源。
-
EDA 用于通过总结统计和数据可视化技术来理解数据集。数据准备是一个预处理步骤,在这个步骤中,我们转换数据集以提高其质量或使其更容易为模型消化。链上数据可能需要大量的转换。我们在第六章中分析了一些这些方法。
现在,让我们分析选择、训练和评估模型的步骤。
构建机器学习流程
在清理数据并选择最重要的特征后,机器学习流程可以概括为以下几个步骤,如图 7.4所示:

图 7.4 – 机器学习流程
要执行这个过程,我们必须进行以下操作:
-
根据问题和可用数据选择一个模型及其初始参数。
-
训练:首先,我们必须将数据分割成训练集和测试集。训练过程包括让模型从数据中学习。每个模型的训练过程在时间和计算消耗上可能有所不同。为了提高模型的性能,我们必须通过超参数调整技术(如网格搜索或随机网格搜索)来优化模型。
-
预测和评估:然后,使用训练好的模型对测试集进行预测,测试集包含算法未曾见过的数据行。如果我们使用训练数据评估模型,模型总是能够预测得很好,那么我们就无法进一步改进它。模型的表现通过特定任务的评估指标来评估。
当我们得到一个良好的模型时,必须保存它,以便在接收到未见数据时使用它。我们可以使用Pickle和Keras Tokenizer等工具来实现这一点。Pickle 将训练好的模型序列化并转换为文件,使其能够在另一个环境中使用。为了产生结果,我们必须传递结构相同的数据,使模型能够进行预测。
让我们通过一个实际示例来应用这个流程。在Chapter07/ML_warmup中,我们的目标是使用一个名为以太坊欺诈检测数据集的 Kaggle 数据集,识别以太坊网络上的欺诈交易,其中只有 17%的行是欺诈的。这是一个典型的监督分类任务。
模型
根据手头的问题,我们必须选择一个或多个模型进行测试,以判断哪个模型在我们的数据上表现更好。如果我们不确定该选择哪个模型,可以查看 Kaggle 上已解决的相似结构问题。在 Jupyter notebook 中,我们选择了一个随机森林分类器,代码片段如下:
random_forest = RandomForestClassifier(random_state=42)
有许多算法可以用于训练,选择可能会很困难。选择多种模型的一种方法是减少可减少的误差。文献通常将这个问题称为偏差-方差权衡。在解决这个权衡之前,我们需要理解存在的不同类型的误差。任何机器学习算法的预测误差可以分为以下几类:
-
噪声或不可减少的误差:这种类型的误差无论我们如何实现模型,都无法消除。
-
偏差误差:这是可以减少的。维基百科将其定义为“由于学习算法中的错误假设而产生的误差”。高偏差的模型过于简化现实,导致预测值和真实值之间存在较大的误差。高偏差模型过度简化,意味着它们没有足够的参数来捕捉它们学习数据的复杂性,导致欠拟合。下一节将详细讨论这一概念。
-
方差误差:这也是可以减少的。维基百科将其定义为“对训练集中的微小波动的敏感性导致的误差”。这意味着模型过于深入地学习了训练数据集的特殊性,以至于无法对未见数据进行有效的泛化。这些模型高度依赖于精确的训练数据,无法做到泛化。当模型在训练数据上表现良好,但在测试/验证数据上表现不佳时,我们就会遇到这个误差,表明存在过拟合问题。
低方差高偏差的算法训练复杂度较低的模型,具有简单或刚性的基础结构 – 例如线性回归。另一方面,高方差低偏差的算法训练复杂、灵活的模型,可以在训练数据上准确,但在预测中不一致 – 例如 KNN。
如果我们理解了偏差和方差,并认识到两者都源于我们所做的模型选择,为了做出最优决策,我们将选择在两者之间进行总误差的权衡的模型:

图 7.5 – 偏差-方差权衡
选择模型的另一个标准是其性能,这由所选的评估指标来衡量。我们可以运行多个模型,并使用相同的指标评估它们,性能更好的模型将被继续调优。我们将在后续章节讨论评估指标。
在Chapter07/ML_warmup中,我们选择了随机森林分类器。这种算法旨在减少模型的方差而不损害偏差,并在被称为召回率的评估指标上表现良好。有关随机森林算法的更多信息,请参阅进一步阅读部分。
训练
开始训练过程时,我们将数据分为训练数据集和测试数据集。这样做可以使模型在训练过程中看不到部分数据,并且我们可以在训练后评估其性能:
X_train, X_test, y_train, y_test = train_test_split(X, y,\
test_size=0.33, random_state=42)
训练过程包括将特征和标签传递给算法,使其从中学习。学习算法将尝试在训练数据中找到模式,将输入数据的属性映射到目标上。训练后的模型捕获这些模式。
在Chapter07/ML_warmup中,我们使用以下代码片段指导模型学习:
random_forest.fit(X_train, y_train)
欠拟合和过拟合
考虑三种情景,模型由一条黑线表示。哪种情景能更好地进行分类?

图 7.6 – 三种分类情景
让我们理解这些情景:
-
情景 A:模型非常简单,无法捕捉两个类别之间的边界。这被称为欠拟合。
-
情景 B:模型能够找到两类之间可接受的边界,尽管可能会误分类一些边界样本。总体上,它捕捉了数据集的复杂性。
-
情景 C:模型过度适应了训练数据集,并学到了所有细节,而不仅仅是区分一个类别与另一个类别的相关特征。它无法泛化。这被称为过拟合。

图 7.7 – 模型过拟合时的表现(来源:https://twitter.com/MaartenvSmeden/status/1522230905468862464)
我们的目标是场景 B,在这个场景中,模型足够复杂,能够捕捉重要特征,但不会过度适应训练数据,因此在未见过的样本上表现良好。
预测与评估
在这里,我们将未见过的数据传入训练好的模型,并评估它的预测与实际情况的准确性。如果结果可接受,我们会保留模型;否则,我们将调整超参数并重新训练。超参数是在训练过程前设置的变量,在学习过程中不能更改。参数是那些在训练过程中调整的值。
在 Jupyter notebook 中,我们使用以下代码片段进行预测和评估:
y_test_pred = random_forest.predict(X_test)
print(classification_report(y_test_pred,y_test))
conf_mat=confusion_matrix(y_test_pred,y_test)
为了评估结果是否可接受并决定是否保留模型,我们可以使用二分类任务的混淆矩阵。在 Jupyter notebook 中,我们分析的数据集的混淆矩阵如图 7.8所示:

图 7.8 – 混淆矩阵
让我们来理解混淆矩阵的组成部分:
-
真反例(TN):模型预测为负,并且预测正确。这些交易不是欺诈性的。
-
真正例(TP):模型预测为正,并且预测正确。这些交易是欺诈性的。
-
假反例(FN):模型未能预测,并且它们是欺诈性的。
-
假正例(FP):模型将这些交易标记为欺诈性交易,但它们并非如此。
基于这些数据,我们可以计算精确度和召回率。精确度回答的问题是:我们预测为正的所有类别中,实际为正的有多少?
TP _ TP + FP
我们的精确度是0.91。
召回率回答的问题是:所有欺诈性类别中,我们的模型正确预测了多少?其公式如下:
TP _ TP + FN
我们的召回率是0.98。
结果的评估取决于具体问题。正确选择评估指标非常重要,因为它将影响我们后续的决策。在Chapter07/ML_warmup中,我们的目标是发现欺诈交易,因此我们更看重召回率高于精确度。我们更偏向召回率,因为漏掉一个欺诈交易的成本远高于错误标记一个可能无害的交易。然而,假正例(FP)的数量不能过大,因为这会带来交易成本并影响客户。
现实世界的数据集大多数是不平衡的,这意味着不同类别的样本数量不均衡。我们的任务是应用技术,让模型学习两种类别的存在和特征,特别是当我们试图检测的类别是较少出现的类别时。
关于平衡和不平衡数据集的说明
准确度,即正确预测的百分比,是另一个常用的评估指标。然而,如果数据集不平衡,准确度将无法得出好的结果。如果在不平衡数据集中将准确度作为评估指标,模型只需要识别出多数类,就能返回一个好的结果,这并不能保证这是一个好的模型。
在我们的 EDA(探索性数据分析)中,我们将检查每个类别的比例,并确定我们处理的是平衡数据集还是不平衡数据集。例如,在Chapter07/ML_warmup中,我们知道欺诈性样本的比例是 17%。
我们可以通过在特征工程预处理步骤中使用过采样或欠采样技术来解决这个问题。必须谨慎进行,因为这可能会改变数据中的潜在关系,或者删除一些关键信息。
我们还可以使用已经为不平衡数据集优化的算法,并允许用户在训练过程中添加这些信息——例如,使用随机森林算法中的class_weight参数。
此外,我们还可以通过在train_test_split中使用stratify来考虑类别的不平衡表示,从而优化拆分过程。
引入深度学习
在本书的第二部分中,我们在解决用例时也将使用深度学习方法。深度学习模型采用多个互联的节点(称为神经元),这些神经元处理输入数据,并基于学习到的权重和激活函数产生输出。神经元之间的连接促进了信息流动,网络的架构决定了信息如何被处理和转化。
我们将在各自的章节中详细研究三种神经网络架构。现在,让我们先介绍一下我们将在这些章节中使用的框架和术语。
神经元作为系统的基本构建单元,可以定义为一个节点,具有一个或多个输入值、权重和输出值:

图 7.9 – 神经元的结构
当我们将多个具有这种结构的层叠加在一起时,它就形成了一个神经网络。这种架构通常由输入层、隐藏层和输出层组成:

图 7.10 – 神经网络结构
输入层启动网络并将数据传递给隐藏层,隐藏层对特征和模式进行计算。隐藏层越多,执行的计算就越复杂。
输出层接收来自隐藏层的处理信息,并提供一个总结网络内已处理信息的结果或输出。
节点之间的连接包含权重,这些权重携带有关如何解决特定问题的信息。在模型训练过程中,我们调整这些权重以使模型适应我们的数据集。这些权重代表了模型的可学习参数。
这个灵活的结构允许用户调节多个超参数,以增强模型的表现。基本原理如下:
-
学习率:这个超参数控制模型在响应权重更新时的变化程度。找到正确的学习率非常重要,因为过小的学习率可能会导致训练过程过长,而较高的学习率可能会导致次优的权重集合和结果变化。学习率与优化器密切相关。
-
激活函数:这些函数决定神经元是否应该被激活,即它们决定神经元对网络的输入是否对预测过程重要,通常通过简单的数学运算来实现。激活函数从每层输入的值中得出输出。Keras 中的激活函数列表可以在
keras.io/api/layers/activations/找到。 -
损失函数:这些函数量化了预测值与期望值之间的误差,将模型的表现总结为一个需要在训练过程中最小化的单一值。损失函数的选择取决于所解决的问题,常见的例子包括回归任务中的均方误差和分类任务中的交叉熵。Keras 列出了各种损失函数,详情请见
keras.io/api/losses/。 -
优化器:这些算法通过调整神经网络的属性来帮助改善模型的表现。它在架构中的职责是调整学习率和神经元的权重,以达到损失函数的最小值。Keras 支持的优化器列在此:
keras.io/api/optimizers/。 -
训练轮数:这表示算法遍历整个数据集的次数。
-
批量大小:指的是用于更新模型参数的样本数量。批量大小为N意味着将使用训练数据集中的N个样本来更新模型参数。请记住,这些样本会保存在内存中,因此更高的批量大小需要更多的内存。
我们使用的所有模型都将在 Keras 框架下进行分析,Keras 具有出色的文档。
模型准备
在Chapter07/DL_warmup中,我们将使用与上一节相同的数据集——以太坊欺诈检测数据集。这一次,我们将选择更少的列,并使用RobustScaler()来自 sklearn 对数字进行标准化。
与所有预测问题一样,我们希望通过train test split ()将测试集和训练集分开。
模型构建
我们将使用 Keras 创建一个顺序模型。顺序模型的结构由相同或不同的层堆叠而成,其中一层的输出进入另一层。
以下代码片段设置输入层,期望输入具有与数据集列数相同的行数据。在这种情况下,我们只处理 11 列数据:
model.add(Input(shape=(X_train.shape[1],)))
我们添加了三层隐藏层,每一层的节点数逐渐减少。所有这些层都使用relu作为激活函数。Dense层是一个全连接层,是多种类型层之一,例如卷积层或LSTM层:
model.add(Dense(30, activation='relu'))
model.add(Dense(10, activation='relu'))
model.add(Dense(5, activation='relu'))
model.add(Dense(1, activation='sigmoid'))
由于这是一个二分类任务,在最后一层,我们将使用sigmoid激活函数和输出层中的1:
model.add(Dense(1, activation='sigmoid'))
在训练模型之前,需要通过优化器、损失函数和评估指标来编译模型。编译器配置学习过程。值得一提的是,由于这是一个不平衡的数据集,我们关心的是精确度和召回率,因此我们必须利用keras库来构建评估指标,具体如下:
metrics = [
keras.metrics.Precision(name="precision"),\
keras.metrics.Recall(name="recall"),
]
现在,我们必须将其添加到编译器中:
model.compile(optimizer=keras.optimizers.Adam(1e-2), \
loss=loss_function, metrics=metrics)
训练和评估模型
一旦模型构建完成,我们需要将数据集输入模型进行训练。这是通过fit()来完成的,在本例中,我们决定训练 90 个 epoch。
一旦完成训练,就需要通过预测未参与训练的数据来评估模型。我们可以使用X_test和y_test来实现这一点。
分类报告显示,少数类的召回率为 95%,这一结果非常好。通过更多的数据预处理,应用针对不平衡数据集的技术以及超参数调优,我们可以进一步提高结果。
在这个特定的练习中,Python Zen的原则之一得到了完美应用。简单优于复杂 —— 一个更简单的机器学习模型表现优于复杂的神经网络。
现在我们已经探讨了这两种方法,我们将重点介绍每个领域的附加特征:
| 机器学习 | 深度学习 |
|---|---|
| 可以从较小的数据集进行训练和推断 | 需要大量数据 |
| 较短的训练时间,可以使用 CPU 完成 | 较长的训练时间,需要 GPU 才能有效训练 |
| 进行简单的相关性分析 | 进行非线性复杂相关性分析 |
| 大多是可解释的 | 不透明的模型,难以解释 |
表 7.1 – 机器学习与深度学习的区别
关于人工智能的伦理和社会影响的提示
关于伦理和社会影响的讨论可能离我们的日常工作较远,但考虑到我们的项目通常在商业环境中展开,因此建议考虑其更广泛的影响。机器学习和深度学习的伦理与社会影响涵盖了多个方面,包括以下内容:
偏差:与偏差误差类似,机器学习模型可能继承训练数据中的偏差,进而导致歧视性结果。偏差可以在机器学习生命周期的各个阶段引入,从数据收集到模型部署。为了训练我们的模型,获取无偏的数据非常重要,并且应定期审计模型以检测并修正偏差。
透明性:复杂机器学习模型的不透明性给监管机构带来了挑战,可能削弱用户的信任。许多 DeFi 项目正在积极寻求监管批准,以促进资金从传统银行体系流向 DeFi 世界。鉴于金融领域的高度监管性质,在该领域工作的数据科学家必须努力提升模型的可解释性,并向监管机构提供决策的解释。
解决这些伦理问题需要一个多学科的方式,涉及技术开发者、政策制定者、伦理学家等。作为从事模型工作专业人士,我们需要牢记这些挑战,尤其是在选择数据集、进行数据预处理或在现实世界中评估模型结果时。
摘要
在本章中,我们深入探讨了人工智能的基本概念,这将为我们在本书第二部分中的旅程奠定基础。我们探讨了包括监督学习、无监督学习和强化学习在内的各种任务类型。通过一个实践示例,我们深入了解了典型的机器学习过程,包括模型选择、训练和评估。
在本章中,我们获得了与机器学习中常见挑战相关的基本知识,如在模型欠拟合和过拟合之间找到正确的平衡,存在不平衡数据集,以及哪些评估指标适用于训练过这些数据集的模型。理解这些概念对于任何成功的机器学习项目至关重要。
此外,我们深入学习了深度学习的基础知识,使用 Keras 探索了神经网络的关键组件。此外,我们实现了一个流程来处理一个监督学习问题,亲自体验了所有概念的应用。
在下一章,我们将讨论一个重要的话题——情感分析。
进一步阅读
想要了解更多本章涵盖的主题,请参考以下资源:
-
定义:
-
Igual, L. 和 Seguí, S. (2017). 数据科学导论:基于 Python 的概念、技术和应用方法。Springer。
-
Ertel, W. (2018). 人工智能导论。Springer。
-
Skansi, S. (2018). 深度学习导论:从逻辑演算到人工智能。Springer。
-
Ian Goodfellow, Yoshua Bengio, 和 Aaron Courville. (2016). 深度学习。可在
www.deeplearningbook.org/查阅。 -
Chollet, F. (2017). 使用 Python 进行深度学习。Manning 出版公司。
-
Müller, A. C. 和 Guido, S. (2016). 使用 Python 进行机器学习导论:数据科学家指南。O’Reilly Media 出版社。
-
VanderPlas, J. (无日期)。什么是机器学习? Pythonic Perambulations。可在
jakevdp.github.io/PythonDataScienceHandbook/05.01-what-is-machine-learning.xhtml查阅。 -
从网站挖掘地址:Furneaux, Nick. 研究加密货币, 第九章。理解、提取和分析区块链证据,Wiley,2018 年。第 125 页。
-
James, G., Witten, D., Hastie, T., 和 Tibshirani, R. (2022). 统计学习导论:应用篇。R. Springer 出版社。
-
Gymnasium 文档:
gymnasium.farama.org/。 -
Introduction – Spinning up 文档。(无日期)。欢迎来到深度强化学习中的 Spinning Up!Spinning Up 文档。可在
spinningup.openai.com/en/latest/user/introduction.xhtml#what-this-is查阅。 -
Nansen 钱包标签与表情符号:它们是什么意思? (2023 年 3 月 14 日)。Nansen – 加密货币、DeFi 和 NFT 分析。可在
www.nansen.ai/guides/wallet-labels-emojis-what-do-they-mean#alpha-labels查阅。
-
-
流水线:
-
EliteDataScience. (2022 年 7 月 8 日). 什么是偏差-方差权衡?(信息图表)。可在
elitedatascience.com/bias-variance-tradeoff查阅。 -
Sklearn.ensemble.RandomForestClassifier。(无日期)。scikit-learn。检索于 2023 年 3 月 14 日,网址
scikit-learn.org/stable/modules/generated/sklearn.ensemble.RandomForestClassifier.xhtml。 -
SMOTE 过采样。(无日期)。机器学习精通。可在
machinelearningmastery.com/smote-oversampling-for-imbalanced-classification/查阅。 -
Nyuytiymbiy, K. (2022 年 3 月 28 日). 机器学习与深度学习中的参数与超参数。Medium。可在
towardsdatascience.com/parameters-and-hyperparameters-aa609601a9ac查阅。 -
Chapter07/ML_warmup中的热力图:T, D. (2019 年 7 月 25 日). 混淆矩阵可视化。Medium。可访问medium.com/@dtuk81/confusion-matrix-visualization-fc31e3f30fea。 -
在 Colaboratory 中使用 Kaggle 数据集的教程。跟随
Chapter07/ML_warmup的内容非常有用:Gupta, K. (2022 年 8 月 24 日). 如何将 Kaggle 数据集加载到 Google Colab 中? Analytics Vidhya。可访问www.analyticsvidhya.com/blog/2021/06/how-to-load-kaggle-datasets-directly-into-google-colab/。 -
Pramoditha, R. (2022 年 1 月 26 日). 如何选择神经网络的激活函数。Medium。可访问
towardsdatascience.com/how-to-choose-the-right-activation-function-for-neural-networks-3941ff0e6f9c。 -
Gupta, A. (2022 年 5 月 24 日). 深度学习优化器的全面指南。Analytics Vidhya。可访问
www.analyticsvidhya.com/blog/2021/10/a-comprehensive-guide-on-deep-learning-optimizers/。 -
PEP 20 – Python 之禅。(2022 年 3 月 15 日). PEP 0 – Python 增强提案(PEPs)索引 | peps.python.org。可访问
peps.python.org/pep-0020/。 -
Keras 团队。 (2020 年 4 月 17 日). Keras 文档:不平衡分类:信用卡欺诈检测。Keras:深度学习工具。可访问
keras.io/examples/structured_data/imbalanced_classification/。 -
Ramchandani, P. (2021 年 4 月 10 日). 随机森林与偏差-方差权衡。Medium。可访问
towardsdatascience.com/random-forests-and-the-bias-variance-tradeoff-3b77fee339b4。 -
使用贝叶斯优化调优:Rendyk. (2023 年 8 月 17 日). 调整神经网络深度学习的超参数和层次结构。Analytics Vidhya。可访问
www.analyticsvidhya.com/blog/2021/05/tuning-the-hyperparameters-and-layers-of-neural-network-deep-learning/。 -
如何在 Python 中使用 Keras 进行深度学习模型的网格搜索超参数。(2022 年 8 月)。机器学习精通。可访问
machinelearningmastery.com/grid-search-hyperparameters-deep-learning-models-python-keras/。
-
第八章:情感分析 – 自然语言处理(NLP)与加密新闻
自然语言处理(NLP)属于人工智能领域,致力于计算机对文本的理解。近年来,随着如 ChatGPT 等工具的出现,NLP 已经成为我们日常生活中不可或缺的一部分。然而,金融行业已经在相当长一段时间里利用 NLP,尤其是在基本面分析方面。
基本面分析旨在根据公开可得的信息确定资产的内在价值,如股票、代币或 NFT 艺术作品。在传统金融中,文本数据来源于定期向美国证券交易委员会(SEC)提交的报告(如 10K 表格或 10Q 表格),包括财务报表、专业媒体新闻、社交媒体平台如 X(前身为 Twitter)以及其他渠道。Web3 创造了一个类似的环境,市场活动持续不断,X 和新闻平台成为主要的文本资源。值得注意的是,虽然大多数 Web3 公司目前可能还没有义务提交监管报告,但这些数据源最终有可能会成为大多数公司可以获取的资源。
自然语言处理在金融领域的应用涵盖了多个方面,包括以下内容:
-
情感分析:确定文本的积极性、消极性或中立性,这些文本可能是新闻文章、社交媒体帖子(推文、Reddit 等)等。这些算法还可以提供关于情感极性和主观性的见解,帮助评估对公司、行业、市场、政府决策、加密货币发展等的情感。
-
主题建模:帮助根据文档所涵盖的主题对大量财务文档进行分类和组织。这有助于高效管理和访问相关信息。
-
摘要:在一个内容不断产生的世界里,显然没有足够的时间和/或资源去分析和给每个内容排出层次。NLP 技术正被应用于收集并创建简短的文档摘要,方便分析人员处理。
-
欺诈检测:利用 NLP 技术审查电子邮件、聊天记录、财务文件、转录对话等,发掘潜在的欺诈活动模式。
-
交易:将 NLP 工具纳入交易策略中,发出市场趋势的信号或预测,或增强基本面分析交易员的决策过程。
NLP 技术的数据源是被归类为非结构化的文本。我们周围充斥着这样的文本,且每秒钟都会产生更多。在第三章中我们探讨了其中一些文本来源;本章将继续探讨其他文本来源。
在本章中,我们将分析来自 Crypto Panic 的新闻情感。为此,我们将构建一个神经网络(NN),并解释预训练嵌入的概念和使用方法。我们将使用加密新闻数据集和传统金融新闻数据集来训练我们的模型。此外,我们还将学习如何为神经网络使用预处理文本的基本知识,以及如何评估此类模型的结果。
在撰写本文时,ChatGPT 已经成为现实。公开的信息揭示了它在一个广泛的多语言语料库上进行了训练,并利用强化学习不断提高其性能。我们将学习如何将 ChatGPT 集成到 Crypto Panic 数据集的情感分析中。这可以作为一个现成的工具来使用,同时我们构建一个专门的语料库来训练我们的模型。
在本章中,我们将覆盖以下主要主题:
-
一种用于情感分析的深度学习管道,包括准备、模型构建、训练和评估阶段。
-
集成 ChatGPT 进行情感分析
技术要求
在本章中,我们将使用 第七章 中介绍的库工具——即 scikit-learn 和 Keras。此外,我们还将使用 NLTK,这是一个 Python 库,对处理人类语言数据非常有帮助。NLTK 包含了一系列模块和函数,使我们能够执行诸如分词、词干提取和词性标注等任务。这个库简化了处理大量文本数据集的过程,使它们能够与机器学习或深度学习模型进行集成。
如果你之前没有使用过 NLTK,可以使用以下代码进行安装:
pip install nltk
nltk 的文档可以在 https://www.nltk.org 找到。另一个在处理文本操作和清理时非常重要的库是 re,即正则表达式的缩写。正则表达式是一串字符,用于定义搜索模式。以下是一个示例:
| 模式 | 搜索标准 |
|---|---|
| [a-z] | 匹配范围 a-z 中的任何单个字符 |
| [0-9A-Fa-f] | 匹配任何十六进制数字 |
表 8.1 – “re” 模式示例
re 库提供了使用上述模式的函数和方法。例如,re.sub 将所有与模式匹配的字符替换为指定的字符串。有关函数的完整列表,请访问 https://docs.python.org/3/library/re.xhtml#module-re。
在我们的工作中,我们将使用 Google 的 Colaboratory 平台,该平台已包含核心库的导入。然而,对于特定任务,还需要其他的导入。
你可以在本书的 GitHub 仓库中找到本章的所有数据和代码文件,地址为github.com/PacktPublishing/Data-Science-for-Web3/tree/main/Chapter08。我们建议你浏览Chapter08文件夹中的代码文件,以便跟随学习。
示例数据集
本章中,我们将合并两个标题数据集;你可以在进一步阅读部分和代码中找到相关来源的链接。数据集如下:
-
金融短语库:该数据集也可在 Kaggle 上获取,包含一个标题,并附带零售投资者角度的情感分析标签。它由多个数据集组成,每个数据集根据短语情感共识的程度对句子进行分类。在本练习中,我们将使用Sentence_AllAgree数据集。
-
CryptoGDELT2022:该数据集来自论文Cryptocurrency Curated News Event Database From GDELT,包含从全球事件、语言与情感数据库(GDELT)提取的新闻事件。它涵盖了 2021 年 3 月 31 日至 2022 年 4 月 30 日之间的新闻事件。该数据集包含多种情感得分和手动标注方法。在本练习中,我们将仅使用手动标注。
让我们开始构建我们的管道。
构建我们的管道
在 NLP 管道中,准备工作通常包括一个预处理步骤,在该步骤中我们清理和规范化数据。接下来,特征表示步骤将语言转换为可以供我们选择的模型使用的输入。完成这些后,我们便可以开始构建、训练和评估模型。这个战略计划将在接下来的章节中实现。
准备
语言在多种形式中表现出来。存在格式化的细微差异,例如大写或标点符号;一些作为语言辅助的词汇,其本身没有真正的语义意义,比如介词;以及包括表情符号在内的特殊字符,进一步丰富了语言的表现形式。为了处理这些数据,我们必须将原始文本转换为数据集,并遵循与数字数据集类似的标准。这个清理过程使我们能够去除异常值、减少噪音、管理词汇大小,并优化数据以便 NLP 模型处理。
数据清理管道的基本流程图如下所示:

图 8.1 – 清理图示
让我们深入了解这些步骤。
规范化
规范化包括一系列任务,如小写化、移除 HTML 痕迹、链接和表情符号。我们的目标是清理数据库,只留下有效的词汇。
此外,这一过程还涉及去除那些对模型缺乏信息量或可能引入偏差的词汇,从而导致不理想的预测。根据任务的不同,我们将选择需要删除的词汇。这个步骤还处理了去除可能遗漏在 停用词 清理过程中的词汇。
我们还可以将 Unidecode 文本转换为 ASCII 文本。Unidecode 支持来自不同语言的字符,将它们转化为最接近的 ASCII 对应字符。例如,西班牙字符“ñ”在 ASCII 中变为“n”。我们在 Database_and_Preprocessing.ipynb 中通过以下代码片段实现了这一转换:
text = unidecode.unidecode(text)
规范化通过将所有文本呈现为一致的格式来促进统一性,指引模型的注意力集中在内容上,而非表面差异。
停用词
我们在这里的目标是排除对模型贡献较小的语义价值或意义的词汇。经常使用的词汇,如冠词(“a”,“the”,“an”)、介词(“on”,“at”,“from”,“to”)、连词(“and”,“so”,“although”)和代词(“she”,“he”,“it”),在语言中起到功能性作用,但缺乏模型可以利用的实质性语义内容。
因此,这些词汇通常在预处理过程中被过滤掉。可以按语言下载停用词集,并通过 NLTK 直接应用于我们的清理过程。在 Database_and_Preprocessing.ipynb 中,我们通过以下代码片段下载了英语停用词:
nltk.download('stopwords')
stop_words = set(stopwords.words('english'))
这一过程减少了数据中的噪声,并有助于提高模型的效率。
分词
分词是将数据库中的文本拆分为较小的有意义单位,称为词元。这些单位可以是句子或单词。例如,我们来看一下以下标题:
“SEC 正在调查 Coinbase 的 Earn 产品、钱包服务和 交易活动”*
当分词为单词时,输出结果如下:
['SEC', 'investigating', 'Coinbase', 'Earn', 'product', ',', 'wallet', 'service', '``exchange', 'activity']
分词产生了模型可以有效处理的结构化输入,促进了数据分析。此类分析指导了词汇大小的选择,用于降维,在 Database_and_Preprocessing.ipynb 中可以找到此类降维的示例。此分析展示了在分析过的数据集中最常出现的词汇。该分析得出以下结果:

图 8.2 – 分析过的标题中最常出现的词
词形还原和词性标注(POS)
这些技术将单词还原为其基本形式或词根。这使我们能够通过选择那些已变化的单词并用其词根替代它们,减少我们需要处理的单词多样性。在我们的示例句子(“SEC 正在调查 Coinbase 的 Earn 产品、钱包服务和交易活动”)中,单词investigating将变为investigate。
词形还原的准确性取决于库对单词在句子中上下文或功能的理解。词性标注为我们的分析提供了这种上下文信息。以下是一个示例:
nltk.pos_tag
词性标注帮助我们根据单词在句子或文档中的位置,程序化地为每个单词分配上下文。以下是一个示例:
word= ['SEC', 'investigating', 'Coinbase', 'Earn', \
'product', ',', 'wallet', 'service', 'exchange','activity']
[nltk.pos_tag([w]) for w in word]
[[('SEC', 'NNP')], [('investigating', 'VBG')], [('Coinbase', 'NN')], [('Earn', 'NN')], [('product', 'NN')], [(',', ',')], [('wallet', 'NN')], [('service', 'NN')], [('exchange', 'NN')], [('activity', 'NN')]]
清理后的句子结果如下所示:
investigate coinbase earn product wallet service exchange activity
让我们来看一些额外的预处理技术:
-
词干提取:这涉及从单词中去除前缀和后缀,以推导出一个共同的基本形式,称为“词干”。得到的词干可能并不总是形成有效的单词,但它旨在捕捉核心含义。
-
命名实体识别(NER):该技术自动识别并分类文本中的命名实体(例如,人名、地名、组织名和日期)。NER 从非结构化文本中提取结构化信息,将实体分类到预定义的类别中。我们在《第三章》中讨论的 X(前身为 Twitter)数据集就是这一方法的一个示例。
-
依存句法分析:该技术分析句子的语法结构,以建立单词之间的关系。它创建了一个层次结构,其中每个单词与其支配单词(“头”)相连,并分配一个语法角色(“依存标签”)。
检查点
该管道的逐步版本已详细列出在Database_and_Preprocessing.ipynb中。如果你想跳过这一部分,生成的.csv文件已经上传到本书的 GitHub,并可以通过preprocessed.csv访问。
特征表示
在预处理阶段之后,下一步是将得到的原始文本数据转换为模型可以利用的特征,用于统计推断。目标是从文本中提取相关信息,并以算法能够理解的方式进行编码。实现这一目标的方法有多种,但通常涉及将单词表示为向量,并衡量单词在文档中的频率。一些常见的技术包括词袋模型、词频-逆文档频率(TF-IDF)和词嵌入。我们简要描述它们。
词袋模型
该技术通过统计单词出现的次数构建一个表示文档中所有单词的向量。它忽略句子的顺序和单词的上下文。可以使用来自 scikit-learn 库的sklearn.feature_extraction.text.CountVectorizer来实现该方法。这个方法比较基础,丢失了重要的上下文信息,并且可能会创建一个非常稀疏的矩阵,因为词汇表非常庞大:

图 8.3 – 词袋模型。文本摘自 https://rif.technology/content-hub/crypto-credit-card/
此外,通过结合 n-grams(即将具有上下文意义的两个或多个单词连接在一起)可以增强这种方法。例如,“自然语言”,“机器学习”和“新闻稿”在组合时能 encapsulate 特定的概念,但单独来看,它们并不保留这些概念。将 n-grams 融入到词袋模型中,可以进一步扩展词汇表。
TF-IDF
这是一种替代方法,使用sklearn.feature_extraction.text.TfidfVectorizer。
词嵌入
词嵌入将单词表示为连续空间中的密集向量。通过捕捉单词之间的关系,这种方法保留了上下文和语义信息。Word2Vec 和 GloVe (www.tensorflow.org/tutorials/text/word2vec) 是生成词嵌入的流行算法。这些嵌入可以在大型文本语料库上进行预训练,或者针对特定任务进行微调。在我们的模型中,我们使用了 GloVe (nlp.stanford.edu/projects/glove) 向量。
GloVe,特别是,通过一种无监督学习算法开发的预训练向量。这种方法利用文本中普遍存在的线性子结构,通过测量向量之间的距离来评估语义相似性。GloVe 网站提供了一个经典示例,说明了模型所识别的关系:

图 8.4 – GloVe 发现的单词结构示例(来源:nlp.stanford.edu/projects/glove/)
模型构建
我们正在处理一个监督学习任务,目标是将 Crypto Panic 的头条新闻分类为正面、负面和中立。为此,我们将使用Modeling.ipynb文件。
LSTM 是一种递归神经网络(RNN),能够学习长期依赖关系,在文本任务中显著优于常规的 RNN。该结构常用于自然语言处理任务,因为它能够很好地建模输入数据的序列并保留句子或文档中单词之间的依赖关系。因此,它不仅可以基于当前输入进行预测,还可以考虑远程信息——即上下文——而不仅仅是特定的单词。需要注意的是,虽然 LSTM 在捕捉长期依赖关系方面可能更有效,但其性能也可能取决于一些因素,如具体任务、数据集的大小以及模型的架构。在某些情况下,基于 Transformer 的高级架构(如 BERT 和 GPT)在某些自然语言处理任务中也表现出了更优的性能。
Christopher Olah 在他的博客中对该模型进行了很好的介绍,他是这样描述的:
“人类在思考时不会每一秒钟都从头开始。当你阅读这篇文章时,你是基于对前一个单词的理解来理解每一个新单词的。你不会把所有东西都抛弃然后重新开始思考。你的思维 具有持续性。”
LSTM 是一种专门的 RNN 变种,旨在检测数据序列中的模式,无论这些模式来源于传感器数据、资产价格还是自然语言。其独特之处在于与传统的 RNN 相比,LSTM 能够在更长的时间内保存信息。RNN 具有短期记忆,只能在当前神经元中保留信息,这导致它在处理更长序列时的预测能力有限。当内存超出时,模型会简单地丢弃最旧的数据,并用新数据替换它,而不考虑被丢弃的数据是否重要。LSTM 通过选择性地将相关信息保存在单元状态中,除了传统的短期记忆存储在隐藏状态外,克服了这种短期记忆问题。
在每个计算步骤的开始,我们有当前的输入 x(t)、长时记忆的前一个状态 c(t-1),以及存储在隐藏状态中的短期记忆的前一个状态 h(t-1)。在过程的结束时,我们获得更新后的单元状态和新的隐藏状态。单元状态携带着信息和数据集的时间戳,使其能够从输入数据的顺序中提取意义。
这三个输入通过三个门进行处理,每个门都有其特定功能:
-
遗忘门:该门决定哪些当前信息和先前信息被保留,哪些被丢弃。它将隐藏状态的先前状态和当前输入进行整合,并通过一个 sigmoid 函数进行传递。sigmoid 函数输出的值在 0 到 1 之间,0 表示先前的信息被认为无关并可被遗忘,1 则表示该信息应被保留。最终的结果将乘以当前的单元状态。
-
输入门:该门决定当前输入在解决任务中的重要性。它量化了由输入 x(t) 传递的新信息的相关性。当前输入与上次运行的隐藏状态相乘。输入门认为重要的所有信息都被加到单元状态中,形成新的单元状态 c(t)。这个新的单元状态成为长期记忆的当前状态,并将在下一次运行中使用。
-
输出门:LSTM 模型的输出在隐藏状态中计算:

图 8.5 – 单元状态
为了与 LSTM 进行交互,我们需要输入具有统一长度的向量。为了满足这一要求,我们必须按照以下方式顺序地对预处理后的输入文本进行编码:
-
tokenizer.texts_to_sequences(X_train):此步骤将每个文本转换为一个整数序列,使用 tokenizer 中最常见的词汇。如果 tokenizer 的词汇表中缺少某些词汇,则会使用预定义的<OOV>(超出词汇表)标记。 -
pad_sequences:此函数将先前转换的序列转换为形状为(序列数,所需序列长度)的二维数组。maxlen参数可以由用户定义,或者默认设置为列表中最长期序列的长度。此外,用户可以选择填充发生在序列的开始还是结束。
我们构建的模型以嵌入层作为其核心元素,并设置trainable = False以保持来自 Glove500 的见解。如果我们选择从头开始训练,则需要将该参数设置为True:
model = Sequential()
model.add(Embedding(input_dim = len(word_index) + 1 ,\
output_dim = embedding_dim ,\
weights = [embedding_vectors],\
input_length = max_length ,\
trainable = False))
此外,我们的设计包括了一个 LSTM 层、一个全连接层和一个 dropout 层。dropout 层是一种常用的正则化技术,旨在防止过拟合,其通过在每次训练的前向传播中随机停用(即将其置为零)一部分神经元来操作。这有助于防止网络过度依赖特定的神经元,并鼓励网络学习更为鲁棒且具备泛化能力的特征:
model.add(Bidirectional(LSTM(embedding_dim, activation = 'relu',\
dropout = 0.0 ,\
recurrent_dropout = 0.0)))
model.add(Dense(embedding_dim, activation='relu'))
model.add(Dropout(0.3))
对于最后的全连接层,我们使用'softmax'激活函数,它为每个训练类别分配一个小数概率:
model.add(Dense(label_distinct, activation='softmax',\
bias_initializer = 'zeros'))
我们通过利用'categorical_crossentropy'作为损失函数来编译模型,这是多类别分类任务(包括两个以上类别)的标准选择,正如在这里的情况:
model.compile(loss = 'categorical_crossentropy',\
optimizer = Adam(1e-3), \
metrics = ['accuracy'])
检查点
该部分管道的逐步版本显示在Modeling.ipynb中。如果你想跳过这一部分,生成的模型和分词器已经上传到本书的 GitHub 仓库,并可以通过chapter8_model.h5和text_tokenizer.json进行访问。
训练与评估
我们可以使用以下代码片段训练模型:
model.fit(X_train_pad, y_train, batch_size = batch_size, \
epochs = 10, validation_data = (X_test_pad, y_test), \
verbose = 0, callbacks=[tensorboard_callback])
在完成训练后,我们通过三种不同的方法评估其性能和结果:
小测试:我们查找测试样本,应用模型,并进行评估。我们必须始终记得对样本进行预处理,并将它们以模型准备好的形状传递给模型。
log 文件夹用于存储训练和验证结果:
tensorboard_callback = \
tf.keras.callbacks.TensorBoard(log_dir="./logs")
这个文件夹在随附的训练说明中提到(callbacks=[tensorboard_callback])。TensorBoard 然后访问这个文件夹以显示结果。
ROC AUC 曲线:根据 Jason Brownlee 的博客,“ROC 曲线是通过计算不同阈值下模型预测集的假阳性率和真阳性率来总结模型行为的诊断图。” ROC 曲线是二分类任务的评估指标。为了将其应用于我们的多类问题,我们必须通过 一对一 (OvO) 或 一对多 (OvA)/一对其余 (OvR) 方法将多类问题转化为二类问题。在 OvR 中,我们评估每个类别与其他类别的关系;在 OvO 中,我们评估每对类别之间的关系。选择这些技术取决于特定问题的细节、类别数量、计算资源和数据集特点。某些机器学习库,如 scikit-learn,为多类分类算法提供了 OvA 和 OvO 策略的选择。
在这种情况下,我们使用 OvA 方法,其中我们衡量模型预测每个标签的效果,将一个标签视为真实,其他所有标签视为假。通过这种方式,我们可以绘制 ROC AUC 曲线。曲线越接近 1,模型越好;越接近 0.5,模型的表现越差:

图 8.6 – 应用的 ROC AUC 曲线
在处理不平衡数据集时,准确率和 ROC AUC 曲线可能会过于乐观。
F1 分数:通过 OvA 角度解决多类分类问题时,我们获得一组二值值,从中可以计算精确度、召回率和 F1 分数。F1 分数在目标是最小化假阳性和假阴性时更加适用。这个指标结合了精确度和召回率的信息,是它们的调和平均数。F1 分数的公式如下:
F1 分数 = 2 * 精确度 * 召回率 _____________ 精确度 + 召回率
Joos Korstanje 在他的博客中简洁地总结了这一点:
-
如果模型的精确度和召回率都很高,模型将获得高 F1 分数
-
如果精确度和召回率 都较低,模型将获得较低的 F1 分数
-
如果精确度或召回率较低,而另一个较高,模型将获得中等的 F1 分数。
上述度量可以通过以下代码片段生成:
classification_report(y_test, y_pred_onehot, target_names=target_names
该模型的加权平均 F1 分数为 0.72。
我们可以使用以下代码片段保存已训练的模型,以备将来使用:
text_tokenizer_json = tokenizer.to_json()
with io.open('text_tokenizer.json','w',encoding='utf-8') as f:
f.write(json.dumps(text_tokenizer_json, \
ensure_ascii=False))
model.save('chapter8_model.h5')
在本书 GitHub 仓库中的 Chapter08/app.py 文件里,我们开发了一个应用程序,它从 Cryptopanic API 获取标题,应用已训练的情感模型,并在控制台中显示结果。
关于 NLP 挑战的说明
由于人类语言固有的复杂性,NLP 面临着多个挑战,这些挑战可能会显著影响其模型的表现和准确性。然而,存在潜在的缓解策略来应对这些挑战:
歧义性:单词和短语通常具有多重含义,正确的解释依赖于上下文。这种复杂性即使对母语和非母语使用者来说也是一种挑战,尤其是在隐喻的使用中。同样,模型在解释用户意图时也会遇到困难。为了解决这个问题,可以设计模型以纳入更广泛的上下文信息,通过利用周围的单词和短语来进行更准确的意义推断。
语言多样性:语言在语法、句法和语义上展现出广泛的差异。此外,俚语、地区方言和文化差异进一步加剧了语言的多样性。NLP 模型如果只在特定类型的数据上训练,可能难以在多样的语言环境中推广应用。为了解决这一限制,模型可以在更广泛且多样化的数据集上进行训练,以涵盖各种语言模式。
数据稀缺性:NLP 模型在训练过程中严重依赖大量的标注数据。然而,为所有可能的语言变体和应用获取标注数据是一个挑战。迁移学习技术,如在大语料库上进行预训练并对特定任务进行微调,通过减轻对大量标注数据的需求,提供了一个可行的解决方案。
伦理考量与偏差:NLP 模型可能会无意中学习到训练数据中的偏差,从而导致偏向的输出。解决这个问题需要精心策划多样化和具有代表性的训练数据集、定期审查模型的偏差,并实施公平意识的训练技术。
虽然 NLP 面临许多挑战,但机器学习技术的持续研究和进步有助于克服这些障碍。
ChatGPT 集成
当时间紧迫且无法收集必要的数据来训练新模型以构建分类器时,我们可以考虑使用预训练模型,如 TextBlob、spaCy 或 Hugging Face 库提供的模型。此外,我们还可以无缝集成现成的模型,如 ChatGPT。
我让 ChatGPT 自我介绍,以下是它的回答:
“我是 ChatGPT,一个由 OpenAI 开发的大型语言模型,基于 GPT-3 架构。我在大量文本数据上进行训练,能够生成类人回答,回应各种问题和提示。我的主要目的是帮助用户生成文本,无论是写文章、回答问题,还是完成创意任务。我在各种话题上拥有广泛的知识,包括科学、技术、历史和文学等。我旨在理解自然语言,能够以 对话式的方式 回复基于文本的输入。*”
本章特别相关的是最后一句话。该工具精通多样的词汇,能够处理文本输入。
ChatGPT 的架构与 LSTM 不同。它使用transformer架构,使其能够理解和生成自然语言文本。Transformer 使用自注意力机制来捕捉句子中单词之间的关系,从而允许对单词进行并行处理,而不像 LSTM 那样进行顺序处理。Transformer 被用于翻译语言、总结长文章、回答问题、完成句子,甚至创作故事。BERT 和 GPT 是常见的 Transformer 模型。
在Chapter07/chat_gpt integration文件中,我们复制了与前一部分相同的用例,在该用例中,我们与 Cryptopanic API 进行了交互,提取标题,应用 ChatGPT 模型,并在控制台中显示输出,取得了优异的结果。为了方便操作,需要一个 API 密钥,可以通过以下步骤在 OpenAI 官网生成:
-
访问
platform.openai.com/docs/api-reference,前往注册部分,然后在其网站上进行注册。 -
在左侧,你会看到一个下拉菜单,写着查看 API 密钥。点击这个菜单,进入生成新 API 密钥的页面:

图 8.7 – ChatGPT – API 密钥登录页面
- 生成并安全存储生成的 API 密钥非常重要,因为一旦生成,它们就无法再被检索:

图 8.8 – Chat GPT – API 密钥生成
本节的目的是要认识到 ChatGPT 的存在,它能够完成出色的工作,并通过连接 API 来解决情感分析问题,这可能是一个临时解决方案,特别是在没有足够数据来训练专用模型的情况下。
可以使用任务特定的数据对 ChatGPT 进行微调,以适应特定任务或领域。此过程使模型能够适应目标应用的细微差别和需求。例如,我们可以将模型定制为生成更简短的回答,减少在提示中所需的上下文量,以提高响应效果,并定义它如何处理边缘情况。假设我们希望将一个专门的机器人集成到公司内部通讯系统中,提供简洁的加密货币新闻摘要,具有特定的语气或格式。这可以通过该训练过程来实现。有关该过程的详细文档,请参阅 platform.openai.com/docs/guides/fine-tuning,并且可以在 进一步 阅读 部分找到逐步教程。
摘要
自然语言处理(NLP)领域正在迅速发展,为从非结构化数据(如文本)中提取洞察提供了有效的手段。在本章中,我们介绍了该领域,展示了其中的一个典型任务,阐明了工作流程,讨论了相关数据,并使用嵌入进行模型训练。此外,我们还展示了模型评估过程,并展示了如何将其集成到一个程序中,该程序从 CryptoPanic API 获取头条新闻。
值得强调的是,积累大量数据对高模型准确性至关重要。然而,在无法构建此类模型的情况下,也可以采取替代方案。我们探讨了其中一种解决方案,涉及使用 ChatGPT API,它提供了访问经过全面数据集训练的文本机器人。
在接下来的章节中,我们将深入探讨数据团队如何为艺术团体提供支持,帮助他们通过使用 NFT 将艺术作品转化为独特的产品。
进一步阅读
要了解更多关于本章内容的主题,请查阅以下资源:
-
引言:
-
Bird, Steven, Edward Loper 和 Ewan Klein(2009),Python 自然语言处理。O’Reilly Media Inc. 可在
www.nltk.org/book/查阅。 -
Yordanov, V.(2019 年 8 月 13 日)。文本自然语言处理简介。Medium。可在 https://towardsdatascience.com/introduction-to-natural-language-processing-for-text-df845750fb63 查阅。
-
Gabriel Doyle 和 Charles Elkan。(无日期)。金融主题模型。可在
pages.ucsd.edu/~gdoyle/papers/doyle-elkan-2009-nips-paper.pdf查阅。 -
Sigmoider.(2018 年 5 月 3 日)。开始使用 NLP(第一部分)。Medium。可在 https://medium.com/@gon.esbuyo/get-started-with-nlp-part-i-d67ca26cc828 查阅。
-
Suhyeon Kim, Haecheong Park, 和 Junghye Lee.(无日期)。基于 Word2vec 的潜在语义分析(W2V-LSA)用于主题建模:区块链技术趋势分析的研究。
www.sciencedirect.com/science/article/pii/S0957417420302256。 -
数据科学与机器学习的现状(2022)。Kaggle:您的机器学习和数据科学社区。
www.kaggle.com/kaggle-survey-2022。 -
非常好的 ChatGPT 微调教程:Tech-At-Work。 (2023 年 9 月 11 日)。轻松微调 ChatGPT 3.5,超越 GPT-4![视频]。YouTube。
www.youtube.com/watch?v=8Ieu2v0v4oc。
-
-
示例数据库:
-
Malo, P., Sinha, A., Korhonen, P., Wallenius, J., 和 Takala, P. (2014 年)。好债务还是坏债务:检测经济文本中的语义取向。信息科学与技术协会期刊,65(4),782-796。
www.kaggle.com/datasets/ankurzing/sentiment-analysis-for-financial-news。 -
Manoel Fernando Alonso Gadi 和 Miguel Ángel Sicilia.(2022 年 10 月 10 日)。来自 GDELT 的加密货币精选新闻事件数据库 [pdf]。Research Square。
assets.researchsquare.com/files/rs-2145757/v1_covered.pdf?c=1665769708。
-
-
预处理:
-
Bird, S., Klein, E., 和 Loper, E. (2009 年)。使用 Python 进行自然语言处理。O’Reilly Media。
-
Sklearn.feature_extraction.text.CountVectorizer。(无日期)。scikit-learn。检索于 2023 年 3 月 24 日。
scikit-learn.org/stable/modules/generated/sklearn.feature_extraction.text.CountVectorizer.xhtml。 -
Sklearn.feature_extraction.text.TfidfVectorizer。(无日期)。scikit-learn。检索于 2023 年 3 月 24 日。
scikit-learn.org/stable/modules/generated/sklearn.feature_extraction.text.TfidfVectorizer.xhtml。
-
-
模型:
-
Dudeperf3ct。 (2019 年 1 月 28 日)。LSTM 和 GRU 的力量。博客。
dudeperf3ct.github.io/lstm/gru/nlp/2019/01/28/Force-of-LSTM-and-GRU/#bag-of-words-model。 -
Brandon Rohrer。 (无日期)。循环神经网络(RNN)和长短期记忆(LSTM) [视频]。YouTube。
www.youtube.com/watch?v=WCUNPb-5EYI&list=PLVZqlMpoM6kaJX_2lLKjEhWI0NlqHfqzp。 -
Pennington, J.(无日期)。GloVe:全球词向量表示。斯坦福自然语言处理组。
nlp.stanford.edu/projects/glove/。 -
Jason Brownlee. (2020). 深度卷积神经网络在情感分析(文本分类)中的应用。机器学习大师。可在
machinelearningmastery.com/develop-word-embedding-model-predicting-movie-review-sentiment/获取。
-
-
评估:
-
T., B. (2022 年 12 月 9 日). 多分类分类指标的综合指南。Medium。可在
towardsdatascience.com/comprehensive-guide-on-multiclass-classification-metrics-af94cfb83fbd获取。 -
Jason Brownlee (2021). 不平衡分类的评估指标概览。机器学习大师。可在 https://machinelearningmastery.com/tour-of-evaluation-metrics-for-imbalanced-classification/获取。
-
Korstanje, J. (2021 年 8 月 31 日). F1 得分。Medium。可在
towardsdatascience.com/the-f1-score-bec2bbc38aa6获取。
-
第九章:NFT 的生成艺术
“我使用数据作为颜料,借助人工智能的画笔进行绘画。”
——Refik Anadol
在本章中,我们将进行一次艺术休息,尽情发挥创造力。虽然我们之前的重点是分析区块链上由他人生成的内容,但在本章中,我们将创造自己的内容,并将其添加到区块链上。
本章的加入源于认识到,作为数据科学家,我们可能会遇到需要与艺术家团队合作,制作或协助制作 NFT 系列的请求。在第四章中,我们研究了 NFT 的艺术应用,并探索了诸如Bored Ape等知名系列,该系列的总交易量为 978,382 ETH(约合 18 亿美元)。我们不清楚他们是否使用了人工智能来制作所有图像,但它们是艺术可以在区块链上拥有和交易的一个很好的案例。为了能够参与这个市场,我们将学习从制作图像到在 OpenSea 上列出销售的整个过程。
一个名为Artsy Monke的系列使用人工智能通过将 Bored Ape 系列与 20 种精选的绘画风格相结合来创作图像。您可以在opensea.io/collection/artsy-monke找到他们的 OpenSea 系列网站。书本封面上的图像是 Artsy Monke #9937。
另一个例子是 Refik Anadol 的机器幻觉系列,这是与 NASA 合作的项目,使用了超过两百万张由国际空间站、哈勃望远镜和 MRO 望远镜等空间机构记录的原始图像,经过人工智能数据处理,创作了六幅画作和一件雕塑作为输入。
人工智能所带来的工具范围超出了本章的讨论范围。然而,我们将讨论三种可能对艺术家团队联系以帮助他们建立 NFT 系列时有用的实际工具:上色、风格迁移和提示生成艺术。我们将从不修改内容的编辑开始,逐步过渡到完全创作图像。最后,我们将学习如何在区块链上创建一个系列并将其列出销售。
在本章中,我们将涵盖以下主要主题:
-
创作色彩——上色工具
-
创作风格——风格迁移工作流程
-
创作提示——文本转图像解决方案
-
变现——铸造和销售 NFT
技术要求
在本章中,我们将为每个部分使用不同的工具。对于上色部分,我们将使用一个名为.zip的程序,该程序需要下载到您的计算机并解压缩。
转到风格迁移部分,我们将使用一个 VGG19 模型,其文档可以在www.tensorflow.org/api_docs/python/tf/keras/applications/vgg19/VGG19找到。它遵循的是 Keras 示例,详见keras.io/examples/generative/neural_style_transfer/。
对于文本到图像部分,我们将与 Leonardo AI 平台进行互动,只需要创建一个账户。此外,我们还将与 OpenSea 平台互动,这要求我们拥有一个有效的钱包,以便进行铸造。
你可以在本书的 GitHub 仓库中找到所有数据和代码文件,链接为github.com/PacktPublishing/Data-Science-for-Web3/tree/main/Chapter09。我们建议你阅读Chapter09文件夹中的代码文件,以便跟随本书学习。本章节中创建的 NFT 系列可以在opensea.io/collection/mysterious-library访问。
创作与颜色 – 着色
给图像着色需要艺术团队付出大量工作。作为数据科学家,我们可以借助一种工具来辅助他们,这个工具可以在遵循艺术方向的同时,轻松地进行绘画。我们所提到的工具叫做Style2Paints,它是一种半自动着色方法,在不需要色彩修正时可以生成自动化的结果。它还提供了一个功能,允许为工具提供提示,以便获得更加定制化的结果。
使用 Style2Paints 实操
一旦安装了 Style2Paints,主页面将像图 9.1所示。左侧有一个颜色样式栏,右侧则有一个色板:

图 9.1 – Style2Paints 主视图
这个工具可以与彩色图像和黑白图像一起使用。请按以下步骤操作:
-
要上传图像进行着色,点击符号。
![]()
-
选择图像的绘画区域并点击确定。
-
在左侧,我们将看到一个已预先着色的图像列表,可以点击并下载。例如,如果我们上传一个基础草图或“线条艺术”,工具将会在网站的左侧建议一些颜色样式。
请参考以下线条艺术示例:

图 9.2 – 书籍装订机,Joseph William Zaehnsdorf,公共领域,来自 Wikimedia Commons
通过使用这些颜色样式,我们可以仅通过点击一种颜色组合,从一张黑白图像创建出八种不同颜色的书籍装订机图像:

图 9.3 – 书籍装帧的彩色版本
也可以编辑已经有一些颜色的图像。例如,我们考虑艺术猴 #9937:

图 9.4 – 艺术猴 #9937
我们可以通过使用位于工具左侧的颜色样式选项轻松更改图像使用的颜色。点击每种颜色组合,图像会发生变化。可以在图 9.5中看到一些示例:

图 9.5 – 彩色艺术猴 #9937
也可以在没有颜色样式建议的情况下手动上色,并使用文档所称的“提示点”颜色调色板。提示的使用场景是保持某种美学一致性或纠正一些颜色样式建议。按照以下步骤操作:
-
通过点击工具右侧的颜色之一来选择一个颜色。
-
在我们想要用选定颜色着色的图像部分添加一个点。这是一个“提示”。
-
点击图标;图像将重新加载,用我们选择的颜色涂绘所选区域。
![]()
关于如何使用这个直观工具的逐步教程可以在进一步 阅读部分找到。
理论
卷积神经网络(CNN)是一种专门用于分析视觉数据的深度神经网络类型。总体而言,CNN 受到人类视觉系统如何处理信息的启发。它们由多个层次组成,这些层次能够自动学习和检测各种特征,如边缘、角落、纹理以及更复杂的模式,从原始像素数据中提取出来。这些学习到的特征随后可用于图像分类、物体检测、人脸识别等任务。
以下是 CNN 的关键组件:
-
卷积层:这是卷积神经网络(CNN)的核心。它将一组可学习的滤波器(也叫卷积核)应用到输入图像上。这个过程被称为特征提取,用于识别图像的不同特征。
-
池化层:此层减少特征图的空间维度,同时保留重要信息。池化有两种类型:最大池化和平均池化。通常在卷积层后应用,以减少在前一层创建的特征图的大小。经过几层卷积和池化层后,特征图被展平成一维向量,作为全连接层的输入。
-
全连接层:这些层类似于传统神经网络中的层,连接不同的层。
我们刚刚详细描述的组件可以按顺序在图 9.6中可视化:

图 9.6 – CNN 的结构。照片由 Alison Wang 提供,来自 Unsplash
CNN 使用标注数据集进行训练。在训练过程中,网络的参数(权重和偏置)通过优化算法(如梯度下降)进行更新,以最小化一个损失函数,该损失函数量化了预测标签和实际标签之间的差异。
Style2Paints 模型基于一个 CNN 框架,并使用 Danbooru 数据库进行训练,模型包含两个部分:草图和细化过程。根据两阶段草图着色论文,“第一个草图阶段会大胆地将颜色涂抹到画布上,创建一个颜色草图,目的是丰富颜色的多样性 (…) 第二个细化阶段纠正颜色错误,细化细节并打磨模糊的纹理,以达到最终的输出效果。”该神经网络已被训练来处理缺乏一些重要信息(如阴影或纹理)的彩色草图。
它使用生成对抗网络(GANs),这是一种用于生成建模的 CNN 类型。这种神经网络由两个子模型组成:生成器和判别器。生成器执行无监督任务,总结训练数据集(通常是图像)的分布,并生成合成副本供判别器分析。判别器接收这些副本,并将其与一些训练数据集的样本结合起来,执行有监督任务,区分真实样本(地面真实样本)和假样本(由生成器生成的)。当判别器无法区分生成图像和地面真实图像时,模型被认为已经训练完成。生成器此时被保留用于生成该问题领域的新样本。
训练过程可以通过以下图示来查看:

图 9.7 – 训练过程的步骤
这可以看作是两个子模型相互竞争并不断提高生成和辨别能力。这就是为什么“对抗性”这个词出现在它的名称中的原因。该结构的概述可以在进一步阅读部分找到。
训练 GAN 需要大量数据集和大量 GPU。如果你有兴趣训练自己的 GAN,圣路易斯华盛顿大学的视频已经包含在进一步阅读部分。
关于训练数据集的说明
如果使用的模型已经使用我们尝试重现的图像风格进行训练,通常会得到更好的结果。例如,如果我们想要用摄影风格进行绘画,我们可能会尽量避免使用经过动漫风格训练的模型。
正如预期的那样,Style2Paints 是使用 Danbooru 数据集训练的,Danbooru 是一个经过标注的动漫数据集,随着时间的推移不断发展和扩展。Style2Paints 是在 2018 年版本上进行训练的,但在撰写时,已有 2021 年版本。该数据集包含带有元数据和标签的图像。动漫艺术有一些共同特征,例如大而富有表现力的眼睛、鲜艳的色彩、夸张的表情,以及变化丰富的色彩调色板,用以反映图像中的氛围。
以下是一些常用的图像数据集:
-
ImageNet:这是一个图像集合,遵循 WordNet 层级结构。WordNet 集合中的每个相关概念都是一个“同义词集”,与其他同义词集形成关系,建立起从一般到抽象和具体的概念层级。ImageNet 项目试图为每个同义词集提供 1,000 张图像。该数据集对于目标分类任务非常有用。欲了解更多信息,请访问
www.image-net.org/。 -
常见的上下文对象(COCO):这是一个大型数据集,已被注释用于目标检测任务。它包含超过 33,000 张图像,按目录组织,注释以 JSON 格式存储,包含对象和边界框坐标。欲了解更多信息,请访问
cocodataset.org/#home。 -
MPII 人体姿势数据库:该数据集已为人体姿势估计任务准备。它包含大约 25,000 张图像,反映了超过 410 种日常人类活动。欲了解更多信息,请访问
human-pose.mpi-inf.mpg.de/。 -
电影中标记的帧:该数据集包含从流行好莱坞电影中提取的图像。这些图像经过多个处理过程(从选择到清理),然后进行了最终的人工审查和身体关节的标注。欲了解更多信息,请访问
bensapp.github.io/flic-dataset.xhtml。 -
Caltech-UCSD Birds-200-2011:该数据集包含约 12,000 张来自 200 个鸟类类别的图像,并分为测试集和训练集。每张图像都有详细的注释,包括一个子类别标签、15 个部位位置、312 个二进制属性和一个边界框。该数据集可在 TensorFlow 上获取。欲了解更多信息,请访问
www.vision.caltech.edu/datasets/cub_200_2011/。 -
Laion-5b:这是 Stable Diffusion(我们稍后将回顾的内容)训练所使用的数据集。它包含 58.5 亿对通过 CLIP 筛选的图像-文本对,这些数据通过德国实体 LAION 进行的互联网大规模抓取收集而来。欲了解更多信息,请访问
laion.ai/blog/laion-5b/。
在这一部分,我们学习了如何使用一个工具,它可以帮助进行着色工作流程,无论是自动还是手动。接下来的部分,我们将深入探讨通过 AI 将一种图像的风格迁移到另一张图像,从而对图像进行广泛的着色影响。
风格创作——风格迁移
我们可以通过风格迁移来帮助艺术团队,这是一种将两张图像结合起来的过程:
-
风格图像或根图像,我们将从中学习风格
-
目标图像,我们将使用新的风格来转换它
结果图像将保留目标图像的核心元素,但看起来像是按照风格图像的风格绘制或印刷的。
风格迁移有多种方法,包括利用 GAN(上一部分中描述)、使用 视觉几何组(VGG),以及使用稳定扩散(我们将在下一部分讨论)。
在 style_transfer.ipynb 中,我们将使用 VGG19,这是一个具有 19 层的特殊 CNN 类型,已使用来自 ImageNet 数据库的超过百万张图像进行训练,以提取毕加索画作的风格并将其迁移到一张照片上。毕加索属于立体主义运动,在这一运动中,艺术家们运用了多种视角,使用几何形状,并且将画面平面进行了简化。关于这一艺术运动的定义特征,可以在 进一步 阅读 部分找到一篇有趣的文章。
让我们逐步了解我们必须遵循的步骤。
准备工作
首先,我们必须获得根图像和目标图像的张量表示。preprocess_image() 函数通过使用 Keras 库和以下代码片段来完成这项工作:
def preprocess_image(image_path):
img = keras.preprocessing.image.load_img(
image_path, target_size=(img_nrows, img_ncols)
)
img = keras.preprocessing.image.img_to_array(img)
img = np.expand_dims(img, axis=0)
img = vgg19.preprocess_input(img)
return tf.convert_to_tensor(img)
模型构建
我们通过设置 ImageNet 数据集的权重来构建 VGG19 模型,这意味着模型将使用已经在 ImageNet 数据集上预训练的权重进行初始化。include_top 参数设置为 False,这意味着模型中不包括负责分类的顶部层。原因是我们希望将 VGG19 模型用作特征提取器,而非用于分类目的:
model = vgg19.VGG19(weights="imagenet", include_top=False)
代码还提取了由模型每一层生成的信息,以便在后续的损失函数中使用,这些损失函数我们将在此处进行描述。
我们定义了三个损失函数:
-
总变差损失,它通过衡量结果图像中像素之间的空间连续性,来确保最终图像的一致性。
-
content_layer_name。 -
style_layer_names。
风格损失使用的是一个 Gram 矩阵(本质上是一个张量与其转置相乘),并在 gram_matrix() 函数中计算。卷积层的 Gram 矩阵的理论基础是将它们之间学到的风格特征结合起来。例如,毕加索的立体主义是一种颜色、形状和纹理的结合。通过这些特征的合成(即 Gram 矩阵)来衡量它们之间的相关性,将能代表毕加索的风格。
compute_loss函数总结了之前定义的各种损失的组合,而compute_loss_and_grads执行计算。
训练与推理
训练过程将减少风格损失和内容损失,这两者构成了总变差损失。训练过程使用随机梯度下降(SGD)作为优化器,以迭代方式减少损失。
提议的脚本在每 100 次迭代后保存图像,以便我们监控图像变化。文档建议在训练过程结束时展示最终图像,我们将训练步数设置为 4000 步。
通过使用笔记本中名为deprocess_image()的util函数,该函数将张量重建为.png文件,以便可以保存和显示,我们可以看到将毕加索画作风格转移到照片上的效果:

图 9.8 – 毕加索画风中的瀑布
在第一部分,我们学习了如何通过应用颜色自动修改图像;在这一部分,我们回顾了如何通过将基础图像与特定风格相结合来创建图像。在这两种情况下,我们都提供了想要修改的图像。在接下来的部分,我们将学习如何通过文本输入或提示生成图像。
使用提示生成 – 文本到图像
在本节中,我们将介绍一些能够基于提示生成图像的服务。提示是一组自然语言指令,输入模型后可以生成图像。任何可以用语言描述的内容都可以转化为图像。提示越详细,输出的作品就越独特。指令可以包括一些关键词,这些关键词将增强生成作品的原创性,例如生成图像的风格、长宽比、预期图像的分辨率等。
我们将介绍的所有服务都使用某种形式的扩散模型,结合其他模型以提高图像生成过程的效率,去除干扰性结果(例如,针对次要 18),等等。扩散模型是生成模型,旨在复制训练数据。在训练过程中,模型将噪声添加到训练数据集中,并学习如何反向操作以恢复原始图像。通过从训练噪声中恢复,模型学习图像的基本特征以及如何生成新数据。
让我们简要分析它们逐一。
DALL.E 2
OpenAI,开发了 ChatGPT 的同一个研究团队,开发了 DALL-E 2,它是一个从文本描述生成图像的工具。根据他们的文档,“DALL·E 是一个变换器语言模型。它接收文本和图像作为一个包含最多 1280 个令牌的数据流,并使用最大似然训练来生成所有令牌,依次生成。”该模型是一个 120 亿参数的自回归变换器,经过 2.5 亿对图像-文本对的训练,这些对从互联网上收集而来。
DALL-E 2 不仅根据预定义的提示生成图像,还允许用户修改图像的部分内容或为较小的图像区域添加背景信息。
同样的团队还设计了对比语言图像预训练(CLIP),它使我们能够将文本与图像进行映射,并返回最适合输入图像的标题。更多信息可以在openai.com/research/clip找到。这使得图像标签和分类的速度提升到了一个新水平。
Stable Diffusion
Stable Diffusion 模型是开源的,包含代码和检查点。为了让 Stable Diffusion 模型能够在低 GPU 上训练,它们并不是直接在图像上训练,而是在数据集的潜在空间中进行训练。模型从数据集的潜在结构中学习,而不是处理每一张图像。使用潜在空间进行训练使得我们能够向模型提供文本和图像,这些内容将在模型用来重新生成图像的同一空间中进行处理。
上一节提到的 CLIP 模型帮助训练了最新版本的 Stable Diffusion V2。仓库链接是github.com/Stability-AI/stablediffusion。
Midjourney
Midjourney 使用的基础模型没有公开,但它们可能是多种扩散模型的组合,正如 DALL-E 和 Stable Diffusion 的解释所示。Midjourney 目前只能通过其官方 Discord 服务器上的 Discord 机器人访问,或者邀请机器人到第三方服务器。它没有 API。
这项服务迅速变得非常流行。
Leonardo.Ai
他们页面的链接是app.leonardo.ai/。这个工具提供现成的模型,能够生成专门针对一些最常见主题训练的图像,例如角色扮演游戏(RPGs)或现实照片。它还提供工具来微调模型,使其能够适应我们的训练数据集,并且提供一个慷慨的免费层。最后,它对开发者友好,提供易于互动的 API。每个模型都有一个基于 Stable Diffusion 发布版的“基础模型”描述。
要开始使用,请在他们的应用程序上注册并完成入门调查。与基本服务互动无需付费,但获取 API 密钥时必须付费:

图 9.9 – 第一次登录 Leonardo.Ai
在主页视图中,列出了我们可以互动的模型,具体取决于我们想生成的图像类型。如前所述,每个模型都是针对特定目的进行优化的。例如,有一个模型专门用于复古风格摄影或角色扮演游戏角色肖像。
我们还可以看到两个标签,分别是社区动态和个人动态,它们显示由社区和我们自己生成的图像。
如果我们转到 AI 生成工具,我们将看到视图左侧有多个选项可供选择,其中包括以下内容:
-
图像数量:这使我们可以选择每次运行时生成的图像数量。
-
提示魔力:根据他们的描述,“我们的实验性渲染管道可能具有更好的提示遵循性”。启用此功能后,生成的图像更加艺术化。
-
提示魔力强度:此选项决定了之前渲染的详细程度的权重。
-
公开图像:此选项允许我们选择是否将这些图像与公共动态分享。
-
图像尺寸:此选项让我们可以设置图像的大小。
-
指导尺度:此选项决定了提示在最终图像中的权重。建议将其保持在 7 或 8。
我们还可以上传一张图片作为提示使用。
关于好提示的说明
词汇:避免使用“very”或“super”来表示强调。相反,可以选择表达相同意思的词汇。例如,将“very tired”替换为“exhausted”。
拼写错误:避免发送拼写错误的单词、缩写、收缩词或俚语,因为模型可能难以将它们与其训练时所使用的数据集对齐。
具体性:尽量减少词汇选择中的模糊性和不必要的文本。为了提高效果,可以使用“cheeseless pizza”而不是“pizza with no cheese”。利用负面提示来排除图像中的特定物体或特征。
需要考虑的关键词:包括图像背景、风格词(如动漫、写实、纸艺、立体主义、炭笔画、民间艺术、涂鸦)、光线(柔光、环境光、霓虹灯、工作室灯光)或一天中的时间(早晨、黄金时段、午夜)的提示。
此外,该应用还帮助我们生成提示。在我们刚刚描述的 AI 工具中,我们可以看到提示生成标签,它帮助我们生成提示,以便使用 AI 获取所需的图像。
亲自体验 Leonardo.Ai
让我们通过 API 做一个练习。文档可以在docs.leonardo.ai/reference/getuserself找到。它是一个易于使用的 API,可以通过我们熟悉的request库进行访问。
API 可以帮助我们从提示到文件夹的整个管道建设,我们可以将其提交给艺术团队进行审核。Leonardo_AI.ipynb文件包含我们将要探索的工作流。
尽管 API 仍在开发中,并且并非所有功能和模型都可以通过程序调用,但前面描述的大部分选项都可以作为参数添加到负载中。
让我们查看以下代码片段:
payload = {
"prompt": prompt,
"modelId":"6bef9f1b-29cb-40c7-b9df-32b51c1f67d3",
"width": 512,
"height": 512,
"sd_version": "v2",
"presetStyle": "LEONARDO",
"public": False,
"promptMagic": True
}
要与 API 互动,我们需要登录并获得一组 API 密钥,这些密钥将作为授权信息传递在请求头中。
重要的是要从网站上阅读参数,因为文档并不完整。例如,有些模型是以特定的图像尺寸进行训练的,因此最好将这些首选尺寸输入到参数负载中。此外,并非所有模型都可以通过 API 调用,也无法访问提示生成器。
尽管有这些限制,这仍然是一个很棒的工具,可以帮助我们快速生成高质量的图像。
铸造一个 NFT 收藏
本节分析所有工具的目的是为了创建或修改我们可以出售的图像,或者艺术团队可以出售的图像。一旦我们生成了图像,我们希望以 Web3 的方式“拥有”它们,正如在 第四章 中解释的那样。为了实现这一目标,我们将在市场平台上创建一个收藏。
铸造是指在区块链上创建一个物品的数字踪迹。正如我们在描述 ERC 721 时看到的,它意味着这个踪迹将指向一个包含存储图像的 URL。所有存储在区块链上的内容都需要支付油费。
懒铸造的概念相对较新。懒铸造意味着授权平台在 NFT 售出时铸造 NFT,而不是提前铸造。这一点很重要,因为铸造需要消耗油费,在高峰期油费可能很高。此外,懒铸造有助于减少创建一个可能不会高价售出的收藏品的风险。截至目前,主要的市场平台,如 OpenSea 和 Rarible,提供这一服务。
该过程包括以下步骤:
-
创作者通过特定的智能合约 懒铸造 NFT。智能合约会代表我们铸造并出售 NFT。我们提供授权。
-
买家在购买我们的 NFT 时支付包括铸造费用和 NFT 本身的费用。
这种方法将铸造过程推迟到 NFT 售出之前,这是对创作者的激励,鼓励他们继续创作和展示艺术作品,而无需支付油费。
让我们在 OpenSea 上创建一个收藏:
-
访问
opensea.io/。要与平台互动,你需要一个钱包。 -
连接你的钱包并进入个人资料选项:

图 9.10 – 连接到你的钱包
- 点击 我的收藏:

图 9.11 – 我的收藏标签页
- 点击蓝色的 创建一个 收藏 按钮:

图 9.12 – 我的集合页面
- 系统会提供两个选项:传统选项(部署您自己的合约)和懒铸造选项(使用 OpenSea 合约)。点击第二个选项:

图 9.13 – 选择懒铸造选项
-
会打开一个页面,您可以在其中填写集合的详细信息。我们将找到以下几个细节:
-
集合的名称。
-
描述
-
可接受的货币。
-
集合页面的图片。
-
作者收益。如我们在第四章中提到的,每次 NFT 被出售时,可以设定创作者将保留的百分比。
-
填写完所有必需的详细信息后,点击保存。现在我们有了一个集合,接下来需要将艺术品添加到其中:
- 返回您的个人资料并点击创建:

图 9.14 – 创建 NFT
-
您可能需要额外的授权才能访问此面板。如果是这样,您将被带到创建新项目页面:
opensea.io/asset/create。 -
上传您想要铸造的图片、视频或音频。在这个示例中,我们将铸造一张使用
Leonardo_AI.ipynb笔记本生成的图片:

图 9.15 – 新项目的详细信息
-
开始填写必填字段:
-
名称
-
描述
-
将其连接到之前在步骤 4中创建的集合
-
确定可以铸造的相同性质的物品数量
-
该物品将所在的网络
点击创建;您将看到以下输出:
-

图 9.16 – 签署创建后的结果信息
- 启用销售。为此,请访问该物品的页面并点击出售按钮:

图 9.17 – 销售详情
新选项将会出现供您选择。可以选择固定价格或限定时间的拍卖。如果我们想以固定价格出售,可以按照以下步骤操作。
- 点击固定价格:

图 9.18 – 固定价格选项
-
设置一个价格,使用我们在创建集合时决定的任何可接受的货币或代币。
-
在此下方,我们将看到收益的总结以及 OpenSea 收取的费用(在写作时,这个费用为 2.5%)。
-
如果我们同意,可以点击完成列表。为了批准这个列表,OpenSea 需要我们的签名。
-
一旦签署完成,我们将收到新的通知,告知我们该物品已列出。现在,它已经在市场上,可以购买了!

图 9.19 – 销售列表已启用
本节中生成的所有插图均可在《神秘图书馆收藏》查看:opensea.io/collection/mysterious-library。
总结
在本章中,我们探讨了三种不同的使用 AI 工具进行艺术项目的方式。我们研究了使用 GAN 模型为草图上色,探索了 VGG19 模型进行风格转移,并发现了基于提示生成艺术的 Stable Diffusion 模型的最先进应用。
此外,我们还了解了整个工作流程,从完成的艺术作品到将最终图像列出在市场上。通过结合 AI 和区块链技术的力量,我们现在有了探索和变现艺术作品的新机会,以激动人心和创新的方式。
值得注意的是,关于使用 AI 生成的图像的所有权问题已经引发了讨论。这源于这些模型可能在没有艺术家同意的情况下使用了受版权保护的艺术作品进行训练的可能性。回应者认为,模型输出的变革性特征,加上合理使用的论点,可能会驳回此类指控。这个持续的问题尚未被法律当局明确解决,并且可能在不同国家之间存在差异。
在探索了 NFT 领域之后,我们将把注意力转向一个关键方面,这一方面是确保这一创新领域完整性的基础——欺诈检测。在接下来的章节中,我们将分析另一个应用案例,在这个案例中,机器学习可以帮助我们发现异常并提高交易安全性。
进一步阅读
想要了解更多本章所涵盖的主题,请参考以下资源:
-
Crypto Grims:
twitter.com/cryptogrims -
Artsy Monke 收藏品:
opensea.io/assets/ethereum/0xa4bcd3b7f141ba1f08f36033fdfce691565561bc。 -
Mishra, M. (2020, September 2). 卷积神经网络解析. Medium. 可在
towardsdatascience.com/convolutional-neural-networks-explained-9cc5188c4939查看。 -
Fortis, S. (n.d.). Google AI 将所有 10,000 个 BAYC NFT 转化为机器生成艺术. Cointelegraph. 可在
cointelegraph.com/news/google-ai-turns-all-10-000-bayc-nfts-into-machine-made-art查看。 -
Lllyasviel (n.d.). style2paints.github.io. 可在
style2paints.github.io/查看。 -
Lllyasviel/style2paints. (n.d.). GitHub. 可在
github.com/lllyasviel/style2paints查看。 -
Tang, J.(2020 年 10 月 20 日)。尝试理解一个全明星自动上色项目——Style2Paints(第一部分)。Medium。可在
medium.com/ai-innovation/attempt-to-understand-an-all-star-auto-color-project-style2paints-part-1-84d2e3d96da查看。 -
Lvmin Zhang, Chengze Li, Tien-Tsin Wong, Yi Ji 和 Chunping Liu。(无日期)。CUHK 计算机科学与工程。可在
www.cse.cuhk.edu.hk/~ttwong/papers/colorize/colorize.pdf查看。 -
Nerdy Rodent。(2020 年 11 月 19 日)。Style2Paints——使用 AI 轻松为任何线条艺术上色 [视频]。YouTube。可在
www.youtube.com/watch?v=cvN9oQfC3w0查看。 -
GAN 结构概述。(无日期)。Google 开发者平台。可在
developers.google.com/machine-learning/gan/gan_structure查看。 -
Prof. Jeff Heaton – 圣路易斯华盛顿大学。(2022 年 1 月 19 日)。图像和数据生成的 GAN 入门(7.1) [视频]。YouTube。可在
www.youtube.com/watch?v=hZw-AjbdN5k查看。 -
Prof. Jeff Heaton – 圣路易斯华盛顿大学。(2021 年 2 月 17 日)。从您自己的图像训练 GAN:StyleGAN2 ADA [视频]。YouTube。可在
www.youtube.com/watch?v=kbDd5lW6rkM查看。 -
Prof. Jeff Heaton – 圣路易斯华盛顿大学。(2021 年 5 月 12 日)。在 Colab Free 和 Colab Pro 技巧下训练 NVIDIA StyleGAN2 ADA [视频]。YouTube。可在
www.youtube.com/watch?v=L3JLzoe-dJU查看。 -
T81_558_deep_learning/t81_558_class_07_1_gan_intro.ipynb at master · jeffheaton/t81_558_deep_learning。(无日期)。GitHub。可在
github.com/jeffheaton/t81_558_deep_learning/blob/master/t81_558_class_07_1_gan_intro.ipynb查看。 -
T81_558_deep_learning/t81_558_class_07_2_train_gan.ipynb at master · jeffheaton/t81_558_deep_learning。(无日期)。GitHub。可在
github.com/jeffheaton/t81_558_deep_learning/blob/master/t81_558_class_07_2_train_gan.ipynb查看。 -
Jason Brownlee 博士。(2019 年 7 月 19 日)。机器学习精通。机器学习精通。可在
machinelearningmastery.com/what-are-generative-adversarial-networks-gans/查看。 -
立体主义的 4 个特征及其重要性。(无日期)。Artlex – 艺术词典和百科全书。可在
www.artlex.com/art-movements/cubism/characteristics/获取。 -
神经风格 迁移:
keras.io/examples/generative/neural_style_transfer/。 -
DALL·E:从文本创建图像。(无日期)。OpenAI。可在
openai.com/research/dall-e获取。 -
零-shot 文本到图像生成。(无日期)。arXiv.org。可在
arxiv.org/abs/2102.12092获取。 -
Aleksa Gordić - The AI Epiphany. (2022 年 9 月 1 日). 稳定扩散:使用潜在扩散模型进行高分辨率图像合成 | ML 编程系列 [视频]。YouTube。可在
www.youtube.com/watch?v=f6PtJKdey8E获取。 -
Stability-AI/stablediffusion。(无日期)。GitHub。可在
github.com/Stability-AI/stablediffusion获取。 -
稳定扩散是如何工作的?潜在扩散模型解析。(2022 年 12 月 3 日)。Louis Bouchard。可在
www.louisbouchard.ai/latent-diffusion-models/获取。 -
Arya, G. (2023 年 1 月 14 日). 潜在扩散模型的力量:革命性的图像创作。Analytics Vidhya。可在
www.analyticsvidhya.com/blog/2023/01/power-of-latent-diffusion-models-revolutionizing-image-creation/获取。 -
API 文档。(无日期)。Leonardo.Ai。可在
docs.leonardo.ai/reference/getuserself获取。 -
Ashley, K. (2021). 用人工智能创作艺术:用 AI、区块链和 NFT 创作并销售你的艺术。
第十章:安全与欺诈检测概述
“所有战争都基于欺骗。” —— 孙子
欺诈的历史与人类历史一样悠久。在加密世界中,欺诈并不令人惊讶,随着加密货币的主流化,意识到不同形式的欺诈变得愈加重要,以便能够识别它。
欺诈是企业、政府以及区块链行业尤其面临的重大问题。根据 2022 年普华永道全球欺诈年度报告,46%的受访组织表示在过去 24 个月内遭遇过某种形式的欺诈或经济犯罪。
政府出于税务目的以及打击洗钱和恐怖主义融资的需要,已经意识到这个问题。相关机构有责任执行法律,打击此类非法活动,即使涉及加密货币。对于所有涉及金融活动或货币服务业务的主体,都需要进行尽职调查,这一概念已扩展至包括集中式交易所。因此,主要的集中式交易所(CEXs)仅在验证身份证背后的人身份后才会为新用户开设账户。遵守一定的质量标准至关重要,未能遵守可能导致制裁。
加密行业也有兴趣通过合规的智能合约和无缝交易体验来巩固信任。智能合约漏洞、欺诈计划以及将加密货币作为支付手段来进行黑客攻击的行为并未助力这一目标。数据科学在解决这个问题方面已经有一段时间了,挑战在于如何将数据科学实践应用于区块链数据集,因为它具有较大的差异性且是伪匿名的。一些有趣的公司,如 Chainalysis、Elliptic 和 CipherTrace,处于区块链法医数据科学的前沿,帮助相关部门进行调查并支持用户的普遍信任。
在本章中,我们将研究地址的交易行为,训练一个机器学习模型,以确定我们是否遇到骗子。
特别地,我们将覆盖以下主题:
-
以太坊上的非法活动表现
-
以太坊交易数据的探索性数据分析
-
准备工作、模型训练和评估以标记欺诈交易
技术要求
你可以在本书的 GitHub 仓库中找到本章的所有数据和代码文件,网址为github.com/PacktPublishing/Data-Science-for-Web3/tree/main/Chapter10。我们建议你浏览Chapter10文件夹中的代码文件,以便跟随学习。
在本章中,我们将使用以太坊实用程序库(eth-utils),该库包含用于与以太坊合作的 Python 开发人员常用的实用函数。根据我们的环境,我们可能需要导入其他低级别库,这些库由eth-utils使用。
如果您尚未安装eth-utils,可以使用以下代码片段进行安装:
pip install eth-utils
eth-utils的文档可在eth-utils.readthedocs.io/en/stable/找到。如果由于缺少支持库而安装失败,您可以在Chapter10/EDA.ipynb中找到需要预先安装的完整库列表。
以太坊非法活动入门
欺诈和骗局之间存在技术上的差异。骗局是一种行为,我们在不知情的情况下支付虚假物品、转移资金或向犯罪分子提供我们的私钥。相反,欺诈指的是我们的地址上出现的任何未经授权的可疑活动。在本书中,我们将两个术语互换使用。
以太坊安全博客为刚入行加密行业的人提供了三条关键信息:
-
始终 持怀疑态度
-
没有人会免费或 打折 ETH
-
没有人需要访问您的私钥或 个人信息
截至今日,一些最常见的欺诈行为包括以下几种:
-
赠送骗局: 这些骗局基本上通过犯罪分子承诺,如果我们向某个地址发送X数量的加密货币,它将被以加倍的金额返回给我们。这些方案通常是心理上的,只为受害者提供有限的时间参与这个“机会”,产生错失良机 (FOMO) 的效果。此方案通常利用高调的 X(前身为 Twitter)账户、名人视频等。
-
IT 支持骗局: 这些骗子冒充区块链服务(如钱包、交易所、市场等)的 IT 支持或管理员人员。他们可能会向我们索要一些信息或验证我们的身份,并且通常会试图获取提取我们资金所需的最少信息。这类骗子主要出现在 Discord 讨论频道或 Telegram 上。通常可以在真实人名旁边看到短语“永远不要主动私信”。骗子会主动发起对话,试图建立联系和信任。值得记住的是,Web3 是一个去中心化的领域,因此不太可能看到支持团队在互联网上回答我们的问题。如果我们与一个有支持团队的集中式平台进行交互,团队将始终通过官方渠道联系我们。
-
网络钓鱼诈骗:这是一种社交工程攻击,通过电子邮件伪装来诱使受害者提供必要的信息以实施诈骗。邮件通常包含指向假网站的链接或下载恶意软件。正如我们在第三章中所看到的,在详细说明如何访问链外数据时,我们应该尝试通过受信任的链接访问网站——例如,通过 CoinMarketCap 或 CoinGecko。检测网络钓鱼有很多方法,但事实是它们随着时间的推移变得越来越有创意。
-
经纪人诈骗:这些是拥有大量社交媒体粉丝的交易经纪人,声称能够创造出色的利润。经纪人账户背后有一个真实的人物,他会与受害者互动,直到后者将资金转给经纪人“管理”。一旦资金转出,这些资金就会丢失。
每种诈骗都通过实际案例在这个博客中进一步解释:ethereum.org/en/security/。
无论欺诈方案如何,资金都会通过交易转移并保存在账户中。在接下来的部分,我们将分析账户行为,尝试确定哪些账户可以信任,哪些账户应该被标记为诈骗。
预处理
我们将使用在论文《以太坊区块链上非法账户的检测》中使用的平衡数据集。你可以在进一步阅读部分找到该论文的链接。这个数据集是一个平衡数据集,包含 48 列或特征,结合了合法和非法账户。该数据集通过使用 CryptoScamDB 数据库和 Etherscan 创建,后者是我们已经熟悉的工具。cryptoscamdb.org管理一个开源数据集,跟踪恶意网址及其关联地址。
列及其描述如下:
| 特征 | 描述 |
|---|---|
Avg_min_between_sent_tnx |
账户发送交易之间的平均时间(分钟) |
Avg_min_between_received_tnx |
账户接收交易之间的平均时间(分钟) |
Time_Diff_between_first_and_last(Mins) |
第一次和最后一次交易之间的时间差(分钟) |
Sent_tnx |
发送的普通交易总数 |
Received_tnx |
接收到的普通交易总数 |
Number_of_Created_Contracts |
创建的合约交易总数 |
Unique_Received_From_Addresses |
账户收到交易的唯一地址总数 |
Unique_Sent_To_Addresses |
账户发送交易的唯一地址总数 |
Min_Value_Received |
曾经接收到的最小以太币金额 |
Max_Value_Received |
曾经接收到的最大以太币金额 |
Avg_Value_Received |
曾经接收到的平均以太币金额 |
Min_Val_Sent |
发送过的最小 Ether 值 |
Max_Val_Sent |
发送过的最大 Ether 值 |
Avg_Val_Sent |
发送的 Ether 平均值 |
Min_Value_Sent_To_Contract |
发送到合约的最小 Ether 值 |
Max_Value_Sent_To_Contract |
发送到合约的最大 Ether 值 |
Avg_Value_Sent_To_Contract |
发送到合约的 Ether 平均值 |
Total_Transactions(Including_Tnx_to_Create_Contract) |
总交易数量(包括创建合约的交易) |
Total_Ether_Sent |
发送的总 Ether 数量(针对某个账户地址) |
Total_Ether_Received |
接收的总 Ether 数量(针对某个账户地址) |
Total_Ether_Sent_Contracts |
发送到合约地址的总 Ether 数量 |
Total_Ether_Balance |
执行交易后的总 Ether 余额 |
Total_ERC20_Tnxs |
ERC20 代币转账交易的总数 |
ERC20_Total_Ether_Received |
接收到的 ERC20 代币交易总量(以 Ether 计算) |
ERC20_Total_Ether_Sent |
总共发送的 ERC20 代币交易数量(以 Ether 计算) |
ERC20_Total_Ether_Sent_Contract |
发送到其他合约的 ERC20 代币总量(以 Ether 计算) |
ERC20_Uniq_Sent_Addr |
发送到唯一账户地址的 ERC20 代币交易数量 |
ERC20_Uniq_Rec_Addr |
从唯一地址接收的 ERC20 代币交易数量 |
ERC20_Uniq_Rec_Contract_Addr |
从唯一合约地址接收的 ERC20 代币交易数量 |
ERC20_Avg_Time_Between_Sent_Tnx |
ERC20 代币发送交易之间的平均时间(以分钟计算) |
ERC20_Avg_Time_Between_Rec_Tnx |
ERC20 代币接收交易之间的平均时间(以分钟计算) |
ERC20_Avg_Time_Between_Contract_Tnx |
ERC20 代币发送交易之间的平均时间(针对合约交易) |
ERC20_Min_Val_Rec |
从 ERC20 代币交易中接收到的最小 Ether 值 |
ERC20_Max_Val_Rec |
从 ERC20 代币交易中接收到的最大 Ether 值 |
ERC20_Avg_Val_Rec |
从 ERC20 代币交易中接收到的平均 Ether 值 |
ERC20_Min_Val_Sent |
从 ERC20 代币交易中发送的最小 Ether 值 |
ERC20_Max_Val_Sent |
从 ERC20 代币交易中发送的最大 Ether 值 |
ERC20_Avg_Val_Sent |
通过 ERC20 代币交易发送的平均 Ether 值 |
ERC20_Uniq_Sent_Token_Name |
发送的唯一 ERC20 代币数量 |
ERC20_Uniq_Rec_Token_Name |
接收的唯一 ERC20 代币的数量 |
ERC20_Most_Sent_Token_Type |
通过 ERC20 交易发送最多的代币类型 |
ERC20_Most_Rec_Token_Type |
通过 ERC20 交易接收最多的代币类型 |
表 10.1 – 每列数据集的解释(来源 – 《检测以太坊区块链上的非法账户》论文第 10 页)
在Chapter10/EDA.ipynb中,我们分析了数据集并得出了以下结论:
-
数据中有 4,681 个账户和 48 个特征。在这些地址中,有五个重复地址和五个无效地址。
为了判断一个地址是否有效或无效,我们使用了 EIP-55 的一部分代码,并结合一个名为
address_validation()的自定义公式。在
address_validation()函数中,我们添加了一个额外的条件来计算每个地址的字符数,丢弃那些不是 42 个字符的地址。如果满足两个条件,则认为地址有效,并返回带有校验和的版本。否则,返回
not an ethereum address标志:def checksum_encode(addr): hex_addr = addr.hex() checksummed_buffer = "" hashed_address = eth_utils.keccak(text=hex_addr).hex() for nibble_index, character in enumerate(hex_addr): if character in "0123456789": checksummed_buffer += character elif character in "abcdef": hashed_address_nibble = int(hashed_address[nibble_index], 16) if hashed_address_nibble > 7: checksummed_buffer += character.upper() else: checksummed_buffer += character else: raise eth_utils.ValidationError( f"Unrecognized hex character {character!r} at position {nibble_index}" ) return "0x" + checksummed_buffer def test(addr_str): addr_bytes = eth_utils.to_bytes(hexstr=addr_str) checksum_encoded = checksum_encode(addr_bytes) try: assert checksum_encoded == addr_str, f"{checksum_encoded} != expected {addr_str}" except AssertionError: return checksum_encoded def address_validation(addr_str): if len(addr_str) == 42: result = test(addr_str) else: result = "not an ethereum address" return result -
第 25 到 49 列有一些缺失值,缺失值的百分比为 17.7%。我们识别数据框中的任何缺失值,并计算每列的缺失值百分比。
我们使用以下代码片段:
Chapter10/Rebuilding.ipynb. -
欺诈交易和缺失值位于数据集的顶部。看起来最具欺诈性的账户似乎有缺失值。请参阅
Chapter10/EDA.ipynb中的热力图。 -
有 12 列数据方差较小(且只有一个值,即零)。方差较小的列可能对我们的训练没有帮助。这些列如下:
['min_value_sent_to_contract', 'max_val_sent_to_contract', 'avg_value_sent_to_contract', 'total_ether_sent_contracts', 'ERC20_avg_time_between_sent_tnx', 'ERC20_avg_time_between_rec_tnx', 'ERC20_avg_time_between_rec_2_tnx', 'ERC20_avg_time_between_contract_tnx', 'ERC20_min_val_sent_contract', 'ERC20_max_val_sent_contract', 'ERC20_avg_val_sent_contract']我们使用以下代码片段来识别这些列:
variance_df= df.nunique() -
清理重复项和无效项后,有 2,497 个非欺诈账户和 2,179 个欺诈账户。
-
我们运行了相关矩阵,并发现有五列数据高度相关。这些列如下:
['ERC20_max_val_rec', 'ERC20_min_val_sent', 'ERC20_max_val_sent', 'ERC20_avg_val_sent', 'ERC20_uniq_rec_token_name']删除具有相似信息的列非常重要,因为冗余信息不会为我们的训练增加价值,反而可能使我们的算法学习变慢,并且如果我们需要解释模型,可能会使模型的可解释性变得更复杂。多重共线性也会影响某些模型,如线性模型。请参阅
Chapter10/EDA.ipynb中的相关热力图。 -
两列包含分类数据(
ERC20_most_sent_token_type和ERC20_most_rec_token_type)非常稀疏,大多数代币只出现一次或为空。当我们按 ERC 代币进行分组时,没有明显的类别可以用来提供帮助。对这些列进行独热编码可能会导致一个稀疏的训练数据集。此外,每天都有新的代币被铸造,将这些信息加入我们的模型将创造一个很快过时的变量。
基于前面分析得出的结论,我们清理了数据以使其适应我们的需求。采取的步骤包括:
-
我们删除了重复的地址。
-
我们尝试从 Etherscan 填充缺失值。
-
我们删除了低方差的列。
-
我们删除了相关性为 0.95 或更高的列。
-
我们删除了
object类型的列。 -
我们删除了
Address列。 -
我们用中位数填充了 NaN 值。
让我们扩展一下 步骤 2 的预处理工作,涉及从 Etherscan 填充缺失值。现实中的数据集往往不完整,数据分析师或数据科学家的职责就是填补那些部分完成的列。填补的方式有很多种,我们在 第五章中探讨了传统方法,适用于当没有更多数据可用时。
在 Chapter10_Rebuilding 中,我们尝试了另一种方法论,即直接访问数据源,查找缺失的数据。全书中,我们列出了多个数据源,随着这一领域的不断发展,新的链上数据源将逐步可用,帮助我们完善数据集。此外,Web3 的专业化将使我们能够对数据进行推断,因为我们能理解这些数据。当我们需要在数据集里反映的某个数据点是间接的,或者并非直接来源于链上数据时,这一点尤其重要。
在从论文《检测以太坊区块链上的非法账户》中提取的数据集里,有 17% 的行缺失数据。为了补充这部分数据,我们使用了一个我们已经分析了一段时间的数据源——Etherscan。我们利用了他们免费 API 的免费层,能够补充大部分缺失的行。API 文档链接为 docs.etherscan.io/。补充这些列的步骤在 Chapter10_Rebuilding 中进行了说明,我们提取了缺失的数据点并将其添加到数据框中。如果 Etherscan 没有记录,我们可以推断该地址并未进行过该交易。
经过这一过程后,仍然留下了一些空值行,我们用列的中位数进行了填充。通过这最后一步,我们获得了一个完整的数据集,准备好进行训练。
.csv 文件已上传至本书的 GitHub,并可通过 final.csv 访问。
关于优秀预处理的一些说明
在该领域,关于数据构建和预处理的一个典型例子是与论文 Exploiting Blockchain Data to Detect Smart Ponzi Schemes on Ethereum 相关的一个数据集(论文链接在 进一步阅读 部分提供)。该论文的目的是训练一个机器学习算法来分类庞氏骗局的智能合约。为了实现这一目标,研究人员构建了一个包含 200 个庞氏骗局智能合约和 3,580 个非庞氏骗局智能合约的数据集。对于每个合约,他们提取了字节码、交易数据和内部交易。由于内部交易没有存储在链上,研究团队重新运行了一个以太坊客户端来重现这些交易。此外,为了将字节码转换为有意义的特征或类别,团队将其转换为操作码并记录了每种操作码在智能合约中的频率。
训练模型
一旦我们完成了数据清洗和预处理,我们将数据集进行洗牌,然后将其分割为训练集和测试集。接着,我们遍历在二分类任务中表现良好的多个模型,包括 KNeighborsClassifier、DecisionTreeClassifier、AdaBoostClassifier、GradientBoostingClassifier 和 RandomForestClassifier。
然而,仅仅因为一个模型在某个数据集上表现良好,并不意味着它在另一个数据集上也能取得相同效果。这时,调整模型变得非常重要。机器学习模型有一些超参数,需要调整以适应特定数据。定制这些超参数来适应我们的数据集,将提高模型的性能。为了执行这种优化,有一些可用的工具,比如 scikit-learn 中的 GridSearchCV。
GridSearchCV 返回的 best_estimator_ 将包含在其中。如果我们不知道选择哪些参数,可以运行 RandomizedSearchCV,它会定义一个搜索空间并随机测试。两个类的文档可以在 scikit-learn.org/stable/modules/generated/sklearn.model_selection.RandomizedSearchCV.xhtml 和 scikit-learn.org/stable/modules/generated/sklearn.model_selection.GridSearchCV.xhtml 中找到。
GridSearchCV 和 RandomizedSearchCV 都有一个 cv 参数,表示交叉验证。K 个大小相等的区间用于运行 K 次学习实验。然后将结果平均化,以减少模型性能的随机性并提高其稳健性。该类通常包含在其他实现中,例如网格搜索。然而,它也可以独立使用。
有一些变化,例如分层K折叠,它确保每个分割包含每个类别相同比例的观察值,以及重复K折叠,它为每个折叠重复操作,但每次都会打乱每个分区,使其成为一个新的样本。有关这些过程的文档可以在scikit-learn.org/stable/modules/generated/sklearn.model_selection.KFold.xhtml找到。
我们的训练结果显示GradientBoostingClassifier模型表现最好。
评估结果
我们将使用混淆矩阵来展示模型的表现,因为它对于二分类问题非常有用。评估指标的选择将取决于所处理问题的类型。在欺诈检测的情况下,我们希望确保最小化假阴性率,因此我们将使用召回率作为评估指标。有关评估指标的详细解释,参见第五章。
结果在整个项目中的得分是 95.6%,这是一个不错的数字。
一个不平衡的数据集
一个类似的数据集也可以在 Kaggle 上找到,最初我们在第六章中进行了分析。这个数据集是一个不平衡的形式,因为只有 20%的行是欺诈性的。欺诈检测任务通常与不平衡数据有关,因为通常合法交易的数量要多于欺诈交易。某些模型可能会忽视少数类,而少数类有时正是我们感兴趣的需要检测的特定类别。为了处理不平衡数据,传统的方法是通过双向重采样数据集,或者通过过采样少数类或随机删除多数类行来进行欠采样。关于这些过程的更多文档可以在进一步阅读部分找到。
展示结果
数据实践者必须具备强大的沟通能力,以确保他们的发现能够让决策同事、客户以及所有使用这些见解的人容易理解。根据观众的不同,定制结果的展示方式至关重要。
我们可以通过仪表盘来展示分析结果,之前在本书中我们学习了如何使用 Dune analytics、Flipside 或 Covalent 来构建仪表盘。值得注意的是,并非所有的可视化分析平台都能灵活查询链上数据;有些平台仅限于传统数据库。像 Tableau 和 Power BI 这样的平台非常灵活,能够连接 API 并处理来自链上数据的复杂 SQL 查询。
我们还可以利用公司幻灯片演示文稿,并且可以通过非正式的X(前身为 Twitter)讨论串来传达数据分析的结果。无论选择何种媒介,目标都是捕获并保持观众的兴趣。以一个引人注目的问题和引言开始,保持句子简洁,只有在观众表现出兴趣时才深入细节,这些都是关键原则。一份关于创作引人入胜故事的宝贵资源可以在这个 X 讨论串中找到:twitter.com/alexgarcia_atx/status/1381066483330117632.
无论演示平台如何,讲故事的技巧在传递发现时至关重要,要有吸引力的叙事。
摘要
总结来说,我们已经识别并讨论了加密货币领域的一个关键威胁,突出了有效交易监控和识别的必要性。为此,我们在以太坊地址层面开展了机器学习实验,利用 Etherscan 完成了我们的数据集。
我们评估并比较了各种机器学习模型,通过网格搜索超参数调优和交叉验证优化其性能。通过开展这个项目,我们深入探讨了一个法医专业人员活跃的主题,并且这个话题仍然是当前的新闻焦点。
区块链取证是数据科学应用中较为创新的领域之一,因为模型需要扩展并不断发展以适应新的变化,能够发现新类型的欺诈和诈骗。
在下一章中,我们将深入探讨价格预测。
进一步阅读
以下是供您进一步阅读的资源列表:
-
PwC. (2022). PwC 全球经济犯罪与欺诈调查报告 2022.
www.pwc.com/gx/en/forensics/gecsm-2022/PwC-Global-Economic-Crime-and-Fraud-Survey-2022.pdf -
Furneaux, N. (2018). 研究加密货币:理解、提取和分析区块链证据. John Wiley & Sons. 第 268 页。
-
Sfarrugia15/Ethereum_Fraud_Detection. (无日期). GitHub:
github.com/sfarrugia15/Ethereum_Fraud_Detection -
Steven Farrugia, Joshua Ellul, George Azzopardi, 检测以太坊区块链上的非法账户,《专家系统与应用》, 第 150 卷, 2020, 113318, ISSN 0957-4174:
doi.org/10.1016/j.eswa.2020.113318. -
利用区块链数据检测以太坊上的智能合约庞氏骗局。(2019 年 3 月 18 日)。IEEE Xplore:
ieeexplore.ieee.org/stamp/stamp.jsp?arnumber=8668768 -
以太坊安全与防诈骗. (无日期). ethereum.org.
ethereum.org/en/security/ -
Senilov, I.(2021 年 9 月 27 日)。接近事务数据中的异常检测。Medium:
towardsdatascience.com/approaching-anomaly-detection-in-transactional-data-744d132d524e -
Janiobachmann.(2019 年 7 月 3 日)。信用欺诈 || 处理不平衡数据集。Kaggle:您的机器学习与数据科学社区:
www.kaggle.com/code/janiobachmann/credit-fraud-dealing-with-imbalanced-datasets -
Jason Brownlee.(2020 年)。用于不平衡分类的随机过采样与欠采样。机器学习精通:
machinelearningmastery.com/random-oversampling-and-undersampling-for-imbalanced-classification/ -
聚类:一旦我们完成了地址的聚类,就可以构建一个异常检测标识符,使用每个地址所属聚类的参数作为正常性标准。
Price, W.(2021 年 5 月 28 日)。聚类以太坊地址。Medium:
towardsdatascience.com/clustering-ethereum-addresses-18aeca61919d -
Ethereum_clustering/main.ipynb at master · willprice221/ethereum_clustering.(无日期)。GitHub。
github.com/willprice221/ethereum_clustering/blob/master/main.ipynb -
故事讲述资源:Insider.(2019 年 6 月 21 日)。皮克斯制作完美电影的秘密公式 | 电影艺术 [视频]。YouTube:
www.youtube.com/watch?v=Y34eshkxE5o
第十一章:使用时间序列进行价格预测
金融行业中,分析师和研究人员花费大量时间进行投资机会预测,包括资产价格和资产收益。随着大量数据的可用性和处理技术的进步,机器学习(ML)得到了迅猛发展,应用领域也从资产定价扩展到如保险定价、投资组合管理和风险管理等领域。
除了机器学习在金融行业中的广泛应用外,我们现在还可以考虑 Web3 和开放数据的影响。正如我们在本书中所学到的,Web3 中的数据是任何人都可以访问的。特权信息,如银行余额或重要账户变动,任何知道去哪里查看的人都可以看到,正如在第五章中所解释的那样。
金融行业中的许多资产建模和预测问题都涉及时间因素和连续输出的估计。因此,本章的重点将放在时间序列分析上,理解这些输出是什么,以及如何对其建模。我们的目标是利用包括时间因素在内的历史数据点,来预测未来的结果,特别是在预测价格的背景下。
总结一下,本章将涵盖以下主题:
-
时间序列基础
-
数据库选择和特征工程
-
模型建立、训练和结果评估
我们将同时采用传统统计模型和深度学习(DL)方法来捕捉时间序列数据中的模式和动态。
技术要求
在本章中,我们将使用statsmodels库,特别是其时间序列分析包(tsa和statespace)。statsmodels是一个全面的 Python 模块,提供了广泛的类和函数,用于估计各种统计模型,执行统计测试,并进行统计数据探索。对于时间序列分析,它提供了基本的模型,如单变量自回归(AR)模型,向量自回归(VAR)模型,以及单变量自回归滑动平均(ARMA)模型。此外,它还提供了时间序列的描述性统计,如自相关和偏自相关函数(ACF和PACF)。
如果你之前没有使用过statsmodels,可以通过以下命令进行安装:
pip install statsmodels
statsmodels的文档可以在www.statsmodels.org/stable/index.xhtml找到。
我们还将使用pmdarima,它允许我们与pmdarima进行交互,pmdarima作为多个统计和机器学习库(包括statsmodels和scikit-learn)的 Python 封装。如果你之前没有使用过pmdarima,可以通过以下命令安装:
pip install pmdarima
pmdarima 的文档可以在 alkaline-ml.com/pmdarima/ 找到。
我们还将从 yfinance 中提取我们的工作数据集,yfinance 是一个开源的 Python 库,作为 Yahoo Finance API 的接口,提供便捷的金融数据访问,包括股市价格、历史数据、股息信息等。要安装该库,我们需要运行以下命令:
pip install yfinance
yfinance 的文档可以在 pypi.org/project/yfinance/ 找到。
与本章相关的所有数据和代码文件可以在本书的 GitHub 仓库中访问,点击此处查看:
github.com/PacktPublishing/Data-Science-for-Web3/tree/main/Chapter11
我们建议你阅读 Chapter11 文件夹中的代码文件,以便更有效地跟随本章内容。
时间序列基础
时间序列是一组在时间上等间隔观测值的集合。
– 路易斯·阿尔贝里科·吉尔-阿拉尼亚
吉尔-阿拉尼亚教授提到的观测值集合形成了一系列事件,这些事件随着时间的推移按时间顺序展开并发展。
这些观测值代表了随时间变化或波动的各种数据点,例如股价、温度读数、销售数据、网站流量、区块链交易数量等。每个观测值都包含关于过去的宝贵信息,并为未来的趋势提供线索。
一个代表 比特币-美元(BTC-USD)月度收盘价的 10 个月时间序列如下所示:
| 日期 | 收盘价 |
|---|---|
| 2014/10/1 | 338.321014 |
| 2014/11/1 | 378.046997 |
| 2014/12/1 | 320.192993 |
| 2015/1/1 | 217.464005 |
| 2015/2/1 | 254.263 |
| 2015/3/1 | 244.223999 |
| 2015/4/1 | 236.145004 |
| 2015/5/1 | 230.190002 |
| 2015/6/1 | 263.071991 |
| 2015/7/1 | 284.649994 |
表 11.1 – BTC-USD 时间序列片段(来源:Yahoo Finance)
在我们分析时间序列数据时,可以识别模式、趋势和波动。这些模式可能揭示反复出现的主题,遵循清晰的轨迹,或者表现出混乱和不可预测的行为。以下是自 2015 年以来 BTC 价格的时间序列可视化:

图 11.1 – 整个系列的图示
时间序列包括以下组成部分:
趋势:这代表系列的整体方向性运动。趋势可以是确定性的,由潜在的理由驱动,或者是随机的,表现出随机行为。
在下一个例子中,我们观察到自 2017 年以来的持续上升趋势,并且在过去 2 年中加速:

图 11.2:趋势图
季节性:这部分指的是系列中在特定时间框架内重复出现的周期或模式。
在给定的数据集中,我们可以观察到每年中期的下降和年末的增长:

图 11.3 – 季节性成分
白噪声:这表示系列中未被趋势或季节性成分捕获的部分。
在给定的数据集中,该成分最初看起来是平坦的,但在特定点呈现出高峰,如 2017-2018 年末和 2021 年:

图 11.4 – 白噪声表示
为了分解时间序列以分析其成分,我们可以使用以下代码:
decompose = seasonal_decompose(df, model= 'additive').plot(observed=True, seasonal=True, trend=True, resid=True, weights=False)
时间序列分析中还有两个相关概念:自相关和平稳性。
自相关:这指的是序列中连续点之间的依赖关系。它表明给定时间段的值受先前时间段的测量影响。自回归的顺序表示用于预测当前值的先前值数量,称为滞后。例如,如果我们使用前 2 个月的价格来预测比特币的月均价,这对应于滞后为 2 的自相关。
平稳:如果“均值和方差不依赖于时间,并且任何两个观测值之间的协方差仅取决于它们之间的距离,而不取决于具体的时间位置”(Luis Alberiko Gil-Alaña)。对于许多时间序列模型和分析,平稳性是一个重要的假设。我们可以从前述引用中得出结论,具有趋势或季节性的时间序列不能被认为是平稳的。
例如,以下时间序列示例明显呈上升趋势,因此不是平稳的:

图 11.5 – 带有趋势的时间序列
以下时间序列随着时间的推移和趋势具有增加的方差,因此不是平稳的:

图 11.6 – 方差时间序列
以下时间序列没有趋势或季节性,因此可以被视为平稳的:

图 11.7 – 平稳时间序列
现在我们已经了解了理论,让我们介绍数据集。
探索数据集
对于价格预测,我们将利用两个数据集。第一个数据集是从 Yahoo Finance 提取的 BTC 价格时间序列数据,以每日为粒度。
为了提取它,我们使用 Yfinance 库和以下代码:
data=yf.Ticker('BTC-USD')
df= data.history (start='YEAR-MONTH-DAY', end='YEAR-MONTH-DAY')
该数据集包含多个列,但我们将重点关注收盘价列和日期列。date 列需要作为索引使用,并指定频率。如果数据源不是 Yfinance(它已经处理了这一点),以下代码片段可能会很有帮助:
df = df.set_index(pd.DatetimeIndex(df['Date'], freq='D'))
作为 Web3 数据集,相较于传统的金融股票价格数据集,它也包括了周末的价格,反映了市场的连续运营特点。在选择时间序列数据集时,必须确保没有缺失值,或者使用适当的技术处理它们。
如果只需要处理工作日,Pandas 库提供了一些额外的函数,比如USFederalHolidayCalendar,它导入假期日历并提供假期列表:
from pandas.tseries.holiday import USFederalHolidayCalendar
CustomBusinessDay 类提供了一个参数化的 BusinessDay 类,可用于创建自定义的工作日日历,以适应本地假期和本地周末惯例:
from pandas.tseries.offsets import CustomBusinessDay
此外,我们还准备了一个由新闻文章及其对应的情感分析(SA)组成的数据集。对于我们希望建模的比特币(BTC)价格时间序列中的每一天,我们将其与一组新闻文章及其相应的 SA 匹配。我们将验证一个假设,即将来自现实世界的外部信息纳入模型中,将提高预测性能。其他可以考虑的变量包括交易量、包含BTC一词的推文数量、距下次减半事件(即比特币挖矿奖励减半,每约四年发生一次)的剩余天数等。
在探索性数据分析(EDA)过程中,可能会发现数据集中的缺失值、异常值或不规则情况。如在第一章中所讨论,有些时候由于极端波动,市场价格会暂停,例如 UST 脱钩。在处理包含这些问题的数据集时,我们应如何应对?对于平稳序列,非时间序列特定方法,如均值或中位数插补,是有效的。针对时间序列的特定技术包括最近观察值前推(LOCF),它用紧接前一个观察值填充缺失值;以及下一观察值后推(NOCB),它用紧接后一个观察值填充缺失值。另一种方法是插值,根据假定的观察值之间的关系,可以是线性、插值多项式或样条插值。有关解决这一问题的更多方法,参见进一步阅读部分。
在深入研究模型之前,重要的是要解决时间序列数据的训练-测试集拆分概念。与我们迄今为止分析的传统数据集不同,时间序列模型本质上具有内生的时间性,这正是我们希望捕捉的内容。这意味着,值在时间序列中的位置将对未来的点产生影响。为了理解并捕捉这种时间关系,我们必须保持时间序列及任何外生变量的时间顺序。随机拆分数据不适用于时间序列分析。
在这种情况下,测试数据集将由序列中最新的部分组成,而训练数据集将包括从序列开始到所选测试部分的所有行。
Sklearn 提供了一个有用的类来执行这种拆分,叫做TimeSeriesSplit:
from sklearn.model_selection import TimeSeriesSplit
文档可以在以下链接中找到:
scikitlearn.org/stable/modules/generated/sklearn.model_selection.TimeSeriesSplit.xhtml
我们尝试解决的挑战是预测那些不包含在训练中的日期的 BTC 价格。时间序列问题可以通过使用统计建模来处理,我们将其称为传统方法,也可以通过机器学习来处理,在这种方法中我们将训练一个长短期记忆(LSTM)模型。
讨论传统的数据处理管道
初步的方法涉及统计建模,使用像 ARIMA、带外生变量的 ARIMA(ARIMAX)和自动 ARIMA 等模型。为了使用这些模型,我们需要解决两个额外的挑战:确保时间序列的平稳性和确定合适的模型阶数。
统计模型在应用于平稳时间序列时表现更好。像 ARIMA 这样的传统统计时间序列模型在处理平稳时间序列时更为有效。解决这个问题将是预处理阶段的一部分。
第二个挑战出现在建模阶段,这涉及理解数据集、确定合适的滞后和定义时间窗口。我们将使用 Auto ARIMA 算法手动接近解决方案,它会自动处理超参数。
数据预处理
可以采用多种函数将非平稳时间序列数据转换为适合我们模型的格式。例如,差分、对数变换、移动平均(MAs)、百分比变化、滞后和累积和等。
差分计算连续观测值之间的差异。这个技术通过去除某个水平的变化来帮助稳定时间序列的均值,从而减少或消除趋势和季节性。
在Traditional time series models.ipynb笔记本中,我们从一个看起来像这样的数据集开始:

图 11.8 – 完整时间序列
为了应用差分,我们可以使用以下代码:
df.diff().dropna()
经过这样的处理,数据集转换如下:

图 11.9 – 差分时间序列
在某些情况下,仅进行一次差分可能无法使序列变为平稳。在这种情况下,可能需要进行第二次差分以实现平稳。
其他函数,如百分比变化、对数差分和 MA,也可以帮助减少趋势和季节性,使序列更像白噪声。对数变换在处理非恒定方差时尤其有用,而 MA 对于波动性较高的序列也有益。
为了帮助判断一个序列是否平稳,我们可以使用统计检验方法,如迪基-富勒检验。该检验是基于根的检验,重点关注与时间序列变量第一阶滞后相关的系数。如果该系数等于 1(表示单位根),则该时间序列表现为非平稳,即原假设。如果检验结果为负且具有统计学显著性,我们拒绝原假设,表明该时间序列是平稳的。还有其他类似的检验方法,如Kwiatkowski-Phillips-Schmidt-Shin(KPSS)检验或 Phillips-Perron 检验。由于解释超出了本书的范围,但它们都可以从我们使用的同一库中获得。一旦我们获得了平稳的数据集,就可以开始建模。
建模 – ARIMA/SARIMAX 和 Auto ARIMA
在用于预测未来值的统计算法中,我们遇到了 ARIMA/SARIMAX 和 Auto ARIMA。ARIMA 考虑过去的值来预测未来的值,而 SARIMAX 则结合了季节性模式和外生变量。Auto ARIMA 则基于训练数据自动化建模过程。
这些模型的名称源自其包含的概念。ARIMA代表自回归(AR)-差分(I)-移动平均(MA)。SARIMAX在此基础上增加了S,表示季节性,以及X,表示外生性,因为它可以输入独立变量。Auto ARIMA则在Auto(自动建模)前缀的基础上进一步简化了建模过程。让我们深入探讨这些概念。
AR确定时间序列自身的回归阶数。它假设最新的数据点值依赖于前一个值,并且该依赖关系具有我们确定的滞后数,即滞后观测数。
我们可以通过使用 PACF 图来确定回归阶数,该图是statsmodels库的一部分。以下代码可用于绘制该图:
pacf_td = plot_pacf(training_data)
PACF 衡量过去值与当前值之间的直接相关性,并检查每个滞后的尖峰以确定其显著性。如果某个滞后的尖峰超出了显著性限制,则表明该滞后的相关性不为零。显著相关性的数量决定了 AR 项(p)的阶数。
I 表示使序列平稳所需的差分次数。
MA 根据过去的预测误差来建模时间序列的误差,假设当前误差依赖于先前的误差,并且具有我们确定的滞后。这本质上对应于时间序列数据上“窗口”函数的大小,并且对应于模型中的 MA (q) 部分。我们可以通过检查自相关图 (ACF) 来确定 q 的阶数。
ACF 展示了时间序列元素之间是正相关、负相关,还是相互独立的。横轴表示滞后值,尖峰显示了这些滞后值的相关性程度。我们根据远离零的统计显著尖峰,考虑一个阶数为 q 的 ACF。
为了绘制 ACF,我们可以使用以下代码,利用 statsmodels 库:
acf_diff = plot_acf(df_train_diff)
这里是开始测试模型的一个经验法则:
如果 PACF 在滞后 p 处有显著尖峰但之后没有,并且 ACF 图呈现更渐进的衰减,我们将为模型使用以下阶数:ARIMA (p,d,0):

图 11.10 – 假设 1
如果 ACF 图在滞后 q 处有显著尖峰但之后没有,并且 PACF 图呈现出更渐进的衰减,我们将为模型使用以下阶数:ARIMA (0,d,q):

图 11.11 – 假设 2
m 表示时间周期。它将以类似时间序列的方式建模。SARIMA 的季节性组件的具体内容如下:
SARIMA(p,d,q)(P,D,Q)[m]
组件定义如下:
-
P:季节性 AR 阶数。 -
D:季节性差分阶数。 -
Q:季节性 MA 阶数。 -
m:单个季节性周期的时间步数。为了得到这个数字,通常需要分解我们希望预测的相似时间段(始终使用训练数据集)以观察季节性。在此分析中,我们看到季节性为 8 天。
为了评估模型,我们采用一种传统的回归指标——均方根误差 (RMSE)。RMSE 是一种统计度量,用于评估模型预测准确性,方法是计算 均方误差 (MSE) 的平方根。MSE 是原始值与预测值之间平方差的平均值。RMSE 产生一个单一、易于解释的值,代表预测模型误差的典型大小。较低的 RMSE 表示预测值与实际值之间的拟合度更好,反映了模型的预测更为准确。另一个相关指标是 平均绝对误差 (MAE),它表示数据集中实际值与预测值之间绝对差值的平均值。
RMSE 被广泛用于比较回归模型的性能,特别是因为它与因变量的单位相同,从而使得结果更容易解释。
在 Jupyter 笔记本中,我们可以观察到模型还可以进一步改进。手动建模的结果是 RMSE 值为 0.073。
Auto ARIMA
Auto ARIMA 很好地处理了超参数调优任务。它会自动生成参数(p,d,q)的最优值。
被称为赤池信息量准则(AIC)的度量,用于选择回归模型的预测变量,用来确定 ARIMA 模型的阶数。特别地,Auto ARIMA 模型在拟合过程中通过迭代来寻找能最小化 AIC 的最佳参数组合。根据文档,它类似于网格搜索,尝试不同的 p 和 q 参数组合。对于差分项,Auto ARIMA 使用如扩展的迪基-富勒(Augmented Dickey-Fuller)检验等平稳性检验,并考虑季节性。
这种方法显著改善了我们的模型,节省了时间并减少了人为错误。为了实现它,我们可以使用以下代码:
pm.auto_arima(training_data, stepwise=False, seasonal=True, n_jobs=-1, trace=True)
传入的参数如下:
-
training_data:这是我们希望建模的时间序列数据。 -
stepwise:一个布尔参数,控制函数是否应执行逐步搜索以找到最佳 ARIMA 模型。如果设置为True,函数将执行逐步搜索(即,它将迭代考虑添加或删除 AR、MA 或 I 组件)。如果设置为False,函数将通过对所有可能组合进行穷举搜索来查找最佳 ARIMA 模型,类似于网格搜索。逐步搜索较快,但可能并不总是能找到最佳模型。 -
seasonal:一个布尔参数,指定模型是否应包括季节性成分(例如 SARIMA)。如果设置为True,该函数将搜索数据中的季节性模式。如果设置为False,则仅考虑非季节性的 ARIMA 模型。 -
n_jobs:该参数控制在执行模型搜索时使用的 CPU 核心数。将其设置为-1表示使用所有可用的 CPU 核心,这可以加快搜索过程,尤其是在数据集较大的时候。 -
trace:这是一个调试参数。当设置为True时,它启用详细输出,包含诊断信息和模型搜索过程中的中间结果。
实现该模型后,RMSE 显著下降;然而,仍有改进空间。现在,让我们看看如何融入特定领域或主题知识。
添加外生变量
外生变量是可以被纳入模型的附加信息。这些变量可以来自相同的时间序列,比如观察 BTC 价格在特定小时或日期的波动,或者它们可以是完全外生的,如新闻情感分析或来自 X(前 Twitter)的数据。
在我们的笔记本中,我们将每天新闻的情感作为外生变量纳入模型。该数据集的预处理包括以下内容:
-
根据
sentiment_mapping字典将新闻情绪映射到以下标准:sentiment_mapping = { 'Positive': 1, 'Negative': -1, 'Neutral': -1 z-score value, which behaves as a threshold against which we will identify outliers. Those considered outliers are multiplied by 2\. This is done with the following code in the traditional_time_series_models.ipynb file:outliers = day_sentiment_df[z_scores > threshold]
outliers['sentiment_number'] = outliers['sentiment_number'] * 2
day_sentiment_df.update(outliers)
步骤 1 和 步骤 2 中的两个决策是数据科学家的任意决定,旨在反映加密市场通常会对新闻产生过度反应,无论是正面、负面还是中性新闻。
通过应用外生变量,ARIMAX 和 Auto ARIMA 模型显示出相较于不使用外生变量的版本,RMSE 下降,这是非常积极的:
-
rmse -manual: 0.046 -
rmse -auto: 0.062
我们看到,当加入外生变量时,手动调整模型的表现优于 Auto ARIMA 模型。
为了比较这些模型与 LSTM 的性能,我们可以比较 RMSE 指标,或者使用以下代码反转结果,以便比较 USD 价格。要从对数转换中反转,我们可以使用以下代码片段:
testing_data= np.exp(testing_data)
forecast_test=np.exp(forecast_test)
rmse_exog = np.sqrt(mean_squared_error(testing_data, forecast_test))
我们已经回顾了统计模型,现在我们继续构建深度学习(DL)模型。
使用神经网络 – LSTM
我们在第八章中详细解释了 LSTM 的工作原理。简而言之,LSTM 是一种专门设计用来检测数据序列中模式的递归神经网络(RNN)。它的独特之处在于,相比于传统的 RNN,LSTM 可以在较长时间内保留信息。LSTM 通过选择性地保留相关信息来克服短期记忆问题。
数据预处理
我们将把这个问题视为监督学习(SL)任务。为此,我们将修改训练集,具体方法如下:
-
使用
MinMaxScaler()缩放数据集。 -
遍历缩放后的数据集,并提取当前价格(
y_train)之前的 60 天数据,将其转换为每个价格的特征。结果将是一个训练数据集,其中有 60 个价格列作为每个 BTC 价格(y_train)的x_train特征。总之,对于模型学习的每个数据点,它参考的是x_train中的前 60 天数据:

图 11.12 – 训练数据集结构
我们使用之前的 60 天作为每一天的输入变量,将其视为输出变量。
模型构建
为了构建模型,我们将利用 Keras 库。为此,我们为模型添加了两层 LSTM,每层 50 个神经元,第一层的输入形状为我们的数据集。
我们还添加了两层全连接层,每层分别有 25 和 1 个神经元。模型结构应保持尽可能简单,并且完全可以修改:
model= Sequential ()
model.add (LSTM(50, return_sequences=True, input_shape=(x_train.shape[1],1)))
model.add (LSTM (50, return_sequences = False))
model.add (Dense(25))
model.add (Dense(1))
我们稍后会使用 Adam 优化器进行编译,并选择 mean_squared_error 作为损失度量:
model.compile (optimizer='Adam', loss='mean_squared_error')
为了保存回调,以便分析我们训练的结果,我们设置了 TensorBoard 工具,从一个新的文件夹中读取保存的日志:
tensorboard_callback = tf.keras.callbacks.TensorBoard(log_dir="./logs")
训练与评估
我们用批量大小为 10 和 35 个 epoch 来训练我们的模型:
model.fit (x_train, y_train, batch_size=10, epochs=35,callbacks=[tensorboard_callback])
为了评估模型的预测效果,我们将构建一个包含过去 30 天数据的新数据集,这些数据未曾传递给模型。为此,我们需要遵循与数据预处理部分中训练数据集相同的步骤。我们将 60 行数据转化为x_test中的列,这些列成为第 61 个值的特征,该值即为要预测的y(或y_test)。
在预测时,我们只会考虑最后 30 天的数据,并计算预测值与y_test值之间的 RMSE。为此,我们可以使用以下代码:
np.sqrt(mean_squared_error(y_test, predictions))
如果我们绘制预测值和真实数据的图表,结果还不错。请参阅Chapter11/LSTM.ipynb笔记本查看彩色版本:

图 11.13 – 预测值和真实数据
对比模型的 RMSE 显示,在价格高波动的环境中,LSTM 方法表现更好,误差为$457,而最好的 ARIMA 模型误差为$1,283。
需要考虑的一些关键差异如下:
-
变量之间的关系:ARIMA 模型假设输入和输出变量之间存在线性关系。它们可以捕捉一些非线性模式,但数据中的复杂非线性依赖关系无法覆盖。LSTM 模型更适合捕捉时间序列数据中的非线性关系和长期依赖性。这使得 LSTM 模型更适合建模具有复杂时间模式的非线性和顺序数据。
-
训练复杂度:ARIMA 模型涉及估计 AR、MA 和差分项等参数。LSTM 模型和所有神经网络(NNs)一样,需要更多的计算资源和训练时间。它们涉及训练多个递归单元层次,且有大量参数。与传统统计模型相比,训练深度学习(DL)模型通常需要更多的数据和计算能力。
在我们分析的库中,可以同时检查这两种方法,比较它们的表现,并评估每个模型的准确性。
总结
在本章中,我们探讨了对 BTC 价格时间序列的分析,适用于一个持续运作、波动性高且可能对新闻事件产生夸张反应的市场。
我们首先熟悉了时间序列分析的基本概念,并介绍了传统模型,如 ARIMA 和 Auto ARIMA。对于我们的用例,我们将价格数据集转换为平稳形式,并学习如何将这些模型应用于数据。最后,我们将外部变量(如新闻)纳入模型中。这个外部信息证明是有价值的,有助于减少我们跟踪的误差指标。
此外,我们深入探讨了 LSTM 模型方法,这要求我们以不同的方式重构数据集。这涉及到对数据集的众多修改和调整,以适应 LSTM 模型的特定要求,最终取得了更好的表现。
通过采用一系列综合性技术并结合外部因素,我们在分析和预测代币价格时间序列方面获得了宝贵的洞察。这些发现为进一步探索和完善我们的模型奠定了基础。
深入阅读
为了补充本章内容,以下链接可能对您有所帮助:
-
R 中的时间序列分析第二部分:时间序列转换。(无日期)。一个展示 R 与 Python 教程的在线社区。DataScience+。
datascienceplus.com/time-series-analysis-in-r-part-2-time-series-transformations/ -
计算机科学。(2019 年,12 月 22 日)。使用 Python 和机器学习进行股票价格预测 [视频]。YouTube。
www.youtube.com/watch?v=QIUxPv5PJOY -
Luis Alberiko Gil-Alaña。(2021)。时间序列导论 [PDF 文档]。
-
加密货币与股市指数。它们相关吗? LA Gil-Alaña,EJA Abakah,MFR Rojo。国际商业与金融研究,2020。
ddfv.ufv.es/bitstream/handle/10641/2229/cryptocurrencies%20and%20stock%20market%20indices.pdf?sequence=1&isAllowed=y -
比特币市场中的长记忆波动建模:持久性和结构性断裂的证据。E Bouri,LA Gil-Alaña,R Gupta,D Roubaud。国际金融与经济学杂志,2019。
onlinelibrary.wiley.com/doi/abs/10.1002/ijfe.1670 -
Abulkhair, A. (2023 年,6 月 13 日)。数据插补揭秘 | 时间序列数据。Medium。
medium.com/@aaabulkhair/data-imputation-demystified-time-series-data-69bc9c798cb7 -
Jingjuewang。(2017 年,12 月 11 日)。初学者处理时间序列中的缺失值。Kaggle:你的机器学习与数据科学社区。
www.kaggle.com/code/juejuewang/handle-missing-values-in-time-series-for-beginners -
Aldean, A. S. (2023 年,6 月 29 日)。时间序列数据插值。Medium。
medium.com/@aseafaldean/time-series-data-interpolation-e4296664b86 -
Holloway, N. (2019, March 16). 季节性和 SARIMAX. Kaggle: 你的机器学习与数据科学 社区.
www.kaggle.com/code/nholloway/seasonality-and-sarimax -
Brownlee, J. (2020, December). 使用 Python 的预测区间理解时间序列预测不确定性. 机器学习 精通.
machinelearningmastery.com/time-series-forecast-uncertainty-using-confidence-intervals-python/ -
Chugh, A. (2022, March 16). MAE、MSE、RMSE、决定系数、调整后的 R 平方——哪个指标更好? Medium.
medium.com/analytics-vidhya/mae-mse-rmse-coefficient-of-determination-adjusted-r-squared-which-metric-is-better-cd0326a5697e
第十二章:通过图形发现营销机会
数据在营销中发挥了至关重要的作用,推动决策制定,并优化资源配置,以支持有影响力的营销活动。然而,区块链数据固有的伪名性和复杂性为营销团队带来了挑战,其中提取最大价值在很多情况下仍然是一个持续的机会。
营销团队使用的主要应用之一是聚类,它涉及将具有共同兴趣的群体进行组织,以便进行客户细分。这项技术在社交网络中取得了很大成功,促进了产品推荐系统的发展,并推动了新的连接。
类似于社交网络,区块链数据凭借其大量交易,具有从少量互动中推断偏好的巨大潜力。标签分类是另一个有价值的应用场景,它帮助营销团队有效地识别和定位区块链中的社区。通过辨识社区,数据科学家可以帮助营销人员克服伪名性带来的限制,并获得有价值的洞察。
在本章中,我们将深入探讨以下主题:
-
图形入门
-
数据库选择与特征工程
-
建模、训练与评估结果
在本章结束时,我们将全面了解如何利用网络和图形的力量来制定有效的营销策略。
技术要求
在本章中,我们将利用networkx库,这是一个用于处理网络或图形的 Python 库。它提供了一系列工具和功能,用于创建、操作和分析网络。该库便于创建节点、添加信息,并提供用于分析和探索网络的算法,如寻找最短路径、计算中心性度量和检测社区。
如果你以前没有使用过networkx,可以通过以下代码片段进行安装:
pip install networkx
networkx的文档可以在networkx.org/documentation/stable/index.xhtml找到。
我们还将使用Gephi,一款免费的开源图形绘制工具。Gephi 是一个用户友好的工具,旨在可视化和探索图形和网络。它帮助用户深入洞察并分析图数据中的复杂关系。
使用 Gephi,我们可以从各种格式中导入数据,并选择特定的节点,以了解它们在数据集中的位置。该工具提供了众多统计功能来支持图形分析。它允许我们根据特定标准过滤、排序和操作图形,使我们能够聚焦于相关的节点和边。
如果你之前没有使用过 Gephi,可以从他们的页面下载:gephi.org/。关于 Gephi 的全面指南可以在《Gephi Cookbook》一书中找到,点击此处查看:www.packtpub.com/product/gephi-cookbook/9781783987405。
对于我们的机器学习模型,我们将使用 StellarGraph 库。StellarGraph 专为处理图结构数据而设计,特别适用于与机器学习和数据分析相关的任务。它的一个关键特点是与流行的机器学习框架(如 TensorFlow 和 Keras)的集成。StellarGraph 提供了将图转换为这些框架兼容格式的方法,使我们能够将机器学习模型和算法应用于图结构数据。StellarGraph 的文档可以在stellargraph.readthedocs.io/en/stable/找到。
如果这是你第一次使用这个库,你可以通过pip安装它:
pip install stellargraph
与本章相关的所有数据和代码文件,以及彩色图像,可以在本书的 GitHub 仓库中找到,网址是:https://github.com/PacktPublishing/Data-Science-for-Web3/tree/main/Chapter12。
我们建议你阅读Chapter12文件夹中的代码文件,这样你可以更有效地跟随本章的内容。
图论入门
根据伊纳尔·利夫的说法,"网络科学,有时被认为是数据科学的一个子领域,有时被认为是一个独立的学术领域,是研究网络结构模式的一系列技术、方法和工具。" 一个网络的示例是伦敦地铁图的图像:

图 12.1 – 贝克设计的伦敦地铁图概述(来源:en.wikipedia.org/wiki/File:Beck_Map_1933.jpg,属于合理使用)
在我们对网络和图的探索中,我们将交替使用这些术语。
近年来,网络研究因其能够简单地解释实体之间的关系而受到广泛关注。正如马蒂亚斯·阿维拉教授所解释的,“网络,也称为数学文献中的图,是由一些节点组成的集合,其中某些节点通过边连接在一起 *。”
在本教程中,我们将探索图的基本概念,包括它们的定义和特点。
一个网络由节点(也称为顶点或 V)组成,这些节点通过连接(或边或 E)相互链接。图或网络通常表示为 G,表示法为 G=(V,E)。
在图 12.2中,我们可以观察到地址 0xdac17f958d2ee523a2206206994597c13d831ec7 和 0x28C6c06298d514Db089934071355E5743bf21d60 之间网络内图的组成部分:

图 12.2 – 两个地址之间的关系
数据分析师的角色是从数据中提取有意义的见解和可操作的洞察。一旦我们找到了有意义的连接,添加上下文就显得尤为重要。例如,在图 12.3中,我们正在查看 USDT 智能合约与 Binance 地址之间的关系:

图 12.3 – 两个标记地址之间的关系
图的类型
有向图(digraphs),由 Stamile、Marzullo 和 Deusebio 定义,表示为“一个对,G=(V,E),其中 V 是节点集合,E 是表示两个节点之间连接的有序对集合。”E 中的元素是有序的,表示从一个节点(通常称为“源”)到另一个节点(通常称为“目标”)的方向:

图 12.4 – 有向图示例
在 有向图 中,节点可以分为入度(指向某节点的边的数量,表示图中有向边指向该节点的节点)和出度(从某节点出发的边的数量,表示图中该节点有向边指向的节点)。入度和出度提供了关于节点连接性和影响力的见解。理解这个概念对于各种图分析任务非常有价值,比如识别中心节点、研究信息流、检测有影响力的节点、评估有向网络的结构和动态。
自我图,也称为邻居图,专注于一个特定的节点,称为“自我”节点。它显示自我节点及其所有邻居节点,以及连接它们的边。自我图对于分析特定节点周围的局部结构和连接非常有用:

图 12.5 – 自我图示例
加权图是每条边都有一个相关权重或值的图。权重是数值,可以表示连接的节点之间关系的各种特征,如强度、距离、成本、连接频率等。权重提供了额外的信息,可用于分析、训练和推断:

图 12.6 – 加权图示例
还有许多其他具有独特特征和用途的图形模式,它们超出了本介绍的范围。那么,为什么图形模式对我们的数据分析如此重要呢?图形模式有助于揭示区块链中地址之间关系的动态变化。在一篇名为可视化动态比特币交易模式的文章中,作者解析了这些模式并提供了相应的解释:

图 12.7 – 比特币区块中的图形模式示例
归属
可视化动态比特币交易模式,Dan McGinn 等,2016;由 Mary Ann Liebert, Inc.出版。
本开放获取文章根据创作共用许可证(creativecommons.org/licenses/by/4.0)分发,允许在任何媒介中不受限制地使用、分发和复制,只要正确引用原始作品。
在接下来的部分中,我们将分析属于两个具有不同特征的社区的地址数据集——一个与 OpenSea NFT 市场相关,另一个与名为 Binance 的集中式交易所相关。每个地址与其社区之间的关系特征可以通过图中形成的模式观察到:

图 12.8 – 目标社区之间的关系
图形属性
根据 Stamile、Marzullo 和 Deusebio 提出的分类方法,我们发现分析整合度量和隔离度量是很有帮助的。
整合度量显示了节点之间相互连接的趋势。在这些度量中,我们有距离和最短路径。
距离定义为“从给定的源节点到达目标节点所需经过的边的数量”。最短路径是与两个节点之间所有可能路径相比,边数最少的路径。如果图是加权的,它是具有最小边权和的路径。我们对这一概念感兴趣,因为它将帮助我们识别重要的节点。
另一个与最短路径相关的度量是特征路径长度。它被定义为所有可能的节点对之间最短路径长度的平均值。
另一类度量是隔离度量,顾名思义,它们寻找节点之间更可能存在的相似关系模式。它们识别出互联节点的群体,这些群体被称为社区。在这些度量中,我们有聚类系数和模块度。
聚类系数是衡量节点之间倾向于聚集(或“聚类”)的程度。其原理是节点与相似节点之间的聚集程度要高于与随机节点之间的聚集。聚类系数基于三角形或三重组的划分,它由三个节点和三条边组成。它研究节点的邻居之间也是否是邻居的比例。这里存在局部和全局聚类系数。
模块化衡量一个网络的强度,以便它可以被划分成模块或社区。如果一个网络的模块化高,意味着在一个社区内部的节点之间连接密集,而不同模块之间的节点连接稀疏。Gephi 工具和 Networkx 库都可以帮助我们计算模块化并识别社区。
图 12.9 显示了将在下一部分介绍的数据集,数据集以两种颜色呈现,每种颜色对应一个已检测到的社区:

图 12.9 – 应用 Gephi 筛选条件的数据集社区
该图是使用 Gephi 创建的,并应用了以下筛选条件:
-
拓扑筛选器:巨型组件
-
度数范围:大于 3
-
节点大小:介数中心性
-
节点颜色:模块化 2.0
让我们深入了解这个数据集!
数据集
数据集包含一系列目标地址为 Binance 或 OpenSea 的交易。这些实体由多个地址提供服务,为了简化,我们选择了其中一个与它们相关联的地址。
Binance 14 地址(0x28c6c06298d514db089934071355e5743bf21d60)代表一个 Binance 热钱包,用于促进中心化交易所与以太坊之间的连接。这个钱包中的资金用于 Binance 之外的存取款。
另一方面,OpenSea 的地址,特别是 Wyvern Exchange v2(0x7f268357a8c2552623316e2562d90e642bb538e5),对应 OpenSea 的市场合约。
要使用 Flipside 复制此数据集,我们可以使用以下查询:
sql =SELECT from_address, to_address, tx_hash
FROM ethereum.core.fact_transactions
WHERE block_timestamp >= '2023-01-01T00:00:00.000Z'
and block_timestamp <= '2023-06-01T00:00:00.000Z'
and to_address in ('0x28c6c06298d514db089934071355e5743bf21d60', '0x7f268357a8c2552623316e2562d90e642bb538e5')
limit [800]
对于可视化,我们可以使用 Graph Machine Learning 中提出的 draw_metric 函数,该函数突出显示在讨论的指标下具有较高值的节点。我们将进行的分析可以在 Chapter12/features.ipynb 中找到,结果 DataFrame 名为 influencer_nodes.csv。
介数中心性是一个衡量指标,表示一个节点作为最短路径中桥梁的次数。经过该节点的最短路径数量越多,介数中心性就越大。
有趣的是,在influencer_nodes.csv中,我们可以观察到 USDT 和Wrapped Ethereum(WETH)稳定币节点具有较高的介数中心性,分别与 Binance 和 OpenSea 连接。下图展示了具有较高介数中心性的节点:

图 12.10 – 数据集中的介数中心性
以下信息来自 CSV 文件,经过Betweenness Centrality列筛选:
| 地址 或节点 | 介数中心性 | 标签 |
|---|---|---|
0x28c6c06298d514db089934071355e5743bf21d60 |
0.494010213 |
Binance 14 |
0x7f268357a8c2552623316e2562d90e642bb538e5 |
0.323956896 |
OpenSea: Wyvern Exchange v2 |
0xdac17f958d2ee523a2206206994597c13d831ec7 |
0.173128355 |
Tether-USDT 稳定币 |
0xc02aaa39b223fe8d0a0e5c4f27ead9083c756cc2 |
0.16215128 |
Wrapped Ether |
表 12.1 – 经过介数中心性列筛选的数据
度数是指与特定节点直接相连的连接或节点的数量。连接较多的节点通常具有更强的影响力和中心性。
在influencer_nodes.csv中,我们可以看到,与 Binance 连接的有 USDT 和 USD Coin,与 OpenSea 连接的有 WETH 和 Seaport 1.1 地址(是 OpenSea 基础设施的一部分):

图 12.11 – 数据集中的度数
以下信息来自 CSV 文件,经过Degree列筛选:
| 地址 或节点 | 度数 | 标签 |
|---|---|---|
0x28c6c06298d514db089934071355e5743bf21d60 |
0.370160529 |
Binance 14 |
0x7f268357a8c2552623316e2562d90e642bb538e5 |
0.101038716 |
OpenSea: Wyvern Exchange v2 |
0xdac17f958d2ee523a2206206994597c13d831ec7 |
0.094428706 |
Tether-USDT 稳定币 |
0xa0b86991c6218b36c1d19d4a2e9eb0ce3606eb48 |
0.046270066 |
Circle USD |
0xc02aaa39b223fe8d0a0e5c4f27ead9083c756cc2 |
0.16215128 |
Wrapped Ether |
0x00000000006c3852cbef3e08e8df289169ede581 |
0.029272899 |
Seaport 1.1 (OpenSea 基础设施) |
表 12.2 – 经过度数列筛选的数据
在influencer_nodes.csv中,我们可以看到,具有较接近中心性的地址是连接在两个介数中心性较高的地址之间的节点(Binance 14 和 OpenSea: Wyvern Exchange v2)。它们作为两个社区之间的桥梁:

图 12.12 – 数据集中的接近中心性
以下信息来自 CSV 文件,经过Closeness Centrality列筛选:
| 地址 或节点 | 接近中心性 | 标签 |
|---|---|---|
0x411c104dcec01380ee86ea2d090ed3450850f1d6 |
0.33197098 |
无标签 |
0x28c6c06298d514db089934071355e5743bf21d60 |
0.33030801 |
Binance 14 |
0xc02aaa39b223fe8d0a0e5c4f27ead9083c756cc2 |
0.32937989 |
Wrapped Ether |
0x6e785f2fdbdc899f8f08cc1517f82a585b44f9c5 |
0.32602094 |
renethecat.eth |
表 12.3 – 通过接近中心性列筛选的数据
特征值中心性显示了一个节点在网络中的影响力,考虑到它与之连接的节点的得分。如果它与得分较高的节点连接,则中心性将更高。对于本次分析,我们需要尊重社区,因为节点在某个特定社区中会变得很重要。
如果我们计算 Binance 社区内的特征值中心性,我们会看到 USDT 稳定币智能合约和美元稳定币 USD Coin 具有最高的特征值中心性。随后地址值的下降表明,通常这些地址通过稳定币地址连接以到达 Binance:

图 12.13 – Binance 社区的特征值中心性
以下信息来自 CSV 文件,通过Class1_ecentrality列进行筛选:
| 地址 或节点 | class1_ecentrality | 标签 |
|---|---|---|
0x28c6c06298d514db089934071355e5743bf21d60 |
0.669654742 |
Binance 14 |
0xdac17f958d2ee523a2206206994597c13d831ec7 |
0.198603275 |
Tether- USDT 稳定币 |
0xa0b86991c6218b36c1d19d4a2e9eb0ce3606eb48 |
0.080423932 |
Circle USD |
表 12.4 – 通过 Class1_ecentrality 列筛选的数据
对于 OpenSea 社区,第一个两个地址和其余地址之间的差距较小。作为去中心化结构,得分较为分散。我们可以在主要节点中看到 Wrapped Eth、Uniswap 和一个名为renethecat.eth的收藏家的地址(opensea.io/ReneTheCat):

图 12.14 – OpenSea 社区的特征值中心性
以下信息来自 CSV 文件,通过Class0_ecentrality列进行筛选:
| 地址 或节点 | Class0_ecentrality | 标签 |
|---|---|---|
0x7f268357a8c2552623316e2562d90e642bb538e5 |
0.553669353 |
OpenSea: Wyvern Exchange v2 |
0xc02aaa39b223fe8d0a0e5c4f27ead9083c756cc2 |
0.227218243 |
Wrapped Ether |
0x00000000006c3852cbef3e08e8df289169ede581 |
0.208338034 |
Seaport 1.1 (OpenSea 基础设施) |
0xef1c6e67703c7bd7107eed8303fbe6ec2554bf6b |
0.17412939 |
Uniswap: Universal Router 2 |
0x6e785f2fdbdc899f8f08cc1517f82a585b44f9c5 |
0.133520629441651 |
renethecat.eth |
表 12.5 – 通过 Class0_ecentrality 列筛选的数据
执行这种类型的分析有助于我们确定特定社区中的影响力节点。影响力的概念取决于上下文。例如,如果我们正在分析一个中心化交易所,我们可以了解他们使用哪些地址作为储备,他们的客户主要使用哪些稳定币,等等。而对于一个去中心化的 NFT 市场,其中个人通过自己的地址进行交易,我们可以识别出收藏家、收藏智能合约等。
根据之前的分析,我们发现一个标记为“rene the cat”的地址具有影响力。如果我们结合 OpenSea 和 X(前 Twitter)的链下信息(这两个 API 在本书的第三章和第四章中有详细介绍),我们可以检索到以下来自区块链数据的可操作数据:
-
0x6e785f2fDbdc899F8F08cc1517F82A585b44F9c5 -
OpenSea 收藏:
opensea.io/ReneTheCat -
Twitter 账号:
twitter.com/mmendiguchiia
关于展示的说明
有时候,将图形分析结果展示给没有数据背景的观众可能会具有挑战性。通常建议以表格形式展示关键节点,提供一种用户友好的格式,根据所选标准(如最高的接近度、介数中心性等)概览列出的个体。这种方法使我们能够突出在多个排行榜上出现的个体,如本节所示。这样,观众可以轻松识别并理解这些节点的重要性。
通过这一分析,我们已识别出影响力节点。在接下来的部分中,我们将关注被影响的节点,即属于某个社区的节点。
节点分类
正如本章介绍所提到的,在处理大型图时,例如不断增长的区块链交易数据,我们可能只有部分节点带有标签。这些标签指示特定的协议、用户兴趣以及市场细分群体。挑战在于扩展标签,使得随着所有节点被添加到网络中,它们可以归属到一个特定的群体或社区。此练习在Chapter12/Graphsage_node_classification.ipynb中进行。
在这个特定案例中,我们计划构建一个营销解决方案,但图分析也可以用于发现潜在的欺诈检测或洗钱行为。
在本次练习中,我们将使用 GraphSAGE,它是建立在图卷积网络基础上的模型。GraphSAGE 是一个用于图的归纳式深度学习模型,可以处理新增节点而无需重新训练。这一特性对于不断增长的交易数据特别有利,因为随着新的地址和交易的不断加入,我们不需要生成新的训练数据来为整个网络创建新的模型。GraphSAGE 已在 StellarGraph 库中实现。
GraphSAGE 能够预测新节点的嵌入。为了实现这一点,模型学习聚合器函数,这些函数能够基于节点的特征和其邻域的特性生成新节点的嵌入。
图 12.15 显示了我们数据集的简化版本,其中可以观察到两个社区。GraphSAGE 通过对节点的局部邻域进行采样和聚合信息来生成节点嵌入,从而捕捉图中的结构属性和关系。该算法通过考虑邻居节点的嵌入并聚合其信息来迭代更新嵌入。这使得 GraphSAGE 能够在利用局部邻域信息的同时捕捉图的全局结构:

图 12.15 – GraphSAGE 学习步骤
这个过程被称为 归纳 学习,因为模型可以推断出一般原则是从一系列观察中得出的,类似于我们大脑的功能。有关该过程的更多技术解释,请参阅本章的 进一步阅读 部分。
准备工作
对于这个模型,我们需要提供一个 edges 数据集和一个 features 数据集。
edges 数据集与我们在前一部分分析的相同,由与 Binance 14 和 OpenSea 地址交互的交易组成。
influencers.csv 文件是 Chapter12/features.ipynb 笔记本的输出。从这个数据集中,我们将只使用基于特征标准(如介数中心性、节点度数等)的 30 个最重要节点。对于 edges 数据集中的每个节点,我们将分析它们是否与这 30 个顶级影响力节点有任何交易。
此外,我们将向 Louvain 社区检测算法(包含在 Networkx 库中)提供一个模块化字典,以确定每个节点在 edges 数据集中的社区分配。我们将使用 best_partition 函数,它通过 Louvain 启发式方法计算图节点的划分,并最大化模块化。此过程的代码片段如下:
partition = community.best_partition(G)
这个过程的结果是一个平衡良好的数据集,其中每个节点有 30 个特征,包括名为 community 的目标列,其值为 0 和 1。这是一个二分类任务,针对两个社区,但也可以用更多类别重新创建这个练习。
建模
使用模型的第一步是从数据集创建一个 StellarGraph 对象。可以通过以下代码片段使用这两个数据集创建图形来实现:
from stellargraph import StellarGraph
G = StellarGraph({"features": addresses_no_community}, {"transactions": edges})
此外,我们有两个标签:{'community 0' 和 'community 1'}。这些标签需要进行编码。我们将使用来自 scikit-learn 库的 binarize 标签来执行该任务。
与所有机器学习任务一样,我们必须使用传统的model_selection.train_test_split函数将数据分割为训练集和测试集,这个函数来自 scikit-learn。
我们将构建一个GraphSAGENodeGenerator对象,将采样子图中的节点特征输入到 Keras 中:
graphsage_model = GraphSAGE(
layer_sizes=[32, 32], generator=generator, bias=True, dropout=0.5,)
偏差、dropout 和层的概念在第六章中介绍。
预测层将采用 sigmoid 激活函数,因为这是一个二分类问题。如果需要预测更多类别,可以将激活函数改为 softmax:
prediction = layers.Dense(units=train_targets.shape[1], activation="sigmoid")(x_out)
训练与评估
我们将使用 20 个 epochs 来训练模型。在这里,我们关注的是使用accuracy作为评估指标。损失指标是binary_crossentropy,这与我们正在处理的二分类任务一致。我们将使用shuffle来确保在每个 epoch 前对数据进行洗牌:
history = model.fit(
train_gen, epochs=20, verbose=2, shuffle=True)
由于结果已被编码,要解读它们,我们必须将其转回原始格式。为此,我们可以使用以下代码片段:
target_encoding.inverse_transform(all_predictions)
测试集上的准确率为 99%。要查看结果,我们需要创建一个新的 DataFrame,包含两列——一列包含预测的社区,另一列包含实际的标签。该 DataFrame 和混淆矩阵在笔记本中展示。
最后,可以在进一步阅读部分找到 GraphSAGE 演示的列表。
总结
总结来说,本章深入探讨了图网络的基本原理,探索了节点特征、图的类型及其在数据分析中的重要性。通过理解这些基础概念,我们为进一步探索和分析复杂网络奠定了基础。
在此基础上,我们进一步探索了在由两个不同社区——一个集中化的,如 Binance,另一个去中心化的,如 OpenSea——之间互动形成的图中,有影响力节点的特征。
营销解决方案在 Web3 经济的这一阶段至关重要。像 Spindl 这样的公司正在积极构建工具,旨在弥合 Web2 和 Web3 世界之间的信息与粒度差距。为了实现这一目标,它们集中精力研究归因机制,衡量广告对协议的实际影响。一旦归因完成,就需要识别目标社区以进行营销活动。为了实现这一目标,我们采用了 GraphSAGE 算法进行节点分类任务。这种方法使得有限的标签可以扩展到日益增长的 Web3 交易数据。
这是本书第二部分的最后一章。在第三部分中,我们将分析一些实际的建议,以便你能够在理解领先公司专业人士观点的同时,开始 Web3 数据科学的职业生涯。
进一步阅读
要了解本章中涉及的主题,可以查看以下资源:
-
Stamile, C., Marzullo, A., 和 Deusebio, E.(2021 年)。图机器学习:通过应用机器学习技术和算法将图数据提升到新高度。Packt Publishing。
-
Liiv, I.(2021 年)。加密货币 区块链的数据科学技术。Springer。
-
Spindl。(无日期)。介绍:
docs.spindl.xyz/spindl/overview/introduction。 -
关于 GraphSAGE:
-
Ruberts, A.(2021 年 5 月 4 日)。GraphSAGE 在 Python 中的分类应用。Well Enough:
antonsruberts.github.io/graph/graphsage/. -
Özçelik, R.(2019 年 10 月 25 日)。GraphSAGE 的直观解释。Medium:
towardsdatascience.com/an-intuitive-explanation-of-graphsage-6df9437ee64f.
-
-
演示:
-
StellarGraph 基础知识 – StellarGraph 1.2.1 文档。(无日期)。欢迎访问 StellarGraph 文档!– StellarGraph 1.2.1 文档:
stellargraph.readthedocs.io/en/stable/demos/basics/index.xhtml. -
攻击者可追溯性通过图分析在以太坊上的应用。(2022 年 1 月 27 日)。开放获取研究期刊与论文出版 | Hindawi:
www.hindawi.com/journals/scn/2022/3448950/. -
使用网络图可视化以太坊区块链上的潜在欺诈。(2022 年 9 月 29 日)。NVIDIA 技术博客:
developer.nvidia.com/blog/using-network-graphs-to-visualize-potential-fraud-on-ethereum-blockchain/.
-
-
NFT 数据集:
- Blog_scripts/nft_network_analysis_blog_06042022/nft_analytics/nft_analytics_notebook.ipynb 在主分支 · onthemarkdata/blog_scripts。(无日期)。GitHub:
github.com/onthemarkdata/blog_scripts/blob/main/nft_network_analysis_blog_06042022/nft_analytics/nft_analytics_notebook.ipynb?nvid=nv-int-txtad-930904-vt46#cid=an01_nv-int-txtad_en-us.
- Blog_scripts/nft_network_analysis_blog_06042022/nft_analytics/nft_analytics_notebook.ipynb 在主分支 · onthemarkdata/blog_scripts。(无日期)。GitHub:
-
NNs(图神经网络):
-
Prodramp。(无日期)。觉得图神经网络(GNN)难以理解吗?试试这个两部分系列。[视频]。YouTube:
www.youtube.com/watch?v=YdGN-J322y4. -
Avkash Chauhan。(无日期)。你想了解 Python 中的图神经网络(GNN)实现吗? [视频]。YouTube:
www.youtube.com/watch?v=VDzrvhgyxsU. -
DeepWorks/GraphNeuralNetworks/Part2_Example2NodeClassification.ipynb 位于主分支 · prodramp/DeepWorks。 (无日期)。GitHub:
github.com/prodramp/DeepWorks/blob/main/GraphNeuralNetworks/Part2_Example2NodeClassification.ipynb。
-
第三部分 附录
本书的这一部分,我们将探索如何使用我们已获得的知识。我们将深入研究潜在的职业路径,并从 Web3 数据领域的领袖们那里了解他们的经历——他们如何到达现在的职位、他们对未来的愿景,以及他们看重的专业人士素质。
本部分包含以下章节:
-
第十三章,构建加密数据经验 – BUIDL
-
第十四章,与 Web3 数据领域领袖的访谈
-
附录 1
-
附录 2
-
附录 3
第十三章:用加密数据构建经验——BUIDL
如果你不制定计划,那你就是在计划失败。——本杰明·富兰克林,1790 年
教育赋予我们创造价值的能力,无论是为公司做贡献,还是创办自己的企业。如果你已经购买了这本书,那是因为你认识到能够从区块链数据中解锁市场愿意支付的价值。在 Web3 领域,存在很多BUIDLing机会,可以创建有助于推动更透明系统的解决方案。根据币安网站的解释(academy.binance.com/en/glossary/buidl):“BUIDL 是对“build”一词的变形,类似于“HODL”。BUIDL 呼吁大家在区块链和加密货币生态系统中积极建设和贡献 (…) BUIDL 运动认为(…)人们应该主动开始贡献,以帮助采用并改善生态系统 *投资者参与的领域。”
我们已经学会了如何提取价值,现在,让我们看看市场愿意为这些知识提供什么。像阿迪达斯、耐克等全球品牌,以及爱马仕等时尚品牌都已经意识到这个机会,并建立了专注于 Web3 分析的部门。同样,我们可以在招聘搜索引擎和公司官网上观察到越来越多的数据相关职位,这表明该领域有着丰富的机会。为了抓住这些机会,我们需要开始BUIDLing。
在本章中,我们将学习以下内容:
-
构建作品集的重要性以及展示作品集的地方
-
在专门的网站上寻找工作的地方
-
学习 Web3 数据技能的地方
展示你的作品——作品集
构建作品集有两个主要目的。它不仅服务于潜在的求职者,还服务于寻找潜在客户的承包商、顾问和企业主,同时还展示了我们的软技能。
首先,作品集展示了我们取得的成就和知识的深度。当我们能够展示自己的作品,而不仅仅是描述它时,这会给面试官留下深刻的印象。例如,如果我们在以太坊上构建了一个仪表盘,这表明我们能够在其他链上复制这个过程。其次,通过构建作品集的过程,我们获得了关于语言、技术术语和行业当前趋势的宝贵见解。
作品集还突出了市场高度重视的软技能。我们将在本章稍后深入探讨这些软技能,如好奇心、热情、学习敏捷性和主动性。
有许多关于如何构建编程作品集和数据科学作品集的指南。接下来,我们将探讨我们可以在哪里构建数据分析作品集以及在哪里展示我们的作品。
以下一些建议依赖于协作构建,因为分析师在进行分析时不需要从头开始。他们可以使用其他分析师的工作来分叉查询,学习、修改并在此基础上构建:
-
.csv文件。为提供帮助,Dune Analytics 提供了一系列关于其 Web3 数据系统的介绍视频:www.youtube.com/@dunecom。 -
创建 Increment 仪表盘:如在 第二章 中介绍的,Covalent 提供了 Increment 工具,这是一套无代码模型,旨在简化那些不熟悉 SQL 的用户进行分析。这些模型结合了维度和度量,专门覆盖 覆盖率、留存率和收入 分析。例如,留存率区域包括构建群体分析或分析多链用户基础等所需的所有元素。所有查询都可以集成到仪表盘中,并公开嵌入,如在 Notion 上。
-
创建 Flipside 仪表盘:如在 第二章 中介绍的,Flipside 允许分析师构建公开可用的仪表盘。通过超过 20 个已索引的区块链以及充分翻译的所有日志事件,分析师可以轻松查询数据。Flipside 还通过奖励系统激励分析师,社区和社交媒体上趋势上升的有用仪表盘的创作者将获得报酬。更多信息可以在这里找到:
docs.flipsidecrypto.com/our-app/analyst-rewards/top-8-dashboard-rewards。 -
创建 X(前身为 Twitter)线程与 Web3 数据分析:如前所述,开放区块链数据是许多开放供监控的 dApp 的后台。传统上,获取财务数据既昂贵又困难,且仅限于银行、对冲基金和律师事务所的分析师,这些分析师将数据转化为分析并以高价卖给客户。如今,分析师可以基于实时数据看到一流的 Web3 分析,解读趋势、揭示根本原因,并提供基于具体数据的有价值洞察,而不是单纯的猜测。数据是关键,但如果没有数据分析师从中提取洞察并转化为信息和知识,它将失去很大一部分价值。
此外,还有一些由私人公司资助的企业计划,使分析师能够展示他们的工作。公司偶尔会开展面向社区的项目,这也可以作为招聘过程的一部分。
一个最近的例子是 Nansen,这是一家分析公司,开展了一项侦察员计划,鼓励参与者完成一系列请求,特别是帮助其归因团队标记地址。更多信息可以在这里找到:www.nansen.ai/post/introducing-the-nansen-scouts-program。
寻找工作
直接寻找关注 Web3 的工作的主要平台是加密货币工作列表,这是一个专门为 Web3 机会而设的网站。它有一个特定的选项卡用于数据相关角色,可以通过此链接访问:cryptojobslist.com/data。
另一个优秀的网站是Web3.career,它提供更好的数据科学职位筛选功能:web3.career/data-science-jobs。另一个选择是www.web3creators.com/web3-jobs/data-analytics。传统的工作引擎,如 AngelList 和 LinkedIn,也发布了工作机会,但它们的提供更为多样化。
较大的公司通常在其网站上有一个职业选项卡。例如,Binance 数据部门的工作搜索发布在这里:https://www.binance.com/en/careers/department?name=Data %26 Research&job=。你可以在这里查看 Dune Analytics 的工作页面:dune.com/careers。
网络是探索机会的另一种方式,尽管可能是一条更长的道路。如前所述,在 LinkedIn 或 Twitter 上发布信息可能会很有效。你研究过的公司联系你并与你取得联系并非不寻常。此外,参与学习会议,这将在下一节中介绍,可以让你与可能为你推荐机会的数据分析师同行建立联系。
准备工作面试
这是一个简要部分,强调通过传统的数据科学资源进行彻底准备的重要性,如进一步阅读部分所述。当前的 Web3 生态系统主要由寻求具备敏锐商业感和强大数据科学及分析技能的中小型企业组成。
我们的数据面试经验的性质将根据申请的职位和公司的规模而有所不同。至少,我们可以预期会有技术(编码)挑战和案例研究。编码挑战评估的知识领域包括数据提取、处理缺失数据、机器学习(ML)技术和 Web3 数据库访问。为了准备技术挑战,我们可以利用在线问题列表、FAANG 面试模拟器以及 Python 和 SQL 技能挑战等其他资源。
案例研究涉及讨论解决所提出问题的策略或为特定情景提供建议。准备商业问题需要研究面试公司,理解其业务案例和服务,并掌握商业和财务概念。这种准备增强了与面试官的有效沟通,并促进了协作解决问题。
在下一章中,我们将展示与顶级 Web3 数据科学专家的访谈,明显可以看出,他们非常重视软技能。让我们来探索一些在 Web3 领域中特别重要的技能。
软技能的重要性
大多数区块链公司采用远程优先文化,不同地区的团队共同朝着共同目标努力。在这种环境中,招聘人员看重候选人的特定软技能:
-
独立工作的能力:这一技能意味着能够自主工作,在最少的监督和指导下完成任务。“工作做得好”的定义通常与经理达成共识,并要求具备自我激励、组织、规划和解决问题的能力。它还需要拥有良好的工作环境和有效的沟通能力。
-
强大的书面沟通能力:在远程工作环境中,大多数交流都是以书面形式进行的。因此,发展强大的书面沟通能力至关重要。
-
乐于学习新技能:在远程工作中,经理们经常引入新的数字工具来简化沟通、工作跟踪和其他任务。愿意学习如何使用这些工具非常重要,因为它们有助于我们的日常工作。此外,技术在不断发展,影响着我们的工作流程。随着模型的进步,借助对话式聊天(如 Dune,Beta 测试)或拖放模型(如 Increment 所构建的工具),执行简单查询变得可行。然而,我们学习新事物的能力以及始终寻找价值的决心没有改变。通过优先关注价值,我们确保始终对数据提出正确的问题。
-
团队合作精神:在远程工作环境中,我们往往与团队成员密切互动,有时会忽略与其他团队的联系。主动与他人沟通,保持协作氛围至关重要。作为团队成员,我们必须对自己的工作负责,承担由团队共同努力所带来的后果和回报。
-
情商(EI):情商指的是我们在职场中理解和管理自己情绪的能力。区块链领域可能充满不确定性,压力和焦虑时常伴随其间,但它也提供了真实创造的时刻,在这些时刻,之前不存在的产品被开发出来,作为分析师,我们有机会首次衡量其影响。这是一个极好的体验。评估情商是一个自我反思的过程,但我们需要在其中表现出色的特质包括:积极倾听同事的意见,愿意接受反馈,并巧妙地处理团队动态中的情绪。
-
敏捷方法:Web3 公司中的工作方式通常是敏捷的,基于灵活性、持续学习和自组织团队中的适应性。为了实现这一目标,公司会选择或测试多种方法,以找到最符合其文化的方式。诸如 Scrum、Kanban 和目标与关键结果(OKRs)等方法,可能是我们加入的公司工作方式的一部分。
学习地点
Web3 数据正在迅速增长,探索这个领域的机会充足。为了加速你的贡献,可以考虑参与各种分析公司提供的培训项目。一个高度推荐的项目是由 Covalent 团队组织的数据炼金术士项目。该项目包括四门课程,由教授指导你了解动态和最新的市场趋势。
此外,他们邀请所有炼金术士加入一个 Discord 服务器,在这里技术问题能迅速得到解答,进一步学习的额外资源也随时可用。大纲通常涵盖一系列主题,包括链与多链分析、去中心化交易所(DEX)、NFTs 和贷款。
在过去几年里,出现了其他一些培训项目,比如培养数据科学家的实习项目,所以请关注那些公司重新启动这些项目的消息。一个例子是 Dune-Resident 项目。
关于商业影响的说明
在公司、初创公司或任何组织内工作时,我们会遇到多个优先级并存的情况,因此数据从业人员必须量化任何商业数据科学项目的影响。在公司内的所有角色中,包括我们自己的项目,我们必须能够回答类似于“我们项目的投资回报率(ROI)是多少?”和“我们项目的商业影响是什么?”这样的问题。
首先,为了确定优先事项并产生影响,我们可以通过分析与公司目标对齐的商业数据科学项目来开始。如果我们无法识别我们项目支持的商业目标,那么该项目可能需要被降低优先级。一旦找到了目标,我们可以确定一位商业支持者,他将帮助我们收集相关数据、建立联系并克服障碍。
其次,必须考虑关键绩效指标(KPIs),这些指标将衡量我们项目的影响。我们的项目是否会增加我们所参与的协议中的活跃用户数量?我们项目的成功是否会帮助我们的协议增加市场份额?项目是否会提高我们服务的质量?项目是否会改善我们客户的 Web3体验?
第三,一旦我们选择了一个指标,我们需要估算我们将产生的影响百分比。将我们项目的影响转化为商业语言将帮助我们领导成功的事业。
有很多指导方针教我们如何量化商业数据科学项目的影响,我们在进一步阅读部分列出了一些资源。
总结
总之,本章深入探讨了在 Web3 环境中进行 BUIDLing 的重要性,以释放价值并创造机会。我们回顾了建立作品集的重要性,特别是数据分析方面。章节还探索了专门的求职引擎,招聘人员在这些平台上发布相关机会,同时,求职者可以在这些平台上了解 Web3 数据科学的趋势,保持市场竞争力。
此外,我们讨论了候选人在 Web3 数据科学面试中可以预期的内容,涵盖了技术评估和业务评估。章节还提到了在远程优先行业中成功所需的关键软技能。
进一步阅读
以下是你可以回顾的全面资源列表,以深入了解所涵盖的主题:
-
Skiena, S. S. (2017)。数据科学设计手册。Springer。(第十三章)
Skiena书中的第十三章启发了本书的附录部分。它是我们完成数据科学学习后,“接下来该做什么”的答案。
-
Dalton, S. (2012)。2 小时求职法:利用科技更快找到合适的工作。Random House Digital。
一种寻找我们热爱的工作的系统方法。这是一个一步步的过程,能帮助我们将求职这一本身可能混乱的活动加以有序化。
-
avcontentteam。(2023 年 5 月 10 日)。如何准备 2023 年的数据科学面试? Analytics Vidhya。
www.analyticsvidhya.com/blog/2023/04/how-to-prepare-for-data-science-interview/ -
DataCamp。(2022 年 12 月)。数据科学面试准备。在线学习数据科学与人工智能 | DataCamp。
www.datacamp.com/blog/data-science-interview-preparation -
Neeley, T. (2021)。远程工作革命:从任何地方成功。Harper Business。
一本非常适合管理者的软技能书,尤其是那些在远程工作环境中领导并努力取得成功的管理者。
-
Goleman, D. (1995)。情绪智力。Bantam。
情绪智力指导的黄金法则:正确地利用我们的情绪以创造积极结果,避免受我们自身情绪的困扰。
-
数据炼金术士训练营第二季。(2022 年 6 月 18 日)。Covalent。
www.covalenthq.com/data-alchemist/ -
加密货币播客列表:
cryptojobslist.com/blog/top-crypto-podcasts-career-web3 -
你如何衡量你的数据分析项目的影响? (2023 年 6 月 26 日)。LinkedIn。
www.linkedin.com/advice/3/how-do-you-measure-impact-your-data-analysis-projects -
量化你的数据科学项目的商业影响。(2022 年 2 月)。Towards Data Science, Medium。
towardsdatascience.com/quantify-the-business-impact-of-your-data-science-project-b742e4b3208f
第十四章:与 Web3 数据领域领导者的访谈
当那婴儿最终找到了他的母亲时,我完全明白他的感受。
—— Sheryl Sandberg(《Lean In》)
Jeff Olson 在他的书《The Slight Edge》中专门有一章强调了从已经取得成功的人那里学习的重要性。这个概念通过下图进行了说明:

图 14.1 – 学习轮(改编自:《The Slight Edge》,第 192 页,第十三章,向导师学习)
上面的图表显示,学习不仅仅是阅读和实践的结合;它还包括从该领域专业人士的经验中汲取洞见。
虽然这本书一直将理论与实际练习相结合,但还有第三种学习方式,叫做 通过建模学习,我们将在本章中探讨这一方式。
过去,追求某种职业的人会在该领域的大师指导下学习,向拥有第一手经验并能传授真实知识的人学习。秉持这一理念,我联系了一些 Web3 数据科学领域的领军人物,寻求他们对该行业过去、现在和未来的看法。
Hildebert Moulié(又名 hildobby)
数据可访问性为我创造了一个新工作。
Hildobby 是 Dragonfly 的数据科学家。他的 X(前身为 Twitter)账户可以在 twitter.com/hildobby 找到。
Gabriela:你能否向我讲述一下你的职业经历,并突出那些在加密领域中塑造你当前专业知识的最重要经历或角色?
Hildebert:目前,我在一家名为 Dragonfly 的风险投资公司工作,(www.dragonfly.xyz/),该公司专注于投资与加密相关的公司。我是团队中的数据科学家,我认为我进入这个领域的方式非常非传统,这让我感到非常高兴。我现在开始讲述一下是什么让我走到这里。在我获得本科学位后,我希望能积累一些实际经验,以明确我未来想做什么,于是我有机会加入一家名为 Kaiko 的公司,这是一家由家庭成员经营的加密货币中心交易数据公司。我得到了被雇佣的机会,刚开始我是那个令人烦恼的实习生,大家雇我只是因为我是小表弟,但最后发展得非常好,我也非常喜欢在那里工作。我还学到了很多关于加密货币领域的知识,吸引我持续关注这个领域的,绝对是这个生态系统的 精神 和意识形态,任何人都可以以自己的方式做出贡献。
当我的父母说服我去读硕士学位,而不是直接工作时,我去了阿姆斯特丹。我攻读的是计算科学硕士,这基本上是建模方面的内容。在学习的同时,我在一家奶制品数据公司找到了工作,虽然这份工作非常有趣,但主题对我来说并不有吸引力,如果你能理解的话。这个行业对我来说并不最具吸引力。它是一个极其慢节奏的行业;几乎没有什么发生,你懂的;至少对我来说,它并不令人兴奋。
所以,当 COVID 封锁来袭时,像很多人一样,我感到无聊,想重新进入加密货币领域,我心想:“我怎样才能以自己的方式贡献,或者至少更好地理解整个事情?”实际上,我是想先理解并玩一玩。然后我找到了Dune analytics (dune.com/home),在这里我不需要运行自己的基础设施,只需关注从数据中提取洞察。我在 Dune 上玩了大约 9 个月,匿名地在 Twitter(现在是 X)上分享。我想向自己证明,重要的不是我是谁,而是我分享的内容。最终,有些人开始联系我,提供自由职业的工作,发生得越多,我就越考虑放弃学业,专注于这个项目,全职做下去。这是一个非常困难的决定,因为我的家人非常反对。我知道如果我这么做,我就会全身心投入这个项目,我已经处于一个有很多自由职业工作安排的阶段,我的整周时间已经排满了。我赚到了钱,是的。更酷的是,Dune 还支持我成为Resident Wizard,这是一个两年前启动的项目,基本上帮助我能够发布数据,而不必担心获得资金,并给了我自由,专注于那些没有人愿意直接付费研究,但大家都有些兴趣的话题。例如,整个市场在某个行业中的表现如何,类似的问题。我很享受这个过程。
我一直在做一些自由职业的工作,后来我最终想加入一家公司,能够做同样的事情,但不需要担心组织问题,可以与人一起做项目,只需要专注于数据。我在自由职业中看到的请求的一个特点是,付费分析的公司往往在数据中有偏向,他们希望看到的内容,我认为当金钱直接与这个方面挂钩时,很难做到客观。所以,我很高兴我最终有机会在 2022 年 7 月加入 Dragonfly,成为一名数据科学家,差不多是一年半前的事情。你的兴趣爱好是有可能变成全职工作的。
加密货币非常强大,因为它将个体置于聚光灯下,而不是那些已经成名的大公司;任何人,只要贡献得当,都可能在这个领域产生一些影响。不管你是谁,来自哪里,这都非常强大,因为你可以成为自己的创造者,得益于加密货币将数据透明度提升到了一个全新的层次;数据是公开的,一切都以不同的方式运作。Dune 就是其中的一部分;现在任何人都可以查看数据,Dune 让它变得更简单,让每个人可以专注于从数据中提取价值,而不是需要关注后台的事务。此外,它已经成为一个寻找加密分析的好地方,就像我们寻找视频时去 YouTube 一样。
Gabriela:你认为 Web3 的数据科学是一个小众领域吗?它会一直保持这样吗,还是加密数据会扩展到其他应用场景?你认为未来会有哪些其他方使用我们的分析结果?
Hildebert:我认为加密货币已经到了一个阶段,它有扩展的计划,并且已经非常有用,也许不是在你最初想到的常规应用场景中,但以稳定币为例。稳定币对于那些无法轻松拥有银行账户或抵御通货膨胀的国家来说是一个重要解决方案。它提供了一种无需第三方的交易方式,并消除了现有系统中存在的潜在费用。
与现有系统相比,加密货币行业有很大的效率提升空间,我认为我们已经达到了一个具有巨大潜力的技术阶段,但它目前处于类似于 90 年代初互联网的发展阶段,可能我们并不完全了解它是什么,但即使是那些初步的探索,你也能看到它的使用价值。当时,仍然可以看到有人在问“如果我能发信件,为什么还需要电子邮件?”对于一些人来说,这可能感觉像是一种潮流,最后这个行业会找到自己的应用场景,就像今天的社交媒体一样,已经变得非常庞大。我认为这是一项需要一些时间来理解的技术,我们将看到它如何发挥作用,许多行业都可以从中受益。
再举一个例子,Spindl (www.spindl.xyz/),这是 Dragonfly 投资组合中的一家公司。我与他们有着密切合作,我总是对他们正在开发的新东西感到兴奋。如今,区块链广告充满了欺诈行为,这主要是因为它很难做到,因为 Web2 和 Web3 之间没有连接,缺乏像 Google Ads 这样的服务,无法提供广告表现、目标受众、哪些有效和哪些无效的视图。这些信息对行业非常有价值。
我们现在正在建设扩展所需的基础模块。要让这些基础模块作为基础运作并完成整个系统是需要一些时间的。我不知道十年后会是什么样子,但我不认为六年前有人能预见到我们现在所处的位置。我认为没有人能预测那种浪潮的到来;它们只是当技术成熟时自然发生的。
Gabriela:加密生态系统中有哪些发展引起了你的兴趣,特别是在其潜力方面,能够吸引下一个亿级用户?
Hildebert:在我看来,这不一定是某个具体的东西,而是更广泛的,是整个系统新概念的一部分。与现有的系统相比,我认为加密货币有潜力取代那些目前需要第三方参与的结构。它们将被抽象化或移除,并且这将影响费用和成本,而这些通常倾向于朝着“低价竞争”的方向发展,这很有道理,因为它一切都是为了提高效率。归根结底,用户才是真正的赢家,因为你最终得到的费用是合理的,而且完全有可能有人出现并以更好的产品或更低的价格接管。这种方式有助于改善竞争。我想对此我感到相当满意。
另外一个我想强调的特点是加密货币的跨境特性,它真正将世界连接在一起。我想国际支付是一个很好的例子,展示了现在的正常、无摩擦的服务,而在某些地方这可能并不容易,而这项技术在这方面确实帮助很大。你知道,用加密货币做国际支付要便宜得多,而且你不需要任何人批准收款,只要有互联网和钱包地址就行。
数据的透明性使得竞争格局更加清晰,因为一切都是公开进行的,并且至少在公开区块链上可以公开分析,而且有多个竞争者进入,看看是否有某种角度能够让之前的人插手并说“好吧,我们认为可以通过降低费用来获得成功”,而在这种地方每个人都能获益。
要真正产生影响,教育和监管是必要的。我认为良好监管的加密货币将是非常棒的,我相信我们最终会实现这一点。总的来说,我对这两个方面感到兴奋:费用和跨境支付。
Gabriela:考虑到 AI 的持续进展,普遍认为 AI 正在超越知识工作。在你看来,我们应如何适应这种进展并进行转变?最重要的是,在这个不断变化的环境中,你认为有哪些新兴机会?
Hildebert:我认为 AI 使得智力工作能够处于平等的地位。我们每个人都需要以自己的方式得到帮助,而这正是 AI 所做的。我认为它让你将正在做的事情推向更远的地方。以数据为例,现在,对于基本的数据分析,你不一定需要有人去查看它,因为 AI 能够执行好的模型来理解数据,并且它的输出是可靠的。因此,分析师们可以(现在这个问题已经解决)进一步推进研究,真正把研究推进一步。它远不是让我害怕它会取代我工作的地方,因为我认为它只是推动了我们,而不是替代了我们。
Gabriela:如果有人想和你合作,你希望在他们的个人资料中看到什么?软技能(独立工作能力、团队合作、情商、敏捷方法)和硬技能(工具**和技术)?
Hildebert:我认为这非常重要,尤其是在所有公司都远程工作的情况下,你必须具备独立性。我想和一个独立的人合作,我不希望总是需要在别人背后,因为如果这样最终浪费了我太多时间,我们就会失去讨论的部分。我想和你讨论,我很看重别人挑战我所知道的东西。我特别喜欢那些不一定和我意见一致的人。正是这种冲突产生了真正好的对话,我认为这比那些大家都同意的对话要好,因为从中你不一定能获得价值。这个行业更多的是关于每个人交付的内容,而不是大公司开着大量的会议,像回音室一样运作,更多的是聚焦于每个人可以带到桌面上的东西。
我的建议是关注工作和成果,而不是工作时间或以一种标准的 Web 2.0 正式公司方式来监控每个人。我认为最酷的是个体和这个人能带来什么。我认为我们每个人都有自己的技能,能为团队贡献东西,就像有不同形式的智慧一样,你知道的,有些人擅长写作,有些人擅长编码,有些人擅长运动,大家共同合作,创造出优秀的产品。
关于硬技能,我重视理解加密货币是什么以及行业。你不了解数据,直到你了解数据背后的东西。一个行业与另一个行业截然不同,而一个行业中重要的东西可能在另一个行业中不起作用。这也是为什么,当你制作仪表盘时,你要首先展示那些有趣的内容。理解市场可能比编程或其他任何事情更重要。它会让你知道自己是否能够阐明最重要的东西,并且首先展示它。
讲故事也很重要。当我查看仪表盘时,我希望能看到最重要的信息。我应该能够仅凭一两个图表就评估我所看到内容的表现,如果我有兴趣,随时可以深入探索。良好的展示技巧对于数据科学家来说至关重要,因为许多优秀的工作因展示得非常糟糕而被埋没,而许多东西则因人们擅长营销而被推向前台,实际上这些工作并没有太多实质内容。因此,总结来说,对我而言,行业知识和展示技巧的良好结合是非常必要的。
对我来说,一个实际的招聘建议是,我根本不在乎你的简历。对我来说更重要的是你知道自己能带来什么。要创造价值,理解技术和区块链领域是非常重要的,然后你不能没有实践就到达那里。我认为到达那里最好的方法就是开始。如果你感兴趣,你需要开始,你最终会成为专家。我认为,如果我看看我认为在任何行业中成功的人,那些人都是不断尝试的,而他们很少在第一次尝试时就成功,但他们会一直尝试。我想和那些我可以说“我看过你的作品,觉得很有趣”的人一起工作,而且这是我没见过的,或者你确实带来了某些东西。这并不是来自于去一所不是每个人都能接触到的好学校。就像我说的,整个加密领域让我们站在了同一起跑线上。证明你创造的价值,而不是给我看你的学术资历。
Gabriela: 你对那些正在学习 Web3 数据的人有什么建议?对那些想要从其他行业转到 Web3 的人有什么建议?
Hildebert:就像我之前说的,尝试新事物。尝试新事物通常能解锁你能接触到的人和你能够接触到的群体,因为他们也关心你在做什么。在这个领域里,当你提出有趣的问题时,人们会很乐意帮助你。在这个尝试阶段,我建议联系那些(你不一定能及时得到回应的人),但是如果你能带来一些新的东西,并且有非常有见地或有趣的问题,那么他们更有可能联系你。
另外,建立声誉,尤其是在加密数据领域;当我查看仪表盘时,我没有时间深入挖掘每个人的代码并区分信号和噪声,建立信任需要一些时间。但是,如果是 Michael Silberling(twitter.com/MSilb7)或 Chuxin(twitter.com/chuxin_h)发布的内容,我知道他们已经赢得了我的信任,因为我已经多次看到他们的作品,并且知道他们遵循最佳实践。在本书的某一章中,有提到目前尚未形成稳定的标准。这是事实,分析师必须准备好进行迭代。区块链数据是一个迭代过程,与我想象中几年后能够实现的相比,我们目前才处于初始阶段。
此外,这突显了整个预处理部分的重要性,因为通过清理数据可以获得洞见。我去年工作的一项内容是 NFT 交易以及洗盘交易标准是什么(编辑注:该分析在第四章中提到)。如果你以原始形式看待交易,它的活动非常零散,但如果你能够清理掉有机活动并过滤掉那些无机活动,就有可能得到更干净的数据,从中提取出更多的洞见。从这个角度来看,仍然有很多工作要做,可能有多年积压的任务,因为有太多的领域需要调查。
我认为一致性和声誉是密切相关的。必须持续提供精准的分析,因为如果你发布了误导性或不准确的数据,你的声誉就会受到打击,我也不再信任你。我们都犯过错误,我也犯过很多错误,但重要的是要保持透明,出错时道歉并澄清,提供一个修正后的版本。没有人能对一切拥有完美的视野;这本身就是一个迭代过程,但只要你重视透明度,我们就能共存。这是一个透明的系统,我认为系统中的人也应该保持透明。用户没有时间去验证一切;随着时间的推移,他们最终会学会信任。
我们的工作是将复杂转化为简单,正如我之前所说,过高的复杂度会让很多内容丢失。要能够简化它,就必须消化数据,真正理解其中的复杂性才能进行翻译。我通常会从一个高层次的理解开始,然后逐步深入。这或许是最好的方式,因为你可以满足每个人的需求,而不是直接进入细节,那样可能会让人困惑。
对于仪表盘来说,钩子非常重要,而钩子由重要的数据组成。在 YouTube 上的视频也是如此。当人们进入你的仪表盘时,实际上你是在“偷取”他们的时间,因此你需要确保他们花的时间是值得的。如果你不去优化你的钩子,他们就不会坚持下来,去观看你发布的所有内容。钩子非常重要,之后你可以深入讲解,但现实情况是,90%的人只想看到高层次的分析,剩下的 10%才会深入研究,像是到操作层面。我们如何制作最佳的钩子呢?这是一个反复试验的过程,我每次都会稍微尝试不同的方式,现在它已经变得极其简单了,比如一句话和我想发布的主要图表。这个想法是,如果分析师想了解更多,他们可以去浏览线程,但整体的思路已经非常简洁地呈现出来了。
Jackie Zhang
我们是一个非常适应的物种。
Jackie Zhang 在 Dune Analytics 担任开发者关系的角色。她的 LinkedIn 可以在www.linkedin.com/in/jackieyingzhuzhang/找到,她的 X(前 Twitter)账号是twitter.com/agaperste。她还是Journey of the Unordinary频道的主持人,该频道可以在www.youtube.com/@JourneyofTheUnordinary找到。
Gabriela: 你能带我回顾一下你的职业历程,并突出一下对你目前在 加密领域的专业知识影响最大的一次经历或角色吗?
Jackie: 我会从我现在的位置开始,然后倒回去看我是如何到达这里的。我的职位是 Dune Analytics 的开发者关系(dune.com/home)。Dune 是一家加密数据公司,所以这就是加密领域的由来。而且公司由一个小团队组成,因此我有机会深入思考产品以及我们如何销售和发展。我想你们已经可以看到我对加密与数据、产品与社区的桥接的兴趣。如果你要让我定义自己,我就像一位桥梁建设者,我对这个角色感到非常满意。
回到是什么促使我走到今天这一步,在大学时,我学习了计算机科学和金融,大学毕业后我在德意志银行担任软件开发员。我很快意识到,我想在工作中做一座桥梁,即使是在软件开发的角色中。我擅长连接内部用户,架起需求和代码之间的桥梁。还有一个方面是,它让我思考“这就是我想做的事”,这对我来说更具个人意义,因为很长时间我都没有意识到这一点。
我来自非常传统的中国父母,他们会给你关于应该做什么的指导,尽管我想学习国际关系,但他们建议我学计算机科学,因为学计算机科学找工作更容易。我做了,但是在美国生活了将近十年后,我仍然面临签证问题。所以,我当时面临这个签证问题,我要么被公司派往伦敦,要么得做点别的事情。所以,我决定回去读研究生。我已经知道自己想从软件开发转型,选择了数据科学,它更接近商业领域,毕业后我在富达公司找到了一份常规的数据科学工作。说实话,那一年我做了很多 Web 开发工作,在那里时也是如此。
我很幸运遇到了我的丈夫,通过我们的婚姻解决了我的签证问题。然后我第一次感到,我有了思考自己真正想做的事情的自由。我其实不知道怎么过多地质疑自己想做什么或者我热衷于什么。所以,我通过说“好吧,我就看看我最终会把大部分时间花在哪里”来解决这个问题。这就是加密货币兴趣开始的地方。它已经是一个主题,我会花很多时间深入了解,去探索。这是我所有空闲时间投入的地方,我意识到自己从未有过这样的吸引力。最开始,我只是想做这件事,然后最终我不得不全职进入加密货币领域。真正让我兴奋的是,能够更好地分配世界资源的承诺。我内心对加密货币理念有一种推动力,但与此同时,我喜欢使用开放的加密数据,并且能够创造利益,使它变得更加公平。拥有了技术能力,让我能够转型并在我感兴趣的业务中担任角色,这让我非常喜欢它的精神。它是一种理念,然后我意识到我做这件事时是快乐的。
我认为当前找工作的方式已经在慢慢发生变化。不再像以前那样“哦,我投简历然后走传统流程。”而是你先为协议工作,最终被聘用。
Gabriela:你认为 Web3 数据科学是一个小众领域吗?它会一直保持这种状态吗,还是加密数据会扩展到其他使用场景?你认为未来还有哪些其他方会消费我们的分析?
Jackie:好,第一个问题很简单:我们目前确实处在一个小众领域。第二个问题,简短的回答是,只有时间能告诉我们答案。Frederick(Dune 的 CEO)实际上在 DuneCon 上提到过这个问题,他引用了 Steve Jobs 的一句话:
“…人们问我,‘为什么我要在家里买台电脑?’”
…嗯,就是为了了解它,做一些有趣的模拟。
…但除此之外,现在没有什么好理由去为你的家买一个。
但会有的,会有的。

图 14.2 – 来自 2023 年 11 月 2 日里斯本 DuneCon 的照片
时间会证明,我希望会证明。我认为像您这样的行业人士有信念,但您的信念总是带着一种飞跃式的信任。但我已经看到朝这个方向发展的实际数据。我不知道未来会怎样,但如果从大局来看,我认为比特币 ETF 是真实存在的。我不认为我们提到过 adoption(采纳),但越来越多的人在听说它,去年人们的看法更为负面;而现在,也许是更加中立的态度。它在未来如何被采纳,可以通过广告、效果营销以及 Spindl(www.spindl.xyz/)正在做的事情。我很期待看到他们更多的行动。
Web2 是一个高度封闭的领域,尽管有许多内容应该保持私密,我认为我们可以做得更多,在这个领域提出更多的解决方案。如果我们能够抽象出像区块链这样复杂的底层技术,也许可以朝着消费者在应用中所需要的方向发展,技术对他们来说是透明的,我认为这样会有更广阔的前景。
Gabriela:在加密生态系统中,哪些发展引起了您的兴趣,尤其是它们在吸引下一个 十亿用户方面的潜力?
Jackie:基本上,我们还不知道,有很多努力在寻找答案。我仍然认为我们处于早期阶段,因为当你仔细想想,要采纳一个产品需要两个因素。你需要有动机去做,然后你需要有能力去做。
我认为今天,我们正处于一个区块链作为高通胀国家的价值储存工具,或者作为受制裁国家的跨境支付手段的世界,但除此之外,除了现有的麻烦之外,似乎没有什么其他动机让你去经历现在加密货币的复杂性。我看到一些聪明的人早早进入这个领域,试图进行套利,就像做钱的交易员。我还读过有关期权交易员的内容,区块链使他们能够比以前更轻松地进行操作。即便如此,面对开放数据,我们仍然没有让这些非常聪明的人得到他们原本无法获得的机会,所以我对这些想法持看好态度,但我不确定这些极具动力和能力的人是否代表了下一个十亿用户的群体,许多人在生活中仍面临自己的困境,如何获得下一餐等问题。总之,我认为吸引下一个十亿用户的解决方案与日常问题有关。它不涉及新功能或类似的东西,而是服务必须解决人们的日常问题。
Gabriela:考虑到人工智能的持续进步,普遍认为人工智能正在超越智力工作。您认为我们应该如何适应这一进展并做出转变?最重要的是,您认为在这个 变化中的新机遇在哪里?
Jackie:我认为,直到我们拥有通用人工智能,机器人真正接管世界之前,我认为我们不必担心什么,因为我们是一个非常适应性强的物种。如果你想想看,最初人们是不能写字的,对吧?所以,抄写员有很多工作,但后来每个人都学会了读写,抄写员不再需要了,但其他工作出现了。另一个例子是女性,她们曾经花很多时间洗衣服,然后洗衣机发明了,女性开始大规模地为市场创造价值。我只是觉得一切都会好起来的。在短期视角下,我们仍然需要很多分析师来写好的 SQL,以训练 AI。例如,以 Dune AI 为例,你需要有人能够写好查询,然后将它们输入到这个模型中并评估结果是否正确。所以,是的,我认为在短期内,我们仍然需要写 SQL 的人,然后当我们到达不再需要写 SQL 的阶段时,拥有区块链数据知识的人将会没问题,因为那时每个人都需要从数据中提取洞察等等。就像现在每个人都能读书一样,SQL 也会经历相同的过程。人类将会进入下一个阶段。我认为我们会完全没问题,变得更好、更高效。
Gabriela:如果有人想和你一起工作,你希望在他们的个人资料上看到什么?软技能(独立工作的能力、团队合作、情商、敏捷方法)和硬技能(工具**和技术)?
Jackie:关于软技能,我认为独立性的另一个方面就是依赖性。这意味着一个人会出现,并且你可以信任他们。如果他们做了他们说会做的事情,我会信任他们。此外,内在驱动力也很重要。你无法真正评估热情之类的东西,但完成事情的驱动力,因为这表明他们对这件事感兴趣。另一个软技能是沟通能力,基本的沟通能力,但也包括跨部门协作的能力,比如能够与不同的人、不同的部门交流,并努力让大家一起工作。你必须能够确保每个人都互相理解,明白需要交付的内容、方向和如何影响他人,使他们愿意与你一起前行。这就像是以沟通为基础的领导力。学习能力,好奇心和学习能力,因为你总是可以尝试新事物。
在硬技能方面,我会加上数据敏感度,意味着知道该问哪些问题,我认为这来自于经验。然后是常规技能,比如 SQL、Python 和行业知识,这些都是相当标准的。发展软技能很重要,因为你总是可以学习新东西。
Gabriela:你对于正在学习 Web3 数据的人有什么建议?以及对于想从其他行业转向 Web3 的人,有什么建议?
Jackie:我觉得我们已经提到过这个了,但就去做吧,去尝试吧。兴趣会像自然流动一样,一步接一步地来。不要强迫自己。
同时,你需要保持一致性。Andrew、Hildobby 和 Coby 之所以能够保持影响力并继续做大,是因为他们始终产生有价值的内容。他们不是做一次热门内容然后就离开。
此外,特别是对于从 Web2 转向 Web3 的人,我建议专注于学习加密知识,因为分析技能已经足够在 Web3 中表现出色。这个领域的数据成熟度仍然不高,所以他们现有的技术分析技能可能就足够了。我希望更多来自 Web2 的有经验的人加入 Web3,让这个领域变得更加成熟,因为我认为我们的人手还不够,而且还有很多事情要做。这是一次邀请,请加入我们。这个世界如此开放,可以做的事情非常多,而且非常友好。想象一下,在这个领域,有很多相互连接的大团队在与您共同解决问题,而不是像 Web2 中那样,一支由 5 名数据人员组成的小团队,每个人只专注于自己的任务。此外,在 Web3 中,一旦完成了工作,你就可以在别人已经构建的基础上继续构建。这种可组合性的理念在这里非常突出。
简洁明了的仪表盘非常重要。大多数时候,用户看一到两个图表就会离开,对吧?这就像是一个 30 分钟的 PowerPoint 演示文稿。除非它仅仅是关于数据,否则他们能真正记住多少内容呢?专注于制作易于理解的统计数据。它们必须简单,否则信息会丢失。
Marina Ghosh
无论你是出于好奇想要探索资源,还是准备进行全面的职业转型,你都不必单打独斗!
Marina 是 Flipside Crypto 的社区关系顾问,同时也是 MetricsDAO 的董事会成员和贡献者。她的 X(前身为 Twitter)账户是 https://twitter.com/queriesdata。
Gabriela:能否带我走一遍你的职业历程,并重点讲述一下在加密领域塑造你目前专业能力的最重要经历或角色?请从简要描述你目前的角色开始。
Marina: 在我的工作中,我支持区块链分析社区中的数据分析师们发展他们的技能,产生对 Web3 有价值的开源洞见,并将他们的技能和热情转化为充实的职业生涯。与 Web2 中的数据不同,Web3 数据不是专有或需要付费的,这创造了一种独特的方式供任何人参与其中。结果就是在链上数据周围形成了一个狂热爱好者和专业人士的生态系统。这正是我开始这条道路的方式:通过接触这个生态系统,成为这个社区的分析爱好者之一,并制作了大量的仪表板!
开源区块链数据分析可以为个人职业发展带来显著的向上(或者说横向,如果你在转行)机会。对于那些对区块链充满好奇,并有兴趣通过学习入门级数据分析技能开始的人来说,他们会发现自己有无限的主题可以探索,同时专业技能会变得越来越复杂。学习如何处理描述实时 Web3 初创企业和社区的实际数据,会比仅仅下载模拟或经常使用的公共数据集进行练习感觉更加有意义。从一开始,你就可以创造出实际的价值:发现能够帮助协议在业务决策中找到洞见,参与关于资本分配的对话,并帮助社区更好地了解他们喜爱的协议。对于想要在 Web3 数据职业生涯或与数据相关的职位(如产品、客户或社区成功)中找到突破口的人来说,这种影响力在他们的求职申请中非常有帮助。但与此同时,这也在价值转移方面创建了价值,Web3 项目为社区分析师补偿创造的价值——可以想象成自由职业请求、追溯式补助金,以及分析奖励和激励计划。
我通过参与类似的活动更深入地了解了这个行业,并对它充满了热情!(除了追溯式补助金,这是我个人的愿望清单,作为分散自治组织(DAO)团队的一部分,我还没有获得过)。现在,我已经开始与 Flipside 和 MetricsDAO 等组织合作,最初我作为 Web3 分析师社区成员与它们有很多接触点。
Gabriela:你认为 Web3 数据科学是一个小众领域吗?它将保持这种状态还是将扩展到其他用例?你认为未来会有哪些其他方面的人群在消费我们的分析?
Marina:这是一个足够大的领域,当你是其中一部分时,感觉它几乎是吞噬一切的!说正经的,我认为一个有趣的交集是现实世界资产(RWA)。现在,像耐克和星巴克这样的公司正在将 Web3 元素加入到它们的商业模式中,任何人都可以通过链上数据查看它们这一部分业务的成功程度(这些公司反过来也需要加密数据专家)。体育也是另一个应用场景:忠实的粉丝可以从试图评估他们实体交易卡收藏的价值,到查看链上数据了解他们的体育 NFT 收藏品的价值。游戏产业中通过游戏内购买也在拥抱加密技术,并因此可以通过区块链数据获得更多的洞察。
Gabriela:在加密生态系统中,哪些发展引起了你的兴趣,特别是它们在吸引下一个十亿用户方面的潜力?
Marina:我最近在 Flipside 博客上分享了我对这个话题的看法(data.flipsidecrypto.com/blog/new-kid-on-base-network-effects-could-onboard-the-next-billion-into-web3)!为了帮助加密生态系统实现雄心勃勃的用户引导目标,我认为倍增效应和网络效应将创造出比线性增长更快的增长。SocialFi 帮助 Base 最近成功吸引了大量用户,这与 Web2 的社交网络相似,你会加入其中来关注你早期采纳的朋友,然后更多的朋友会注册来关注你,依此类推。另一个倍增器是开发者:那些专注于引导开发者并提供优质开发者体验的协议,将会看到一些开发者创建的应用程序脱颖而出,吸引大量用户。那些旨在成为不太稳定经济环境中日常金融替代方案的项目,也有潜力利用网络效应。例如,一个向家乡汇款的移民工人如果使用稳定币汇款,他们将引导收款人进入 Web3。
Gabriela:考虑到人工智能的不断进展,一般人会认为 AI 正在超过智力工作。你同意吗?在你看来,我们应该如何适应这一进程并做出转变?最重要的是,在这个变化中的环境中,你认为有哪些新兴的机会?
Marina:举个例子,AI 可以帮助你修复 SQL 查询,但它也可以帮助你学习一门新的编程语言或库,你将用它来编程。撇开编程不谈,解释和从区块链数据中得出结论是非常微妙的,因此更适合人类思维。加密数据输出远未标准化,即使未来这一方面得到改进,从数据中提取有意义的结论仍然需要大量上下文(而这通常需要人类)。
Gabriela: 如果有人想和你一起工作,你希望在他们的个人资料中看到什么?软技能(独立工作能力、团队协作能力、情商、敏捷方法)和硬技能(工具和技术)?
Marina:我将为那些想要进入区块链数据分析领域的人回答这个问题。首先,构建数据分析(以及与之相关的领域如数据科学或分析工程)的技术基础,是当今一个资源丰富的事业。现如今,有许多资源(其中许多是免费的),包括书面、视频、社交媒体和互动格式,提供了技能列表以及帮助学习和练习这些技能的材料。而更为难得,但完全可以实现的力量,是建立你自己作为一个深入挖掘、提供优质 Web3 洞察的人的声音和形象,并且培养你的网络和社区(甚至是一个观众群体),他们会发现这些洞察有趣且有用,参与讨论,提出请求,并提供反馈。积极融入社区并理解数据问题与需求,是区分有影响力 Web3 分析师的关键。这需要好奇心、专业性与友好性,以及不断投入精力来关注 Web3 及其细分领域和项目,建立关系,开展对话,并时刻思考如何通过数据驱动的问题为大家带来价值。
Gabriela: 那么对于那些想要从其他行业转型到 Web3 的人呢?
Marina:无论你是出于好奇想要探索资源,还是准备进行彻底的职业转型,你都不需要单打独斗!相反,加入社区,与大家共同前行。这将帮助你在许多方面的旅程中,从找到资源、解答你的问题、认识处于类似 Web3 数据熟悉阶段的他人,到建立同行和有经验的区块链数据专业人士的网络。幸运的是,已经有多个专业化的社区存在。你将会找到与你选择的加密数据工具或服务提供商(如 Flipside)相关的资源和社区;MetricsDAO 是一个与工具无关的中心,汇聚了许多链上数据专业人士、爱好者以及学习资源;Crypto Data Bytes 在 Substack 上提供了大量的教育材料;还有一些发布作品的加密分析师社区,比如 OurNetwork。阅读是寻找灵感和结识数据专业人士的好方式。带着你的好奇心和友善,你会发现自己融入了一个支持你成长的社区。
One Digit 教授
区块链不是传统的数据库。分析师不会向其写入数据或对其进行更正。
One Digit 教授是Sovryn的数据科学家。他的 X(前 Twitter)账号可以在twitter.com/onedigitmoney上找到。
Gabriela:您能为我讲述一下您的职业历程,并突出您在加密领域塑造当前专业知识的最重要经验或角色吗?请从简要描述您的当前角色开始。
One Digit 教授:我目前在 Sovryn 担任数据分析师和技术传播者的角色。这两个角色是相辅相成的,因为每一部分都会影响到另一部分。我以一种不同寻常的方式进入这个角色。我在学术界作为工程学教授工作了超过 30 年,后来加入了 Sovryn,并从一个纯粹的技术传播角色逐步发展到现在的职位。我对高阶数学、数学建模和编程非常熟悉,也有丰富的技术传播经验。我当前角色的具体内容与我之前的职业经验有很大不同,但我的背景为我提供了基础和信心,使我能够发展到这个角色。
Gabriela:这种情况会保持不变,还是加密数据会扩展到其他应用场景?您认为未来还有哪些方方面面会使用我们的分析?
One Digit 教授:我对这个问题没有完全形成定见。我的总体看法是,加密数据分析本质上与其他数据分析没有什么不同。链上分析开辟了数据分析的新应用领域,并激发了许多创造性的分析指标。然而,方法上与传统分析方法类似。我可以看到,未来加密分析将在链上取证、以及交易和投资决策分析中发挥更大的作用。
Gabriela:在加密生态系统中,哪些发展引起了您的兴趣,尤其是在它们能够吸引下一个十亿用户的潜力方面?
One Digit 教授:我对比特币上的 rollups 非常感兴趣,特别是那些可以使用像 BitVM、见证加密或权益证明第二层等方法,将比特币无信任地绑定到比特币之上的更灵活层。这很可能是解决扩展性问题的一种方案。
Gabriela:考虑到人工智能的持续进展,普遍存在人工智能在智力工作领域超越人类的看法。您同意吗?在您看来,我们应该如何适应这一进程并进行调整?最重要的是,您认为在这个变化中的格局中有哪些新兴机会?
One Digit 教授:它使得理解语法或调试代码变得更加容易,但有时也能让我不被细节所困,专注于高层次的问题。人工智能能够帮助的一个领域是分析代码库并描述系统的功能,或者能够回答有关系统的问题。另一个领域是识别那些在对代码功能的初步理解中并不显而易见的漏洞。
Gabriela:如果有人想和你一起工作,你希望在他们的个人资料中看到什么?软技能(独立工作能力、团队合作精神、情商、敏捷方法)和硬技能(工具**和技术)?
教授 One Digit:同时,还需要具备解决新问题的能力和愿意使用不熟悉的新工具。
Gabriela:那么对于那些想从其他行业转行进入 Web3 的人呢?
教授 One Digit:你需要了解 Web3 的动机和文化。这意味着理解我们为什么要追求去中心化、无权限等。否则,很难理解或欣赏数据及其含义。理解区块链的基本理念和结构是必须的。区块链不是传统的数据库。分析师不会向其中写入数据或修正数据。进入这个领域的人还应该了解比特币、以太坊与其他山寨币的子文化和态度。你需要在一个与你对世界未来走向的哲学相符合的领域工作。花时间找到一个你相信会使世界变得更好的项目,而不仅仅是一个能支付你工资并让你做酷事的项目。
附录 1
让我们开始安装以下环境。
Google Colaboratory
-
前往你的 Google Drive 并打开一个 Google Colaboratory 文档。
-
点击连接:

图 A1.1 – 连接 Colab
- 它会显示初始化、分配、连接,然后已连接:

图 A1.2 – 已连接
- 如果你点击查看资源,它会展示你正在使用的计算机:

图 A1.3 – 查看资源
Anaconda
- 前往
www.anaconda.com/并点击下载。它将下载 Python 和多个流行的库:

图 A1.4 – 下载 Anaconda
将下载一个可执行文件,启动它。
- 点击下一步按钮并阅读并接受许可协议:

图 A1.5 – 启动安装文件
-
会出现一些额外的设置问题。
本书中的练习,你只需要做以下几步:
-
安装类型:选择为仅我自己安装选项。
-
安装位置:接受默认设置。
-
高级安装选项:将 Anaconda 3 注册为 Python 3.9 系统。
Python 3.9 是目前的版本,预计会不断发展,版本号可能会有所变化。
-
-
然后,点击安装,等待安装完成,然后点击完成。
根据你对终端的熟悉程度,有两种方法可以使用 Anaconda。点击 Windows Start 按钮,你将看到 Anaconda 应用或 Anaconda 提示符。Anaconda 应用长这样:

图 A1.6 – Anaconda 应用概览
Anaconda 提示符看起来就像一个终端。为了能够安装我们将要使用但 Anaconda 中未预安装的库,你需要通过以下方式添加 pip 分发工具:
-
打开终端并输入以下命令:
conda install pip然后,按 Enter 键并等待下载完成。
-
要创建环境,请按照以下步骤操作(在终端中):
y and press *Enter*, and it will build the environment. -
每次你想在相同环境下工作时,打开终端并输入以下命令:
conda activate web3data -
要访问我们将要工作的 Jupyter notebook,一旦环境被激活,输入以下命令:
jupyter lab一个 Jupyter notebook 网页将在本地服务器上启动。
另一种方法是通过点击 Launch 按钮从应用程序启动 Jupyter Notebook。它将打开一个本地网站。在那里,进入你将保存工作的文件夹,点击左上角的 New 按钮。它会提供一个选项列表;选择 Python3 (ipykernel),然后它会打开一个我们将要工作的笔记本:

图 A1.7 – Anaconda 应用中的 Jupyter Notebook 概览
Ganache
Ganache 是一款旨在创建个人本地区块链网络用于测试和开发的软件。它是 Truffle 套件框架的关键组成部分,Truffle 套件还包括 Drizzle。Truffle 作为开发环境、测试框架和资产管道,而 Drizzle 提供了多种前端库。让我们看看如何访问 Ganache:
- 访问
trufflesuite.com/ganache/并根据你的操作系统下载程序:

图 A1.8 – Ganache 下载
-
启动已下载的可执行文件,阅读并接受条款和条件,并确认是否希望启用分析功能。
-
一旦 Ganache 程序启动,导航到 QUICKSTART。这将是你进行测试的以太坊环境。你将看到一个类似于以下的页面:

图 A1.9 – Ganache 快速入门
Infura
- 首先,访问
infura.io/并点击 注册,然后输入你的电子邮件地址和密码:

图 A1.10 – Infura 注册
-
阅读并接受条款和条件后,点击 创建一个免费账户。检查你的电子邮件,点击其中的验证链接确认你的账户。
-
一系列人口统计学问题将会出现。选择适合你的答案。
-
创建你的第一个项目,并为其命名,例如
web3datascience:

图 A1.11 – 项目创建
- 点击 提交。这将带你进入下一个页面,类似于如下所示的页面:

图 A1.12 – 用户仪表盘
- 在灰色框中导航到 管理密钥,以查找你的 API 密钥:

图 A1.13 – API 密钥信息
附录 2
以下是如何在 X(前身为 Twitter)上创建 开发者 账户并获取 API 密钥的步骤:
- 访问 https://developer.twitter.com/ ,并确保你的 X 账户已成功登录。这里有多个订阅计划;为了完成
Chapter03/Social.ipynb中的练习,你至少需要订阅 基础 计划:

图 A2.1 – 订阅选项
一旦获得权限,我们应该创建一个项目,并为项目命名:

图 A2.2 – 项目名称
从提供的选项中选择一个用例:

图 A2.3 – 下拉选项列表
更详细地描述项目:

图 A2.4 – 描述用例的空间
- 一旦项目创建完成,我们将创建一个与该项目相关的应用。每个订阅计划都允许连接到项目的应用数量有限:

图 A2.5 – 应用选项
- 我们需要提供关于应用的详细信息,在最后一个标签页中,我们将看到 API 密钥;这就是应用将使用的地方:

图 A2.6 – 应用环境选项
为应用提供一个名称:

图 A2.7 – 应用名称
在这个标签页中,我们将看到生成的 API 密钥——一组三个密钥:API 密钥、API 密钥密钥和承载令牌:

图 A2.8 – 密钥与令牌标签
附录 3
以下是对 Dune Analytics nft.trade 表格的逐列分析,并附加了对文档中关于 Bored Ape #6633 销售的评论,这些评论也包含在 第四章 中。(来源:dune.com/docs/data-tables/spellbook/top-tables/nft.trades/#column-data 和 dune.com/queries/3268989):
-
block_time: 交易添加的区块时间戳。 -
nft_token_id: 正在转移的令牌 ID。在我们在笔记本中分析的案例中,该数字为6633。 -
erc_standard:智能合约遵循的标准,表示项目的结构方式。可以是ERC 20、ERC 721或ERC 1155。该表还显示了SuperRare标准。 -
platform:这一列将显示进行交易的市场平台。 -
platform_version:一些市场随时间演变并更改了其智能合约。查询信息的方式和功能可能会根据平台版本有所不同。 -
trade_type:根据文档,这张表列出了三种交易类型:-
单一物品交易:单笔交易中只包含一个物品。
-
捆绑交易:一个交易中包含多个物品。
-
聚合器交易:单笔交易中同时从多个市场转移多个物品。
但在查询数据时,我们发现这一列是指主要销售或二级销售:
-
-
category:智能合约执行的活动类别,范围从拍卖到传统销售。 -
nft_project_name:NFT 项目的名称,以人类可读的形式表示;例如,Bored Ape Yacht Club 或 CryptoPunks。 -
evt_type:以 Bored Ape 6633 为例,它的类型是trade。此表中的选项有trade、redeem、mint和swap。 -
usd_amount:交易中支付的价格。该价格是将转账货币的数量(例如 ETH/USDT)与转账时的市场价格相乘得出的。根据 Dune 文档,市场价格来自第三方数据库。 -
seller:市场中艺术品的卖家。以 Bored Ape 6633 为例,卖家的地址是0xde2…06ef。 -
buyer:市场中艺术品的买家。以 Bored Ape 6633 为例,买家的地址是0xb4…cb57。 -
original_amount:以交易所使用的代币/货币金额表示的支付价格。在我们关注的例子中,是 ETH。此值已解码,意味着它是从最初反映在链上的格式中转换过来的。 -
original_amount_raw:支付的价格,但未解码小数部分。 -
currency_symbol:用于生成交易的货币或代币。 -
original_currency_contract:使用的货币或代币的合约。当在 ERC-20 代币中搜索转账时,这非常有用。例如,如果 NFT 销售的支付使用 USDT 或 DOC,我们需要在 USDT 或 DOC 智能合约日志中搜索转账。在日志中,我们会找到涉及的两个地址之间的转账记录。 -
currency_contract:当货币被包装以便在交易所使用时,这个字段是相关的。例如,对于以太坊,包装合约是 WETH,合约为xc02…6cc2。 -
project_contract_address: 这是集合合约地址,结合代币 ID 可以为非同质化物品提供唯一性。在 Bored Ape Yacht Club 集合中,合约地址为0xbc…f13d,如在第四章开头所示。 -
aggregator_name和aggregator_address: 在本次分析的转账中,这些列为空。它们包含聚合器的地址,以防其中任何一个参与交易。 -
exchange_contract_address: 交易发生的市场地址。在我们在笔记本上跟踪的收藏品的案例中,市场为 OpenSea,地址为0x7b…d12b。这些智能合约处理平台上列出的收藏品的转移和支付。 -
tx_hash: 销售交易的交易哈希。 -
block_number: 交易被纳入的区块号。 -
tx_from: 交易发起方。在 Bored Ape 6633 的销售中,发起方是买家。 -
tx_to: 交易的接收方。在市场中的销售交易中,接收方是交易所智能合约,它接收交易并激活相关功能以执行销售。在本例中,接收方为 OpenSea 交易所地址。 -
royalty_fees_percent: 支付给创作者的版权费(以百分比表示)。以 Bored Ape 6633 的销售为例,版权费为 2%。 -
royalty_fees_amount: 以此次交易所使用的货币表示的版权费用。在本例中,版权费用为 3.99975 WETH。 -
royalty_fee_amount_usd: 执行时版权费用的美元价值。在本例中,版权费用为 12,929.991825 美元。 -
platform_fees_percent: 平台费用(以百分比表示)。在本例中,平台费用为 2%,与版权费用相同。 -
platform_fees_amount: 以此次交易所使用的货币表示的平台费用,金额为 3.99975 WETH。 -
platform_fees_usd: 执行时平台费用的美元价值。金额为 12,929.991825 美元。


浙公网安备 33010602011771号