为什么F#的类型推断不能解决这个问题? [英] Why can't F#'s type inference handle this?
问题描述
我有一个FileInfo序列,但是我只关心它们的字符串名称,所以我想要一个字符串序列.一开始我尝试过这样的事情:
I have a sequence of FileInfo, but I only care about their string names, so I want a sequence of string. At first I tried something like this:
Seq.map (fun fi -> fi.Name) fis
但是由于某种原因,F#的类型推断不足以允许这种情况,并让我显式地将类型指定为"fi":
But for some reason, F#'s type inference isn't good enough to allow this, and made me explicitly give a type to "fi":
Seq.map (fun (fi : FileInfo) -> fi.Name) fis
为什么需要此注释?如果知道fis : seq<FileInfo>
和Seq.map : ('a -> 'b) -> seq<'a> -> seq<'b>
,那么是否不应该推断lambda表达式的类型为FileInfo -> 'b
,然后从fi.Name : string
进一步推断其类型为FileInfo -> string
?
Why is this annotation required? If it is known that fis : seq<FileInfo>
and that Seq.map : ('a -> 'b) -> seq<'a> -> seq<'b>
, then shouldn't it infer that the type of the lambda expression is FileInfo -> 'b
, and then, from fi.Name : string
, further infer that its type is FileInfo -> string
?
推荐答案
类型推断从左到右起作用.这是管道运算符有用的地方;如果您已经知道"FIS"的类型,则将其写为
Type inference works left-to-right. This is where the pipeline operator is useful; if you already know the type of 'fis', then write it as
fis |> Seq.map (fun fi -> fi.Name)
然后推论对您有用.
(通常是以下形式的表达式
(In general, expressions of the form
o.Property
o.Method args
要求先验已知的'o'的类型;对于大多数其他表达式,当没有固定类型时,推理系统可以浮动一个约束",以后可以解决,但对于这些情况,不存在所有具有名为P的属性的类型"或"所有带有名为M的方法的类型"(例如鸭类输入法)都可以推迟,以后再解决.因此,您现在需要该信息,否则推断将立即失败.)
require the type of 'o' to be known a priori; for most other expressions, when a type is not pinned down the inference system can 'float a constraint' along that can be solved later, but for these cases, there are no constraints of the form 'all types with a property named P' or 'all types with a method named M' (like duck typing) that can be postponed and solved later. So you need that info now, or inference fails immediately.)
另请参见 F#中类型推断的概述.
这篇关于为什么F#的类型推断不能解决这个问题?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!