控制流、循环与其他数字统治形式
控制流、循环与其他数字统治形式
这一章给你指挥代码的全套手势。 三个主干:if 不只判断、还能返回值; switch 强迫你覆盖所有情况,漏一个编译不过;for 循环能同时遍历多个序列, 还自带一个 else 分支。两个进阶:optionals(
?T)让「可能没有值」写进类型里, labeled switch 让状态机的跳转写在明面上。每一招都接得住第 1 章那句话: 代码做的就是你读到的。
1. 这一章讲什么
链条位置:第 3 章让程序跑起来,这一章让程序会拐弯。 它也是 Zig 安全哲学的第二次落地(第一次是变量必须初始化): switch 的穷举检查和 optionals 的空值检查,都是「让漏处理在编译期变成错误」。
2. 顶层全景:一张决策地图
要不要做事? → if / else(还能当表达式返回值)
按值选路? → switch(穷举;可带标签做状态机跳转)
重复做事? → for(遍历集合/区间/多序列;可带 else、可带标签)
while(条件循环,本章只点到)
可能没有值? → ?T + if 解包 / orelse 默认值
图说:四问对应四组工具。本章按这个顺序逐个展开。主线例子沿用原书的数组 items = [4, 5, 3, 4, 0]:一个 for 循环把它从头到尾走一遍,
中间跳过 0、求和、带索引、带切片——全部机制都在这一个输入上走;
状态机部分另起一例(红绿灯),那是 labeled switch 的主场。
3. if:不只是判断,还是表达式
3.1 基本形态:和你知道的一样
if (number > 5) { ... } else { ... }、else if 串联,第 3 章就见过,
没有意外——原书说「可预测是福气」1。
3.2 表达式形态:不用三元运算符
别的语言写一个值按条件取值,用三元运算符 cond ? a : b。
Zig 没有三元运算符;它让 if 直接当表达式用2:
const result = if (a != b) 47 else 3089;走一遍:a = 5,b = 4,a != b 为真 → 整个 if...else... 的值是 47 → result = 473。
书里的点评是 Zig 的一贯腔调:「要什么神秘符号,写更清楚的字不好吗」4。
两个纪律(原书的告诫框):别为了炫技把 if 表达式嵌成迷宫;一个代码库里统一一种风格5。 这条告诫在全章反复出现——它其实是 Zig 社区的集体经验,不是这一章特有的。
3.3 与联合类型的配合(预告)
原书预告:if 还能和联合类型(union,第 6 章)配合,区分「成功结果」和「错误」6。 这是第 6 章错误处理的引子,这里只立名字。
4. switch:穷举,且不贯穿
4.1 基本形态
const day = 3;
switch (day) {
1 => print("It's Monday.\n", .{}),
2 => print("It's Tuesday.\n", .{}),
3 => print("It's Wednesday.\n", .{}),
else => print("It's some other day.\n", .{}),
}每个分支 值 => 要做的,else 是兜底7。
4.2 两条安全性质(本章承重墙)
性质一:穷举(exhaustive)。 switch 必须覆盖被判断的类型的所有可能值;
漏了,编译错误:switch must handle all possibilities8。
对比:C 和 Go 的 switch 不检查穷尽,逻辑上留个洞编译器也不吭声9。
这条和第 1 章的六张安全网是同一张:把「漏考虑」从运行时事故变成编译时错误。
性质二:默认不贯穿(no fallthrough)。 C/C++/JavaScript 的 switch 有个著名的坑: 匹配了一个 case 之后,如果没有写 break,执行会继续掉进下一个 case。 Zig 取消了贯穿:每个分支自成一体10。想多个值共用一个分支?显式把它们列在一起:
1, 2, 3 => print("前三天\n", .{}), // 显式分组,不是「掉了 break」原书的总结值得照收:穷举 + 不贯穿,让 switch 从「决策工具」升级成 「把安全和清晰直接砌进逻辑」的机制11。
判断(我们的,不是书里的): 这两条性质里,穷举的性价比更高。 它几乎零成本(else 兜底一下就行),却消灭了「新增枚举值时忘了改 switch」这类 维护期最高发的 bug 之一。不贯穿是「治已经治得差不多的病」——现代 C 风格指南 早已要求每个 case 写 break,这个病在认真写的代码里不常发。 如果错,会错在: 对「值域无限」的类型(比如整数),穷举靠 else 兜底, 此时穷举只保证了「你写过 else」,不保证「else 里处理得对」——安全网有边界。
5. for 循环:一个数组走全程
5.1 主线例子:求和,跳过 0
const items = [_]i32{ 4, 5, 3, 4, 0 };
var sum: i32 = 0;
for (items) |value| {
if (value == 0) {
continue; // 跳过这个元素,进入下一轮
}
sum += value;
}
// sum = 16逐轮走一遍(这是本章的主线例子,后面每个变体都改它一两行):
| 轮次 | value | 动作 | sum 之后 |
|---|---|---|---|
| 1 | 4 | 非 0,累加 | 4 |
| 2 | 5 | 累加 | 9 |
| 3 | 3 | 累加 | 12 |
| 4 | 4 | 累加 | 16 |
| 5 | 0 | continue,跳过 | 16 |
输出 The sum is: 1612。语法要点:for (集合) |元素| { ... }——
竖线里是每一轮绑给循环体的名字。continue 跳过本轮剩余部分,break 直接出循环,
这两个和其他语言一致。
5.2 只遍历一段:切片下标
for (items[0..2]) |value|——[0..2] 是切片语法:从下标 0 开始、到下标 2 之前为止
(含头不含尾,off-by-one 的成年礼)13。走一遍:只碰到 4 和 5,sum = 9。
切片是「视图」不是「拷贝」:它没有复制数据,只是换了个窗口看原数组(第 8 章细讲)。
5.3 要下标:双序列遍历 0..
for (items, 0..) |_, index| {
sum += @intCast(index);
}0.. 是「从 0 开始的无限区间」,和 items 并排走:每个元素配上它的下标14。
两个名字按顺序对应两个序列:|_, index| 里 _ 表示「这个槽位的值我不想要」
(占位丢弃,是 Zig 的惯用法)。@intCast(index) 把下标类型强转成 i32——
类型不匹配编译不过,转换必须显式写(第 9 章的类型转换专讲)。
变形记牢一组就够:for (数组, 0..) |值, 下标|。
反过来写 |下标, 值| 是错的——顺序由序列顺序定,这也算一种「透明」:
名字和值的对应关系由位置白纸黑字写出,不靠约定俗成。
5.4 只遍历数字区间
for (0..5) |i| 直接遍历 0 到 415——不需要集合,区间本身就是可遍历的东西。
5.5 一次遍历两个集合
const items1 = [_]usize{ 1, 2, 3 };
const items2 = [_]usize{ 4, 5, 6 };
for (items1, items2) |i, j| {
total += i + j;
}
// total = 21两个数组锁步(lockstep)前进:(1,4)、(2,5)、(3,6),每对求和16。
边界(原书一句带过但要记住):两个集合必须一样长,不等长会运行时报错17。
(这是 Debug 档的运行时检查在兜底;第 1 章那张四档表在此兑现。)
5.6 循环当表达式:带 else 的 for
Zig 的 for 可以有值,还自带一个 else 分支。语义要记准:
else 在「循环一次都没跑成」或「没 break」时执行;一旦 break 过,else 就不执行。
原书例子走一遍:
const items = [_]i32{ 1, 3, 4, 5 };
var sum: i32 = 0;
var stoppedAtIndex: usize = 0;
const stoppedEarly = for (0.., items) |i, value| {
if (@mod(value, 2) == 0) { // 遇到偶数
stoppedAtIndex = i;
break true; // break 可以带值:整个循环的值
}
sum += value;
} else false; // 没遇到偶数才会执行这里执行轨迹:1 累加(sum=1)、3 累加(sum=4)、4 是偶数 → 记下下标 2、break 带值 true。
输出:Sum of items: 4 和 Stopped at index: 218。
解释词:@mod(value, 2)。 内建函数,取余数;@mod(4, 2) == 0 就是「是偶数」。
这个组合(if 解包 + break 带值 + else)让「查找第一个满足条件的元素」这种高频操作
不需要额外的布尔标志变量——控制流的值本身就是答案。
5.7 标签循环:嵌套的逃生通道
嵌套循环里,内层的 break 只跳出内层。给外层起个名字,就能从内层直接操作外层:
outer: for (1..6) |_| { // 外层起名叫 outer
for (1..6) |_| {
count += 1;
break :outer; // 一次跳出两层
}
}
// count = 1:外层第一轮、内层第一圈就 break 了外层break :outer 从内层直接跳出外层循环19;对称地,continue :outer
是「跳过外层的下一轮」20。走一遍第二个例子:
outer: for (1..5) |i| {
for (1..5) |j| {
if (i == j) continue :outer; // i 和 j 相等:跳到外层下一轮
count += 1;
}
}
// count = 12:i≠j 的 (i,j) 共有 4×3 个原书对 labeled continue 的点评很诚实:「确保只有你自己看得懂的可靠方法」21—— 威力大、可读性税也高,留给真嵌套深的地方用。
5.8 inline for:编译期展开的循环
inline for 强制在编译期把循环展开:数组有几个元素,循环体就被复制几份,
循环变量变成编译期已知的常量22。原书的例子里,i 在编译期已知,
于是可以用 switch 把 2 映射到类型 f32、4 映射到 i8——值到类型的映射,
只能在编译期做。
代价原书也直说:增加二进制体积、复杂化构建;告诫「除非有 compelling 理由 (和医生的条子),否则别用」23。这是 comptime 世界的第一次露面,第 12 章接它。
5.9 while:本章的缺席者
值得注意:本章正文几乎没有讲 while——只有一段边注说「while 和 for 很像,
仓库里有例子,自己去探索」24。而章末测验第 6 题考的却是 while 的
while (cond) : (续行表达式) 语法,答案选项 : (expression)25。
这是原书的一个小断裂:考的没教。我们用一句话补上(补充,不在书里展开):
while (i < 10) : (i += 1) 每轮结束自动执行冒号后的表达式,相当于 for 的「步进」
写在循环头上。深度讲解要等读者自己翻仓库或官方文档。
5.10 循环军规
原书的 best-practice 四条26:保持简单;别过早优化(「相信编译器比你聪明,它多半是」); 写了聪明的(或鲁莽的)代码就留注释解释;认真测试——循环是 off-by-one 和死循环的重灾区。 这些不是 Zig 特有的,但放在 Zig 语境里多了一层意思:Zig 已经把能替你查的都查了 (穷举、越界、长度匹配),剩下的这几条,是它查不了的、归你管的。
6. Optional 类型:?T——把「可能没有」写进类型
6.1 问题从哪来
现实里到处是「可能没有值」:用户没填的输入、没等到的网络数据、没读全的文件。 别的语言的常见结局:空指针异常(null pointer exception)—— 程序在运行时毫无防备地崩掉,而这正是第 1 章说的 C 系崩溃头名死因。
Zig 的解法和「指针默认非空」是同一张网的经纬两面:
- 指针、值,默认都不能是 null;想可空,类型上必须写明
?前缀; - 写了
?,编译器就强迫你处理「没有」的情况,漏处理编译不过。
6.2 ?T 与解包
const maybeValue: ?i32 = 10; // 一个「可能是 i32、可能是 null」的值
if (maybeValue) |value| { // 有值:解包进 value(此时 value 是普通 i32)
print("The number is {}\n", .{value});
} else { // 是 null:走这里
print("No number available.\n", .{});
}if (optional) |名字| 是 Zig 的解包语法27:只有确实存在值的那一分支,
才能拿到里面的值——从类型上保证你在「没有」的时候碰不到值。
多个 optional 可以同时查:if (maybeX and maybeY) |x, y|——
全部非 null 才进 if 分支,并同时解包成 x、y;任何一个为 null 走 else28。
走一遍原书例子:maybeX = 10, maybeY = null → 条件不成立 → 打印
「Cannot compute sum; one of the values is null.」。
6.3 三条安全收益(原书明列)
- 不再有空指针崩溃:解包强迫先查再用;
- 意图可读:看到
?T就知道「这东西可能缺席」,不用翻注释; - 编译期保证:漏处理 null,Zig 编译报错29。
6.4 orelse:给「没有」一个默认值
const n = maybeNumber orelse 0;——是 null 就拿 030。
这是「处理 null 的最懒正确姿势」:适合「缺了就用默认」的语义;
如果「缺了」本身就是需要区分的业务状态,别用 orelse 把它糊掉,回 if 解包。
另两条实践(原书)31:尽早处理 null,别让它顺着调用链传播到深处; 在代码库里写明这个 optional 为什么存在、null 代表什么——类型能强迫你处理, 不能替你解释业务含义。
6.5 遍历装着 optional 的数组
const items = [_]?i32{ 1, null, 3, null, 5 };
var sum: i32 = 0;
for (items) |item| {
if (item) |value| {
sum += value; // 有值才累加
} else {
print("Encountered a null value.\n", .{});
}
}
// sum = 9,中间打印两次 null 提示逐轮:1→累加 1;null→打印;3→累加 4;null→打印;5→累加 9。
解包语法在循环里原样可用32——「数组里可能有空洞」这个常见现实,
至此有了类型安全的遍历姿势。
判断(我们的,不是书里的):
?T是第 1 章「指针默认非空」那张安全网的类型面, 两者合起来构成 Zig 对空值问题的完整回答:默认不可空(消灭「想不到的 null」), 显式可空(消灭「忘了查的 null」)。对比 Java 的 Optional 包装类和 Kotlin 的可空类型, Zig 的版本没有运行时对象开销——?i32和 i32 在机器层面几乎同价 (补充,不在书里,来自 Zig 的可空类型实现惯例:用哨兵值或 padding 表达 null)。 如果错,会错在: 对「值本身合法取值全覆盖」的类型(比如?u0这类边角), 哨兵表达会吃亏;以及 orelse 的滥用会把本该区分的业务状态压成默认值,这是代码评审该盯的。
7. Labeled switch:写在明处的状态机
7.1 它在做什么
普通 switch 判断一次就完;给 switch 加标签后,分支里可以写
continue :标签 下一个值——直接跳到对那个值的匹配分支,相当于把
「循环 + switch + 状态变量」三件套压成一个构造。原书的主例:红绿灯33:
light: switch (@as(u8, 1)) {
1 => {
print("Light is Red. Cars stop.\n", .{});
continue :light 2; // 红 → 黄
},
2 => {
print("Light is Yellow. Prepare to stop.\n", .{});
continue :light 3; // 黄 → 绿
},
3 => {
print("Light is Green. Cars go.\n", .{});
continue :light 4; // 绿 → 行人
},
4 => {
print("Pedestrian crossing activated.\n", .{});
return; // 结束
},
}状态轨迹,一步一格:
入口:值 = 1
→ 分支 1:打印「红灯」,continue :light 2
→ 分支 2:打印「黄灯」,continue :light 3
→ 分支 3:打印「绿灯」,continue :light 4
→ 分支 4:打印「行人通行」,return,结束
图说:每个状态的「下一个状态」就写在自己分支里,没有状态变量,没有循环。第二个例子是自动售货机:投币 → 选饮料 → 出货;多一个「取消退款」分支,
同样用 return 收尾34。 vending 例里 4 号分支(取消)没有任何分支跳过去——
状态机里允许存在「只从外部事件进入」的分支,这在建模真实系统时很自然。
7.2 为什么这样更好(三个理由,前两个是书的,第三个是机制的)
- 状态管理:不用外部变量记账,
continue :label n本身就是转移表35; - 清晰:控制流下一个落点白纸黑字,读者不用在循环里追状态变量的变化;
- 性能(机制层面):如果
continue的目标值编译期可知,编译器直接生成 无条件跳转,CPU 的分支预测器(预测下一条指令走向、猜错要付出代价的硬件单元) 对这种完全可预测的跳转零失误;目标是运行期值时,每个 continue 生成独立分支, 预测器能学习「1 后面通常是 2」这类模式,越跑越准36。
7.3 对照组:老式的 while + switch
原书给了等价的旧写法对照37:外面套 while (true),里面 switch,
每个分支手动改状态变量 op = 2; continue;。功能一样,但你要同时盯三个东西:
状态变量、循环、switch。labeled switch 把三个压成一个——
这就是第 1 章「没有隐藏控制流」的又一次兑现:连状态机的「下一站在哪」都不藏。
7.4 什么时候用它
原书点了三个场景38:状态转移(红绿灯、游戏状态);
分发器/解释器(按输入选动作——编译器、虚拟机内核的典型结构);
多层决策。如果你的代码里有一个 while (true) switch (state) 的三件套,
就是 labeled switch 的候选。
补充(不在书里,来自通用知识): 这种结构在编译器理论里叫
尾调用风格的状态机; labeled switch 还可以 break :标签 值,整个 switch 当表达式
返回值——和 §5.6 的循环表达式是一对。
8. 作者的判断与证据
可核的: if 表达式语法与行为3;switch 穷举报错原文8、不贯穿10; for 的各种形态与输出(16、9、21、4 这些数都能自己跑一遍验证)121618; labeled 循环的 break/continue 语义1920;optionals 解包、and 组合、orelse272830; labeled switch 的两个完整例子3334。
作者的立场: 「别写复杂循环,简单是美德」26——经验之谈,但原书自己给出的 inline for 和多重遍历示例恰恰是「复杂」的;这是教学需要,别当风格指南读。 「inline 循环最好别用」23与「labeled switch 有真实性能收益」36都是合理判断, 但都没有测量数据支撑。
9. 边界与局限
| 缺什么 | 说明 |
|---|---|
| while 几乎没教 | 正文只有一段边注24,测验却考 while (...) : (expr) 语法25——考的没讲,是原书的一处断裂 |
| 循环性能只字未提 | 哪个循环写法快、边界检查多少钱,全章没有数据;「相信编译器」是唯一建议26 |
| labeled switch 的 else 需求 | 穷举要求对 u8 这种宽类型必须有 else 兜底;例子里没写 else 是因为分支已覆盖?——原书例子靠 4 => return 和穷举检查的交互讲得不清,读者照抄前要知道自己类型的值域 |
| union/if 配合是空头支票 | §3.3 预告「if 处理 union」但本章零展开,全靠第 6 章兑现 |
| optional 的内存布局没讲 | ?i32 在内存里怎么表示(是否多占字节),全章没提;对性能敏感的读者会想知道 |
| 习题只到 switch | 章末 10 题39覆盖 if/switch/for/optional,但 labeled switch、inline for、循环表达式都不在考点里——恰好是本章最有 Zig 特色的三样,考点却绕开了它们 |
10. 可带走的
本章主线例子,一行走完: items = [4,5,3,4,0] → for (items) |value|
→ 遇 0 用 continue 跳过 → sum = 16;变体:[0..2] 切片只取前两个(sum=9)、
(items, 0..) 带索引、if...break true...else false 找第一个偶数(停在 2,sum=4)。
状态机:light: switch (1) → 红→黄→绿→行人 → return。
- if 是表达式:
const r = if (cond) a else b;取代三元运算符; - switch 穷举:漏分支编译错误
switch must handle all possibilities;else 兜底; - switch 不贯穿:没有「忘了 break 掉下一个 case」这种病;多值共享分支要显式写在一起;
- for 的完整形态:
for (序列A, 序列B, 0..) |a, b, i|,多序列锁步、必须等长; - 循环可以是表达式:
break 值给出循环的值,else分支处理「没 break 成」——写「找第一个 X」不再需要标志变量; - 标签循环:
outer:+break :outer/continue :outer,嵌套的逃生通道,税是可读性; - inline for 在编译期展开循环,能玩「值映射到类型」的杂技,但最好别用;
- optional
?T:默认不可空,可空要显式标;if (opt) |v|解包、a orelse 默认兜底、if (a and b) |x, y|同时查多个;漏处理 null 编译不过; - labeled switch = 无变量的状态机:
continue :标签 下一状态写在分支里, 编译期目标可优化成无条件跳转,分支预测器友好; - while 的
: (expr)续行语法本章没教,测验却考——去官方文档或原书仓库补这一课。
11. 原文地图
| 主题 | 原书章 | 原文位置 |
|---|---|---|
| if 当表达式 | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:89(搜「moonlight as an expression」) · text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:106(搜「47 else 3089」) |
| if 使用告诫 | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:168(搜「intricate if expressions」) |
| if 与 union(预告) | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:155(搜「error unions」) |
| switch 穷举与报错 | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:178(搜「evaluates all possible cases」) · text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:204(搜「must handle all possibilities」) |
| 不贯穿与显式分组 | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:218(搜「no fallthrough by default」) · text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:222(搜「explicitly group them together」) |
| for 基本遍历(主线例子) | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:256(搜「for (items) |
| 切片只取一段 | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:300(搜「items[0..2]」) · text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:300(搜「grabbing elements from index 0」) |
| 带索引的双序列遍历 | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:319(搜「for (items, 0..)」) · text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:327(搜「infinite range starting from zero」) |
| 纯区间遍历 | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:343(搜「for (0..5)」) |
| 双集合锁步与等长前提 | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:365(搜「for (items1, items2)」) · text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:375(搜「in lockstep」) |
| 循环表达式与 else | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:391(搜「stoppedEarly = for」) · text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:413(搜「Sum of items: 4」) |
| 标签循环 break/continue | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:425(搜「outer: for (1..6)」) · text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:428(搜「break :outer」) · text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:454(搜「continue :outer」) |
| inline for | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:498(搜「unroll at compile time」) · text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:511(搜「Use inline loops sparingly」) |
| while 只给边注 | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:538(搜「while loops」) |
| 循环军规 | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:519(搜「smarter than you」) |
| ?T 定义与解包 | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:569(搜「might be present or might be null」) · text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:580(搜「if (maybeValue) |
| 多个 optional 同时查 | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:606(搜「maybeX and maybeY」) |
| optional 三收益 | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:627(搜「null pointer dereferencing」) · text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:632(搜「forget to handle the null case」) |
| orelse 与最佳实践 | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:640(搜「maybeNumber orelse 0」) · text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:645(搜「Handle null early」) |
| 遍历 optional 数组 | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:665(搜「[_]?i32{ 1, null, 3, null, 5 }」) |
| 红绿灯 labeled switch | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:710(搜「light: switch」) · text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:713(搜「continue :light 2」) |
| 售货机 labeled switch | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:752(搜「vending: switch」) |
| FSM 边注 | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:789(搜「Finite State Machine」) |
| while+switch 对照 | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:812(搜「while (true)」) |
| 分支预测与性能 | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:851(搜「perfectly predictable branches」) |
| labeled switch 三场景 | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:864(搜「Handling state transitions」) |
| 章末测验 | Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination | text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:892(搜「Testing your knowledge」) · text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:947(搜「execute an expression at the end」) |
Footnotes
-
出处:「Chapter 4: Control Flow, Loops, and Other Forms of Digital Domination」第 125–148 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:148,搜「predictability is a blessing」)。 ↩ -
出处:同章第 87–97 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:89,搜「moonlight as an expression」)。 ↩ -
出处:同章第 99–123 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:106,搜「47 else 3089」;text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:117,搜「5 is, shockingly, not equal to 4」)。 ↩ ↩2 -
出处:同章第 121–123 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:122,搜「Why be concise」)。 ↩ -
出处:同章第 163–172 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:168,搜「intricate if expressions」;text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:171,搜「Be consistent」)。 ↩ -
出处:同章第 150–161 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:155,搜「error unions」)。 ↩ -
出处:同章第 177–202 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:187,搜「switch (day)」;text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:200,搜「acts as a catch-all」)。 ↩ -
出处:同章第 203–205 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:204,搜「must handle all possibilities」)。 ↩ ↩2 -
出处:同章第 206–214 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:210,搜「such as C and Go」)。 ↩ -
出处:同章第 215–220 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:218,搜「no fallthrough by default」)。 ↩ ↩2 -
出处:同章第 226–232 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:226,搜「helps you catch potential bugs early」)。 ↩ -
出处:同章第 249–277 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:256,搜「for (items) |value|」;text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:274,搜「is 16」)。 ↩ ↩2 -
出处:同章第 279–303 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:300,搜「items[0..2]」;text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:300,搜「grabbing elements from index 0」)。 ↩ -
出处:同章第 307–333 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:319,搜「for (items, 0..)」;text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:327,搜「infinite range starting from zero」)。 ↩ -
出处:同章第 336–350 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:343,搜「for (0..5)」)。 ↩ -
出处:同章第 352–378 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:365,搜「for (items1, items2)」;text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:377,搜「ends up being 21」)。 ↩ ↩2 -
出处:同章第 374–376 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:375,搜「in lockstep」)——「If not, expect fireworks—or at least a runtime error」。 ↩ -
出处:同章第 379–414 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:391,搜「stoppedEarly = for」;text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:413,搜「Sum of items: 4」)。 ↩ ↩2 -
出处:同章第 416–442 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:425,搜「outer: for (1..6)」;text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:428,搜「break :outer」)。 ↩ ↩2 -
出处:同章第 444–471 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:454,搜「continue :outer」)。 ↩ ↩2 -
出处:同章第 471 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:471,搜「only you understand your code」)。 ↩ -
出处:同章第 473–504 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:483,搜「inline for (nums)」;text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:498,搜「unroll at compile time」)。 ↩ -
出处:同章第 506–512 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:511,搜「Use inline loops sparingly」)。 ↩ ↩2 -
出处:同章第 536–539 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:538,搜「very similar to for loops」)。 ↩ ↩2 -
出处:同章第 947–954 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:947,搜「execute an expression at the end」)。答案 d 见第 954 段。 ↩ ↩2 -
出处:同章第 514–524 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:519,搜「smarter than you」)。 ↩ ↩2 ↩3 -
出处:同章第 568–593 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:569,搜「might be present or might be null」;text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:580,搜「if (maybeValue) |value|」)。 ↩ ↩2 -
出处:同章第 603–622 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:606,搜「maybeX and maybeY」)。 ↩ ↩2 -
出处:同章第 623–634 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:627,搜「null pointer dereferencing」;text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:632,搜「forget to handle the null case」)。 ↩ -
出处:同章第 636–643 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:640,搜「maybeNumber orelse 0」)。 ↩ ↩2 -
出处:同章第 644–650 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:645,搜「Handle null early」)。 ↩ -
出处:同章第 652–683 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:665,搜「[_]?i32{ 1, null, 3, null, 5 }」)。 ↩ -
出处:同章第 690–742 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:710,搜「light: switch」;text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:713,搜「continue :light 2」)。 ↩ ↩2 -
出处:同章第 746–785 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:752,搜「vending: switch」)。 ↩ ↩2 -
出处:同章第 797–804 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:799,搜「State management」)。 ↩ -
出处:同章第 846–855 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:851,搜「perfectly predictable branches」;text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:853,搜「distinct conditional branch」)。 ↩ ↩2 -
出处:同章第 806–844 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:812,搜「while (true)」;text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:842,搜「more verbose」)。 ↩ -
出处:同章第 862–870 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:864,搜「Handling state transitions」)。 ↩ -
出处:同章第 892–990 段(
text/10-ch04-chapter-4-control-flow-loops-and-other-forms-of-.txt:892,搜「Testing your knowledge」)。 ↩