Skip to Content

匹配(Match)

match 把一个值对照一串模式逐个测试,命中哪条臂就执行哪条臂。它是表达式也是语句,两种形态共用同一套匹配机器和穷尽性检查。模式的全部形态见模式一页。

基本形态

臂的形状是 模式 => 臂体,臂与臂之间用逗号分隔,末臂尾逗号可选。臂体可以是表达式、块、或 return / fail 开头的控制流:

enum Shape { Circle(radius: float), Rect(w: float, h: float), Point, } func Area(s: Shape) -> float { return match s { Shape.Circle(r) => 3.14159 * r * r, Shape.Rect(w, h) => w * h, Shape.Point => 0.0, }; } print(Area(Shape.Circle(2.0)), Area(Shape.Rect(3.0, 4.0)), Area(Shape.Point));
12.56636 12 0

Shape.Circle(r) 既测试变体又把载荷解构进 r。

when 守卫

臂后面可以跟 when 条件 做二次筛选,条件必须产出 bool。守卫不计入穷尽性覆盖:

func Describe(n: int) -> string { return match n { 0 => "零", x when x < 0 => "负数", x when x < 10 => "个位数", _ => "两位以上", }; } print(Describe(-5), Describe(0), Describe(7), Describe(42));
负数 零 个位数 两位以上

守卫臂命中后,臂头模式里的绑定(这里的 x)在臂体内可用。

穷尽性检查

match 强制穷尽:所有可能取值都必须有对应臂处理,漏了报 MS4001,并列出未覆盖的情况。守卫与列表模式不算覆盖,兜底一律用 _:

error MS4001: match is not exhaustive: uncovered case(s) Point.

match 作语句时同样检查穷尽性,不是结果没人用就放行。

臂类型统一

match 表达式全部臂的类型必须统一成一种,混用报 MS3254:

error MS3254: match arm body types do not unify: 'string' vs 'int32'.

需要不同形态的结果时,把每臂都做成字符串或元组等同一类型。

match 语句

结果无人消费时写语句形,臂体多为副作用。臂间逗号规则不变:

val n = 2; match n { 1 => print("一"), 2 => print("二"), _ => print("很多"), }
二

注意

  • 对错误值(error)的匹配与 recover 消费同一套穷尽口径,见失败与崩溃;
  • 分支逻辑很平(只比大小)时用 if 表达式更轻,涉及结构拆解时再上 match。
最后更新于 2026年10月9日