我有以下代码(示例),我真的不喜欢这么多'if'检查:
public enum Flags
{
p1 = 0x01, // 0001
p2 = 0x02, // 0010
p3 = 0x04, // 0100
p4 = 0x08 // 1000
};
public static void MyMethod (Flags flag)
{
if ((flag & Flags.p1) == Flags.p1)
DoSomething();
if ((flag & Flags.p2) == Flags.p2)
DosomethingElse();
if ((flag & Flags.p3) == Flags.p3)
DosomethingElseAgain();
if ((flag & Flags.p4) == Flags.p4)
DosomethingElseAgainAndAgain();
}
MyMethod(Flags.p1 | Flags.p3);
有没有办法,我可以使用'switch'语句。也许如果我将它们转换为字符串,或使用数组?
答案 0 :(得分:8)
这样的东西?
public static void MyMethod(Flags flag)
{
// Define action-lookup
var actionsByFlag = new Dictionary<Flags, Action>
{
{ Flags.p1, DoSomething},
{ Flags.p2, DosomethingElse},
{ Flags.p3, DosomethingElseAgain},
{ Flags.p4, DosomethingElseAgainAndAgain},
};
// Find applicable actions
var actions = actionsByFlag.Where(kvp => (flag & kvp.Key) == kvp.Key)
.Select(kvp => kvp.Value);
//Execute applicable actions
foreach (var action in actions)
action();
}
编辑:如果操作顺序很重要,则可能需要OrderBy
条款。
答案 1 :(得分:6)
以下是Ani答案的变体:
public static void MyMethod(Flags flag)
{
// Define action-lookup
var dict = new Dictionary<Flags, Action>
{
{ Flags.p1, DoSomething},
{ Flags.p2, DosomethingElse},
{ Flags.p3, DosomethingElseAgain},
{ Flags.p4, DosomethingElseAgainAndAgain},
};
// Find applicable actions
var actions = from value in Enum.GetValues(typeof(Flags))
where flag.HasFlag(value)
select dict[value];
//Execute applicable actions
foreach (var action in actions)
action();
}
这里的重要区别在于它迭代枚举中定义的值而不是字典中的条目。这样,如果向枚举添加新标志而不将其添加到字典中,则在尝试使用新标志时会出现异常。它总是按标志的顺序迭代。