当交换机不处理一个或多个枚举值时,我可能有C#编译时错误吗?

sha*_*oth 6 .net c# compile-time

假设我有一个switch包含枚举的变量:

SomeEnum variable;
switch( variable ) {
   case Option1:
      Magic1;
      break;
   case Option2:
      Magic2;
      break;
   default:
      throw new InvalidOperationException();
}
Run Code Online (Sandbox Code Playgroud)

并且我知道switch必须处理所有可能的枚举值,以便如果在枚举中添加新值,则switch必须更改,这就是我添加的default引发异常的原因.

问题是没有错误指示,直到代码运行并且控制通过default并抛出异常(并且异常可以在调用堆栈的某处静音).

我想在这里遇到编译时错误.例如,当没有,并且一个或多个值未处理并且该警告可以被提升为错误时,Visual C++可以发出C4062警告default.我本可以default在代码中删除并使用该警告.

我可以在C#中使用类似的东西吗?

Jep*_*sen 12

不,你需要写一个单元测试.编译器不会为您执行此操作.

单元测试可能类似于:

public void TestSwitch()
{
    foreach (var variable in (SomeEnum[])Enum.GetValues(typeof(SomeEnum)))
        Assert.DoesNotThrow(() => YourMethod(variable), "Value {0} not supported", variable);
}
Run Code Online (Sandbox Code Playgroud)

取决于您的测试框架.

实际上,我认为,底层整数类型的任何值(例如,如果底层类型int几乎总是这样,所有4,294,967,296值都是可能的),你永远不会写那么多case标签.我知道你只想要带名字的值,但正如我所说,编译器不会为你检查.它只检查两个是否case引用相同的值.

我建议你把:

if (!Enum.IsDefined(typeof(SomeEnum), variable))
    throw new InvalidOperationException();
Run Code Online (Sandbox Code Playgroud)

在某个地方,如果你的枚举没有[Flags]属性,但它显然只能在运行时使用.