我编写了一些测试代码来绕过泛型语法:
let add_stuff<'T> x y =
printfn "%A" (x + y)
let stuff() =
add_stuff 5.5 2.4
add_stuff 3 4
Run Code Online (Sandbox Code Playgroud)
第二次add_stuff调用无法编译。为什么是这样?为什么编译器不推断类型?
该代码有2个问题:
首先,'T任何参数都不使用泛型类型。参数需要声明为以下类型'T:
// val add_stuff: 'T -> 'T -> unit
let add_stuff<'T> (x:'T) (y:'T) =
printfn "%A" (x + y)
Run Code Online (Sandbox Code Playgroud)
这将创建一个新的错误消息:
在此不能使用声明的类型参数“ T”,因为在编译时无法解析类型参数
在这种情况下,问题在于+操作员。它使用静态解析的类型参数,这意味着您的函数也需要使用它们,这基本上意味着需要对其进行内联:
// val add_stuff: ^T -> ^T -> unit
let inline add_stuff (x:^T) (y:^T) =
printfn "%A" (x + y)
Run Code Online (Sandbox Code Playgroud)
请注意,类型签名的区别'T是通用类型,可以在运行时解决。^T是SRTP,需要在编译时解析,因此需要inline关键字。
如果您没有使用过+运算符,则无需内联它。注意之间的区别pair_stuff和add_stuff:
// val pair_stuff: 'T -> 'W -> unit
let pair_stuff (x:'T) (y:'W) =
printfn "%A" (x , y)
// val add_stuff: ^a -> ^b -> unit
let inline add_stuff x y =
printfn "%A" (x + y)
let stuff() =
add_stuff 5.5 2.4
add_stuff 3 4
pair_stuff 5.5 2.4
pair_stuff 3 4
stuff()
// 7.9
// 7
// (5.5, 2.4)
// (3, 4)
Run Code Online (Sandbox Code Playgroud)