如果枚举在枚举列表中,则进行简单比较

本文关键字:枚举 比较 简单 列表 如果 | 更新日期: 2023-09-27 18:12:15

我有以下枚举:

public enum Materials { Wood, Stone, Earth, Water, Lava, Air }

现在我有3种可以行走的材料(木头、石头、泥土(和3种不能行走的物质(水、熔岩、空气(

如果一面旗帜是三种旗帜中的一种,我想进行比较。

目前,我是这样做的:

Materials myMat = Materials.Earth;
if ( myMat == Materials.Earth || myMat == Materials.Wood || myMat == Materials.Stone)
{
    I can walk on myMat...
}

难道不可能创建一个像Materials.Walkable这样的新标志吗?它将包括这三种材料,所以我可以只使用

if ( myMat == Materials.Walkable )

如果这是可能的,我该怎么做?

提前感谢;(

如果枚举在枚举列表中,则进行简单比较

您可以创建一个扩展方法:

public static bool IsWalkable(this Materials myMat )
{
    return myMat == Materials.Earth || myMat == Materials.Wood || myMat == Materials.Stone; 
    // alternatively:
    return new[] { Materials.Earth,  Materials.Wood,  Materials.Stone }.Contains(myMat);
}

并将其用作:

Materials myMat = ...
bool isMyMatWalkable = myMat.IsWalkable();

如果你愿意,你也可以使用[Flags]枚举:

[Flags]
public enum Materials
{
   None = 0,
   Wood = 1,
   Stone = 1 << 1,
   Earth = 1 << 2,
   Water = 1 << 3,
   Lava = 1 << 4,
   Air = 1 << 5,
   Walkable = Wood | Earth | Stone
}

然后你可以做:

Materials myMat = ..
bool isMyMatWalkable = (myMat & Materials.Walkable) != Materials.None;
System.Enum.GetValues(typeof(Materials)).Contains(myValue)

反射允许您获取枚举的所有值,然后检查它是否存在。虽然,我不确定你是否能解决你试图做的逻辑。

如果我理解你的"逻辑"问题,你可能必须把它变成类,这些类也有一个标志来表示它们是否可行走。允许您使用linq进行查询:

var walkableAreas = AllAreas.Where(area => area.walkable);
if(walkableAreas.Contains(myArea) { //dostruff // }

这是伪代码,但我希望你明白我要解释的。使用枚举,您只能有一个值,并且必须始终在if语句中硬编码哪些是可遍历的,哪些是不可遍历的。

也许您应该使用具有继承性的类,而不仅仅是使用Enum。这将允许您定义所有类型的属性。

public abstract class Material
{
    public abstract bool Walkable();
}

public class Wood : Material
{
    public bool Walkable()
    {
         return true;
    }
}
public class Lava: Material
{
    public bool Walkable()
    {
         return false;
    }
}

您会考虑用实体替换枚举吗?

public class Material
{
    public string Name {get; set;}
    public bool IsWalkable {get; set;}
}

然后你可以进行"直观"操作,如

Materials.Where(m => m.IsWalkable)

您可以尝试创建自定义属性来标记您的材料

public enum Materials
{
    [Walkable(true)]
    Wood,
    [Walkable(true)]
    Stone,
    [Walkable(true)]
    Earth,
    [Walkable(false)]
    Water,
    [Walkable(false)]
    Lava,
    [Walkable(false)]
    Air
}
public class WalkableAttribute : Attribute
{
    public WalkableAttribute(bool value)
    {
        IsWalkable = value;
    }
    public bool IsWalkable { get; private set; }
}

然后使用扩展检查它是否是可行走

public static class  MaterialsExtemsion
{
    public static bool IsWalkable(this Materials material)
    {
        var attribute = material.GetType().GetMember(material.ToString()).First().GetCustomAttributes(typeof(WalkableAttribute), false).FirstOrDefault();
        return attribute != null && ((WalkableAttribute) attribute).IsWalkable;
    }
}

然后使用

        Materials material1 = Materials.Stone;
        bool result  = material1.IsWalkable();  // return true
        Materials material2 = Materials.Air;
        bool result  = material2.IsWalkable();  // return false