Creating Delegates With Lambda Expressions in F#

↘锁芯ラ 提交于 2019-12-08 18:12:49

问题


Why does...

type IntDelegate = delegate of int -> unit

type ListHelper =
    static member ApplyDelegate (l : int list) (d : IntDelegate) =
        l |> List.iter (fun x -> d.Invoke x)

ListHelper.ApplyDelegate [1..10] (fun x -> printfn "%d" x)

not compile, when:

type IntDelegate = delegate of int -> unit

type ListHelper =
    static member ApplyDelegate (l : int list, d : IntDelegate) =
        l |> List.iter (fun x -> d.Invoke x)

ListHelper.ApplyDelegate ([1..10], (fun x -> printfn "%d" x))

does?

The only difference that is that in the second one, ApplyDelegate takes its parameters as a tuple.

This function takes too many arguments, or is used in a context where a function is not expected


回答1:


I haven't looked at the spec to confirm, but I am guessing that the implicit conversion from "lambda" to "named delegate type" only occurs in a "member invocations".

You can always make the conversion explicit:

ListHelper.ApplyDelegate [1..10] (IntDelegate(fun x -> printfn "%d" x))

(The error diagnostic is quite poor; I'll file a bug.)

EDIT:

For the wonks...

Yeah, the spec says

8.13.6 Type-directed Conversions at member invocations As described in Method Application Resolution (see §14.4), two type-directed conversions are applied at method invocations.

If a formal parameter is of delegate type DelegateType, and an actual argument is syntactically a function value (fun ...), then the parameter is interpreted as if it had been written new DelegateType(fun ...).

that lambdas get converted automagically to delegate types only at "member invocations". In the case of the curried member, the first argument passed is a member invocation, but then that returns a function value to apply the second argument, and function invocations do not have this implicit conversion rule.



来源:https://stackoverflow.com/questions/2783450/creating-delegates-with-lambda-expressions-in-f

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!