Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
468 views
in Technique[技术] by (71.8m points)

language design - Why is F#'s type inference so fickle?

The F# compiler appears to perform type inference in a (fairly) strict top-to-bottom, left-to-right fashion. This means you must do things like put all definitions before their use, order of file compilation is significant, and you tend to need to rearrange stuff (via |> or what have you) to avoid having explicit type annotations.

How hard is it to make this more flexible, and is that planned for a future version of F#? Obviously it can be done, since Haskell (for example) has no such limitations with equally powerful inference. Is there anything inherently different about the design or ideology of F# that is causing this?

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

Is there anything inherently different about the design or ideology of F# that is causing this?

Yes. F# uses nominal rather than structural typing because it is simpler and, therefore, easier for mere mortals to use.

Consider this F# example:

let lengths (xss: _ [] []) = Array.map (fun xs -> xs.Length) xss

let lengths (xss: _ [] []) = xss |> Array.map (fun xs -> xs.Length)

The former does not compile because the type of xs inside the anonymous function cannot be inferred because F# cannot express the type "some class with a Length member".

In contrast, OCaml can express the direct equivalent:

let lengths xss = Array.map (fun xs -> xs#length) xss

because OCaml can express that type (it is written <length: 'a ..>). Note that this requires more powerful type inference than either F# or Haskell currently have, e.g. OCaml can infer sum types.

However, this feature is known to be a usability issue. For example, if you screw up elsewhere in the code then the compiler has not yet inferred that the type of xs was supposed to be an array so any error message it can give can only provide information like "some type with a Length member" and not "an array". With only slightly more complicated code, this quickly gets out of control as you have massive types with many structurally inferred members that don't quite unify, leading to incomprehensible (C++/STL-like) error messages.


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...