WebAssembly 和 TypeScript:轻松加速网络

面向初学者的在线Python训练器

轻松学习Python,无需理论负担。在浏览器中直接解决带自动检查的实践任务,无需安装任何东西。

开始课程

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\n

WebAssembly 是一种二进制指令格式,在浏览器的虚拟机中执行。如果说 JavaScript 是一种解释型语言,需要“即时”解析和执行,那么 Wasm 则是已经编译好的字节码。它加载更快,执行起来几乎像原生代码,并且不会让浏览器“卡顿”。

\n\n

WebAssembly 的关键特性:

\n
    \n
  • 速度——在计算密集型任务中,比 JavaScript 快 10 到 20 倍。
  • \n
  • 安全性——在隔离环境(沙箱)中运行,无法直接访问 DOM。
  • \n
  • 可移植性——同一个 .wasm 文件可以在 Chrome、Firefox、Safari 和 Edge 中运行。
  • \n
  • 不是 JS 的替代品——而是补充。DOM、事件、异步操作仍由 JavaScript/TypeScript 负责。
  • \n
\n\n

Wasm 并非用于编写界面逻辑。它的领域是繁重的计算:加密、图像处理、物理模拟、游戏。

\n\n

那么 TypeScript 在哪里?

\n\n

TypeScript 本身不会编译成 WebAssembly(尽管有一些实验性项目,但它们不适合生产环境)。然而,TypeScript 成为了连接 Wasm 模块和用户界面的理想“胶水”。想象一下:您有一个用 C++ 编写的快速算法,已编译成 Wasm。您用 TypeScript 编写一个带有类型的整洁包装器,然后您的 IDE 开始提示函数期望哪些参数,以及它返回哪些类型。没有魔法——只是严格的类型检查和自动补全。

\n\n

这是一个典型的架构:

\n
    \n
  • Wasm 模块——一个执行复杂工作的黑盒。
  • \n
  • TypeScript 代码——加载模块,调用其函数并更新 UI。
  • \n
  • 浏览器——很高兴,因为繁重的工作不会阻塞主线程。
  • \n
\n\n

编写一个示例:在 WebAssembly 和 TypeScript 上生成质数

\n\n

让我们创建一个实际项目。我们将采用一个用 C++ 编写的质数查找算法(埃拉托斯特尼筛法),将其编译成 Wasm,然后从 TypeScript 调用它。不要害怕 C++——代码很简单,我们将使用 Emscripten 进行构建。

\n\n

步骤 1. C++ 源代码

\n

创建一个文件 primes.cpp:

\n
#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}
\n

EMSCRIPTEN_KEEPALIVE

博客

书籍推荐