在F#中实现C#EventHandlers

lvi*_*nis 7 c# events f# interop

我有一个用C#编写的接口,定义如下:

public interface IWidget
{
    object Evaluate();
    event EventHandler Invalidated;
}
Run Code Online (Sandbox Code Playgroud)

当我尝试在F#中实现这个接口时,我会看看F#认为IWidget接口是什么(通过将鼠标悬停在它上面),我看到了

type IWidget = 
    interface
        member Evaluate : unit -> obj
    end
Run Code Online (Sandbox Code Playgroud)

它似乎完全忽略了Invalidated事件......这是F#的一个已知问题,如果有的话有什么方法可以解决它吗?在实现我的F#版本的IWidget时,我可以在IWidget部分之外实现此事件或者什么?f#处理"event"关键字这么糟糕......这似乎真的很讨厌......

更新:在进一步摆弄后,工作室然后说:

'没有给出IWidget.remove_Invalidate(value:EventHandler)的实现:unit'

然后,当我添加这些方法时,整个事情看起来像:

interface IWidget with
    member w.Evaluate() = new obj()
    member w.add_Invalidated(value:EventHandler) = ()
    member w.remove_Invalidated(value:EventHandler) = ()
end
Run Code Online (Sandbox Code Playgroud)

它编译得很好,即使工具提示仍然说IWidget的唯一成员是Evaluate()......似乎F#(或至少IDE)处理这些东西的方式真的很棘手......

另一个更新:根据IDE中的工具提示,[]标签允许将事件编译为CLI元数据事件,方法是将其转换为一对add_/remove_方法......对于任何被困惑的人来说都是FYI就像我一样.简而言之,要么实现这两个方法,要么使用该标记工作正常,尽管IWdiget接口的工具提示视图没有提到Invalidate事件,并且只有在编译器抛出时才会注意到实现这样的事件的必要性.错误,仍然是一个明显的错误,并且非常令人困惑.对于任何好奇的人,以下代码工作正常:

let invalidated = new DelegateEvent<System.EventHandler>()

interface IWidget with
    member w.Evaluate() = new obj()
    [<CLIEvent>]
    member w.Invalidated = invalidated.Publish
end
Run Code Online (Sandbox Code Playgroud)

谢谢各位的帮助!

SLa*_*aks 9

F#确实支持事件.

例如:

let invalidated = new DelegateEvent<System.EventHandler>()

[<CLIEvent>]
member this.Invalidated = invalidated.Publish
Run Code Online (Sandbox Code Playgroud)