WebAssembly 和 TypeScript:当 JavaScript 力不从心时
\n\n您是否曾感到您的网站运行缓慢,尽管您已经用现代 TypeScript 编写了所有代码?视频处理、3D 渲染、复杂的数学计算——浏览器中的 JavaScript 开始力不从心。正是在这里,WebAssembly(或简称 Wasm)——一种允许在浏览器中运行用 C++、Rust 或 Go 编写的代码,速度接近原生的技术——登上了舞台。但这与 TypeScript 有什么关系呢?剧透:直接来说,没有关系,但它们共同形成了一个强大的组合。
\n\n在本文中,我们不仅会给出枯燥的定义。我们将展示 TypeScript 和 WebAssembly 如何协同工作,各司其职:TypeScript 负责便利性和类型化,而 Wasm 负责性能。您将学习如何编写一个简单的 Wasm 模块并从 TypeScript 调用它,最重要的是,您将明白这样做是否值得。
\n\n用简单的话说,什么是 WebAssembly
\n\nWebAssembly 是一种二进制指令格式,在浏览器的虚拟机中执行。如果说 JavaScript 是一种解释型语言,需要“即时”解析和执行,那么 Wasm 则是已经编译好的字节码。它加载更快,执行起来几乎像原生代码,并且不会让浏览器“卡顿”。
\n\nWebAssembly 的关键特性:
\n- \n
- 速度——在计算密集型任务中,比 JavaScript 快 10 到 20 倍。 \n
- 安全性——在隔离环境(沙箱)中运行,无法直接访问 DOM。 \n
- 可移植性——同一个 .wasm 文件可以在 Chrome、Firefox、Safari 和 Edge 中运行。 \n
- 不是 JS 的替代品——而是补充。DOM、事件、异步操作仍由 JavaScript/TypeScript 负责。 \n
Wasm 并非用于编写界面逻辑。它的领域是繁重的计算:加密、图像处理、物理模拟、游戏。
\n\n那么 TypeScript 在哪里?
\n\nTypeScript 本身不会编译成 WebAssembly(尽管有一些实验性项目,但它们不适合生产环境)。然而,TypeScript 成为了连接 Wasm 模块和用户界面的理想“胶水”。想象一下:您有一个用 C++ 编写的快速算法,已编译成 Wasm。您用 TypeScript 编写一个带有类型的整洁包装器,然后您的 IDE 开始提示函数期望哪些参数,以及它返回哪些类型。没有魔法——只是严格的类型检查和自动补全。
\n\n这是一个典型的架构:
\n- \n
- Wasm 模块——一个执行复杂工作的黑盒。 \n
- TypeScript 代码——加载模块,调用其函数并更新 UI。 \n
- 浏览器——很高兴,因为繁重的工作不会阻塞主线程。 \n
编写一个示例:在 WebAssembly 和 TypeScript 上生成质数
\n\n让我们创建一个实际项目。我们将采用一个用 C++ 编写的质数查找算法(埃拉托斯特尼筛法),将其编译成 Wasm,然后从 TypeScript 调用它。不要害怕 C++——代码很简单,我们将使用 Emscripten 进行构建。
\n\n步骤 1. C++ 源代码
\n创建一个文件 primes.cpp:
#include <emscripten.h>\n\nextern "C" {\n EMSCRIPTEN_KEEPALIVE\n int count_primes(int limit) {\n if (limit < 2) return 0;\n bool* sieve = new bool[limit + 1];\n for (int i = 0; i <= limit; i++) sieve[i] = true;\n sieve[0] = sieve[1] = false;\n for (int i = 2; i * i <= limit; i++) {\n if (sieve[i]) {\n for (int j = i * i; j <= limit; j += i) {\n sieve[j] = false;\n }\n }\n }\n int count = 0;\n for (int i = 0; i <= limit; i++) {\n if (sieve[i]) count++;\n }\n delete[] sieve;\n return count;\n }\n}\nEMSCRIPTEN_KEEPALIVE
博客
书籍推荐
推荐阅读