524 words
3 minutes
Effect 入门教程:3.Hello World 示例与基本概念

https://github.com/typeonce-dev/effect-getting-started-course

让我们回到 index.ts

index.ts

import { Console, Effect } from "effect"; const main = Console.log("Hello world"); Effect.runSync(main);

这是 effect 的 “Hello World”,等价于 console.log

我们已经可以注意到 effect 程序的第一个主要区别:在 effect 中,定义应用程序(main)和执行它(Effect.runSync)是两个独立的操作。

我们显式地执行,这意味着 effects 不会像 console.log 那样急切地运行!

/// 1️⃣ 定义 `main` 应用程序 const main = Console.log("Hello world"); /// 2️⃣ 执行应用程序 Effect.runSync(main);

为什么会这样?

Effect 是一系列操作的描述

  • console.log 执行某些副作用并返回 void
  • Console.log 只是描述将要发生什么,而不执行任何副作用
/// 👇 `native` 是 `void`,副作用已经被执行了! /// 这个操作已经"做了"某些事情! const native: void = console.log("Hello world"); /// 👇 `effect` 是 `Effect<void>`,它描述了执行时返回 `void` 的东西 /// 这只是描述应该发生什么,它还没有做任何事情 const effect: Effect<void> = Console.log("Hello world");

Effect 本身不执行任何逻辑。相反,你需要显式地调用 run* 方法(在这个例子中是 runSync)。

这类似于存储一个函数而不是执行它:

/// 1️⃣ 定义 `main` 应用程序 const main = () => console.log("Hello World"); /// 2️⃣ 执行应用程序(显式地) main();

函数式副作用是不可变的数据结构,仅仅描述操作序列。

它们必须被显式运行才能执行真正的副作用。

Console.log 的工作原理#

Console.log 是一个返回 Effect<void> 的函数。

在实践中,这意味着 Console.log 在执行时返回 void

// 👇 定义 const main: Effect<void> = Console.log("Hello world"); // 👇 执行 Effect.runSync(main); // void

同样,这类似于一个执行时在控制台打印的函数:

type Program<T> = () => T; // 👇 定义 const main: Program<void> = () => console.log("Hello World"); // 👇 执行 main(); // void

Effect.runSync 接受一个 Effect 作为输入并同步地运行它。

结果:运行一个同步程序,打印字符串 "Hello World" 并返回 void

  • “运行一个同步程序…”:Effect.runSync
  • ”…打印字符串 "Hello World"…”:Console.log("Hello World")
  • ”…并返回 void”:Effect<void>

index.ts

import { Console, Effect } from "effect"; const main = Console.log("Hello world"); Effect.runSync(main);
> effect-getting-started-course@1.0.0 dev > tsx src/index.ts Hello world
Effect 入门教程:3.Hello World 示例与基本概念
https://0bipinnata0.my/posts/course/effect-beginners-complete-getting-started/setting-up-the-project/effect-hello-world/
Author
0bipinnata0
Published at
2025-08-29 21:29:39