为 WebAssembly 构建
我目前正在为 Memphis(我的 Rust 中的 Python 解释器)探索两个有趣的主题:构建 WebAssembly 和嵌入 CPython。由于本周没有重大里程碑要报告,我想分享一些正在进行的想法。对我来说,孟菲斯是一个通过实际实验扩展我的概念理解的项目 - 希望这篇文章可以为您做同样的事情,因为我们正在探索我正在探索的一些设计决策。
浏览器中的 Python
将 Memphis 编译为 WebAssembly 目标已经在我脑海中浮现了一段时间,两个星期六前,我终于尝试了一下。在杯垫上放了一杯温热的滴滤咖啡,我掰响指关节开始了。
WebAssembly 是现代 Web 浏览器内的沙盒执行环境,它补充了传统的 JavaScript 环境。 Wasm 环境更接近本机代码,可用于受益于更高性能的 CPU 上下文的任务;想想数字运算或愚蠢的繁忙循环。我对它的兴趣不是从性能的角度来看,而是因为它完全是可能的。 Rust 的卖点之一(实际上有无数卖点)是它可以针对 Wasm。有人可能会问,怎么办?这是可能的,因为 Rust 使用 LLVM 作为其编译器后端。 Rust 编译器前端生成 LLVM 中间表示 (IR) 代码,LLVM 可以将其编译为数十个目标的本机代码。
这是一个相当巨大的好处,我很好奇它是否只适用于孟菲斯。我之前对在浏览器中运行 Python 的想法几乎为零,所以这似乎是测试 Wasm 学习曲线的绝佳机会。
设置 wasm-pack 并构建 WebAssembly
我启动了人工智能助手并询问启动顺序。发出嘟嘟嘟嘟嘟的声音。以下是我一路上学到的注释的步骤。
# wasm-pack helps compile our Rust code to WebAssembly and bundle it # with JavaScript bindings we can call from our HTML/JavaScript page. cargo install wasm-pack # wasm-pack also downloads the wasm32-unknown-unknown target via # rustup for us. If for whatever reason it does not, you can use this: # rustup target add wasm32-unknown-unknown # We must specify a feature flag because our wasm_bindgen interface is # behind the wasm feature flag. wasm-pack build --target web --out-dir wasm_ui/pkg -- --features wasm
我第一次尝试就构建成功了!然而,因为我们没有将 Rust 二进制文件中的任何函数标记为可从 WebAssembly 调用,所以它没有做太多事情。
我们可以安装 wasm-bindgen 箱来执行此操作,我将其放在功能标志后面。我将其添加到我的 Cargo.toml 中。
[dependencies] wasm-bindgen = { version = "0.2", optional = true } [features] wasm = ["wasm-bindgen"]
这是我添加到 src/lib.rs 文件中的一小段代码,位于 wasm 功能标志后面。 greet 函数用 #[wasm_bindgen] 修饰,使该符号在 JavaScript 中可用。
# wasm-pack helps compile our Rust code to WebAssembly and bundle it # with JavaScript bindings we can call from our HTML/JavaScript page. cargo install wasm-pack # wasm-pack also downloads the wasm32-unknown-unknown target via # rustup for us. If for whatever reason it does not, you can use this: # rustup target add wasm32-unknown-unknown # We must specify a feature flag because our wasm_bindgen interface is # behind the wasm feature flag. wasm-pack build --target web --out-dir wasm_ui/pkg -- --features wasm
创建 JavaScript 界面
我还向我的人工智能助手询问了我可以用来测试我的 Wasm 界面的尽可能小的 JavaScript 片段。当我们调用 init() 时,浏览器会加载 .wasm 文件,执行 JIT 编译步骤以将可移植的 WebAssembly 二进制文件转换为本机代码,并初始化 WebAssembly 运行时的内存。
[dependencies] wasm-bindgen = { version = "0.2", optional = true } [features] wasm = ["wasm-bindgen"]
就像奇迹中的奇迹一样,它确实有效。诚然,我没有在浏览器中运行任何 Python 代码,但与我的二进制文件交互是一个巨大的步骤,年轻人不能低估它的价值。
下一步是给它一个用 JavaScript 定义的 Python 表达式,并让 Wasm 二进制文件处理数字。正如我在 REPL 文章中提到的,软件项目中的每个入口点都是改进我的抽象的机会,这里肯定会再次出现这种情况。当我翻阅我的 Memphis 存储库时,我意识到哇,我真的应该有一个更好的接口来传递字符串并将其作为 Python 进行评估。就像我说的,我喜欢新的入口点。
目前,我会使用我的交叉检查适配器。 Crosscheck 是我正在进行的测试框架,用于验证 Treewalk 解释器和字节码 VM 对于给定的 Python 输入产生相同的行为。它以空姐所做的事情命名。
这是我更新的 Rust 代码。
#[cfg(feature = "wasm")] mod wasm { use wasm_bindgen::prelude::wasm_bindgen; // Export a function to JavaScript #[wasm_bindgen] pub fn greet() -> String { "Hello from WebAssembly!".to_string() } }
这是我更新的 JavaScript 代码,它调用新的 Rust 评估函数。
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Wasm Test</title> </head> <body> <script type="module"> import init, { greet } from './pkg/memphis.js'; async function run() { await init(); console.log(greet()); } run(); </script> </body> </html>
调试 WebAssembly 错误
现在,当我运行它时,我得到了……控制台错误。它因未实现的错误而崩溃。
我查了一下,并不清楚是什么原因造成的。您可以单击源代码,但对于 Wasm 构建来说,它只是一个汇编块,没有引用原始 Rust 函数。
我进行了一些人工智能聊天/谷歌搜索,发现了两种有用的方法。一种是用于 Wasm 构建的 console_log,它在浏览器控制台中显示来自 Rust 代码的日志语句。这对一些人有帮助,但我真正想要的是堆栈跟踪。输入console_error_panic_hook。它立即给了我 Rust 堆栈跟踪,即 CLUTCH。如果您正在构建自己的 Wasm,请立即停止阅读并添加此箱子。我什至不介意你永远读不完这篇文章。费里斯希望你使用这个箱子?以下是我将其添加到我的 Wasm 界面的方法。
#[cfg(feature = "wasm")] mod wasm { use wasm_bindgen::prelude::wasm_bindgen; use crosscheck::{InterpreterTest, TreewalkAdapter}; // Export a function to JavaScript #[wasm_bindgen] pub fn greet() -> String { "Hello from WebAssembly!".to_string() } #[wasm_bindgen] pub fn evaluate(code: String) -> String { let result = TreewalkAdapter.execute(&code); format!("{}", result) } }
我的堆栈跟踪指出了罪魁祸首:我使用 std::env 来请求一些操作系统资源,这在 Wasm 运行时(即沙盒部分)中是不允许的。我将这些调用放在功能标志后面(它们与我如何随意确定 Python 标准库在主机上的位置有关)并再次启动我的构建。在与正确显示我的返回类型相关的一些小失败之后......
它成功了。这是我现在在浏览器控制台中看到的内容。
# wasm-pack helps compile our Rust code to WebAssembly and bundle it # with JavaScript bindings we can call from our HTML/JavaScript page. cargo install wasm-pack # wasm-pack also downloads the wasm32-unknown-unknown target via # rustup for us. If for whatever reason it does not, you can use this: # rustup target add wasm32-unknown-unknown # We must specify a feature flag because our wasm_bindgen interface is # behind the wasm feature flag. wasm-pack build --target web --out-dir wasm_ui/pkg -- --features wasm
tldr 我可以在浏览器中运行Python。 (值得赞扬的是,RustPython 也这样做了:https://rustpython.github.io/demo/。我没有深入研究他们的项目,但它似乎很全面。)Python 列表理解是在 JavaScript 中以字符串形式定义的,响应列表由编译为 Wasm 的 Rust 代码评估,并转换回可由 JavaScript 显示的字符串。
此设置目前仅支持表达式。为了评估语句(并稍后读回其结果),我需要在 Rust 端保留状态。我也梦想构建一个 JavaScript REPL。这听起来像是未来的我的一个问题(而且是一个无聊的梦)。
结局
我已经聊得够久了,所以我打算推迟到下周一再讨论嵌入式 Python。
对诱饵和开关表示歉意。内容日历不等人。
需要明确的是,通过嵌入式 Python,我的意思是在孟菲斯内部嵌入 CPython 解释器,而不是在“嵌入式系统”环境中运行 Python。那会毫无理由地困难。与孟菲斯不同,孟菲斯很难好玩。
如果您想将更多类似的帖子直接发送到您的收件箱,您可以在这里订阅!
别处
除了指导软件工程师之外,我还写了我作为一名成人诊断自闭症患者的经历。更少的代码和相同数量的笑话。
- 为什么我渴望得到认可? - 来自 Scratch 点组织
以上是为 WebAssembly 构建的详细内容。更多信息请关注PHP中文网其他相关文章!

热AI工具

Undresser.AI Undress
人工智能驱动的应用程序,用于创建逼真的裸体照片

AI Clothes Remover
用于从照片中去除衣服的在线人工智能工具。

Undress AI Tool
免费脱衣服图片

Clothoff.io
AI脱衣机

Video Face Swap
使用我们完全免费的人工智能换脸工具轻松在任何视频中换脸!

热门文章

热工具

记事本++7.3.1
好用且免费的代码编辑器

SublimeText3汉化版
中文版,非常好用

禅工作室 13.0.1
功能强大的PHP集成开发环境

Dreamweaver CS6
视觉化网页开发工具

SublimeText3 Mac版
神级代码编辑软件(SublimeText3)

Python更易学且易用,C 则更强大但复杂。1.Python语法简洁,适合初学者,动态类型和自动内存管理使其易用,但可能导致运行时错误。2.C 提供低级控制和高级特性,适合高性能应用,但学习门槛高,需手动管理内存和类型安全。

要在有限的时间内最大化学习Python的效率,可以使用Python的datetime、time和schedule模块。1.datetime模块用于记录和规划学习时间。2.time模块帮助设置学习和休息时间。3.schedule模块自动化安排每周学习任务。

Python在开发效率上优于C ,但C 在执行性能上更高。1.Python的简洁语法和丰富库提高开发效率。2.C 的编译型特性和硬件控制提升执行性能。选择时需根据项目需求权衡开发速度与执行效率。

每天学习Python两个小时是否足够?这取决于你的目标和学习方法。1)制定清晰的学习计划,2)选择合适的学习资源和方法,3)动手实践和复习巩固,可以在这段时间内逐步掌握Python的基本知识和高级功能。

Python和C 各有优势,选择应基于项目需求。1)Python适合快速开发和数据处理,因其简洁语法和动态类型。2)C 适用于高性能和系统编程,因其静态类型和手动内存管理。

pythonlistsarepartofthestAndArdLibrary,herilearRaysarenot.listsarebuilt-In,多功能,和Rused ForStoringCollections,而EasaraySaraySaraySaraysaraySaraySaraysaraySaraysarrayModuleandleandleandlesscommonlyusedDduetolimitedFunctionalityFunctionalityFunctionality。

Python在自动化、脚本编写和任务管理中表现出色。1)自动化:通过标准库如os、shutil实现文件备份。2)脚本编写:使用psutil库监控系统资源。3)任务管理:利用schedule库调度任务。Python的易用性和丰富库支持使其在这些领域中成为首选工具。

Python在科学计算中的应用包括数据分析、机器学习、数值模拟和可视化。1.Numpy提供高效的多维数组和数学函数。2.SciPy扩展Numpy功能,提供优化和线性代数工具。3.Pandas用于数据处理和分析。4.Matplotlib用于生成各种图表和可视化结果。
