在显式实现接口时,是否有更好的方法在C#中编写这个重复的事件声明代码?

Dam*_*ire 2 c# events refactoring boilerplate

我有很多代码,如下所示,我明确地实现了接口所需的一些事件.

public class IMicrowaveNotifier {
  event EventHandler<EventArgs> DoorClosed;
  event EventHandler<EventArgs> LightbulbOn;
  // ...
}

public class Microwave : IMicrowaveNotifier {
  private EventHandler<EventArgs> _doorClosed;
  event EventHandler<EventArgs> IMicrowaveNotifier.DoorClosed {
    add { lock (this) _doorClosed += value; }
    remove { lock (this) _doorClosed -= value; }
  }

  private EventHandler<EventArgs> _lightbulbOn;
  event EventHandler<EventArgs> IMicrowaveNotifier.LightbulbOn {
    add { lock (this) _lightbulbOn += value; }
    remove { lock (this) _lightbulbOn -= value; }
  }

  // ...
}
Run Code Online (Sandbox Code Playgroud)

你可以看到很多这是样板.在Ruby中,我可以做这样的事情:

class Microwave
  has_events :door_closed, :lightbulb_on, ...
end
Run Code Online (Sandbox Code Playgroud)

在C#中有没有类似的更短的方法来删除这个样板?


更新:我从我的示例中留下了一个非常重要的部分:即,实现的事件是接口的一部分,我想明确地实现它.很抱歉没有提到这个!

And*_*are 10

试试这个:

public class Microwave {
    public event EventHandler<EventArgs> DoorClosed;
    public event EventHandler<EventArgs> LightbulbOn;
}
Run Code Online (Sandbox Code Playgroud)

此代码利用C#的字段式事件语法:

编译类似字段的事件时,编译器会自动创建存储以保存委托,并为事件创建访问器,以便向委托字段添加或删除事件处理程序.

在C#1,2和3中,此代码将编译为您上面的内容.在C#4中,您将获得不使用显式锁的功能等效代码.无论哪种方式,您都可以使用此快捷方式而无需更改此类型的使用者.

更新: 不幸的是,C#编译器不允许您使用类似字段的事件来实现显式接口.如果您尝试,将收到此编译错误:

事件的显式接口实现必须使用事件访问器语法

更新:显式接口实现需要使用事件访问器语法,这太糟糕了.如果C#添加了创建自动实现的类似字段的事件的能力,那将会很酷:

event EventHandler<EventArgs> IAppliance.DoorClosed { add; remove; }
Run Code Online (Sandbox Code Playgroud)

但是这种语法已经比现有的类字段事件语法更加冗长,并且只适用于显式实现接口成员的情况.我认为最好的事情是编译器只是允许我们这样做:

event EventHandler<EventArgs> IAppliance.DoorClosed;
Run Code Online (Sandbox Code Playgroud)