为什么变量在模式中绑定两次?

时间:2012-12-07 10:59:52

标签: f# pattern-matching

通常,F#不允许模式变量在同一模式中出现两次。但是在下面的代码中,F#并没有抱怨 - 这是一个错误吗?

type foo = { A: int }
let test (x, {A = x}) = x
let result = test ("bla", {A = 3})

1 个答案:

答案 0 :(得分:5)

我不认为这是一个错误,虽然看起来很混乱,但它只是编译器编译上述值绑定的方式。

第14.6.3节规定,如果值定义不是单个值模式(如此处所示),则精心设计的表达式为

tmp <typars1… typarsn> = expr
ident1 <typars1> = expr1
…
identn <typarsn> = exprn

其中tmp是一个新的标识符,每个expri都来自模式pat(§7)对输入tmp [来自spec]的编译。

要查看编译器的作用,我们可以使用F#引用,例如:

<@ let test (x:int, {A = x:int})= x in test (3, {A = 5}) @>;;

我以字符串格式得到(留下一些东西):

Let (test,
     Lambda (tupledArg,
             Let (x, TupleGet (tupledArg, 0),
                  Let (_arg1, TupleGet (tupledArg, 1),
                       Let (x, PropertyGet (Some (_arg1), A, []), x)))),
     Application (test, NewTuple (Value (3), NewRecord (foo, Value (5)))))

这就是为什么我们得到“内在的”x。

我不认为这是一个错误,但如果这会产生警告,也许会更加一致。