C# 无两个值幂的标志枚举

C# 无两个值幂的标志枚举,c#,enums,code-analysis,static-analysis,C#,Enums,Code Analysis,Static Analysis,标志的属性表示您应该: 以2的幂定义枚举常数,即1,2,4,8, 等等这意味着组合枚举中的各个标志 常数不重叠 …当然,我总是努力记住要这样做。但是,没有什么可以强制执行这一点,如果您只是以“基本”方式创建枚举,如 [Flags] public enum BrokenEnum { None, FirstOption, SecondOption, ThirdOption } …它的行为将不符合预期。为了解决这个问题,我正在寻找一种静态代码分析(比如),当我的代码中

标志的属性表示您应该:

以2的幂定义枚举常数,即1,2,4,8, 等等这意味着组合枚举中的各个标志 常数不重叠

…当然,我总是努力记住要这样做。但是,没有什么可以强制执行这一点,如果您只是以“基本”方式创建枚举,如

[Flags]
public enum BrokenEnum
{
    None,
    FirstOption,
    SecondOption,
    ThirdOption
}
…它的行为将不符合预期。为了解决这个问题,我正在寻找一种静态代码分析(比如),当我的代码中存在类似上面的枚举时,它可以警告我。我能找到的最接近此类警告是“”-这对正确设计标志枚举也有帮助,但还不够


在我的代码中查找设计错误的标志枚举的最佳方法是什么?解决方案的自动化程度越高越好。

有时您希望有一个代表多个选项的标志枚举;在这种情况下,这不是一个错误。下面是一个常见的例子:

[Flags]
public enum FilePermissions
{
    None = 0,
    Read = 1,
    Write = 2,
    Execute = 4,

    ReadWrite = 3, // Read | Write,
    ReadWriteExecute = 7 // Read | Write | Execute
}

也许是因为需要支持这样的情况,这就是为什么编译器不会导致警告或错误。

我自己从未尝试过,但也许您可以为FxCop编写自定义规则


检查。

正如雅各布所说,混合使用旗帜可能会很有用。。。但你可能会以某种方式表明,这样你的检测就不会介意了

编写一个单元测试应该不会太难,它将遍历用
[Flags]
修饰的程序集中的每个枚举,并检查是否有0的值(可能会确保它被称为
None
Default
),并且每个其他定义的值(来自
enum.GetValues()
)都是二的幂。您可以使用
如果((x&(x-1))==0)
检查

您可能会有类似于属性
[Combination]
的内容来指示设计为组合的值。。。它们甚至可以指出它们是什么标志名称的组合,所以你也可以检查一下


我知道这不如编译时检查好,但假设您已经定期运行测试,这非常接近。

我可以看到编译器不这样做的原因(同时考虑向后兼容性、不合理的复杂性等),所以我很高兴您没有收到编译器警告。但我仍在寻找一种被警告的方式。在像您这样的情况下,如果使用有效,您可以使用
SuppressMessage
属性禁用检查。您还可以使用更精细的标志。例如
{View=1,Alter=2,Action=4 | View | Alter}
:因此,要操作一个项目,您需要查看和更改;除了权利本身。谢谢,这看起来很有希望。我可能会坚持Jon Skeet的答案,因为我认为在短期内编写单元测试比学习如何编写自定义FxCop规则更快。我想我不应该考虑静态代码分析的“盒子内部”。像这样的单元测试应该非常简单,并且给出几乎相同的最终结果。