2

列挙型は確かに混乱する可能性があります。列挙型に値を取り、一致するすべてのビットの名前を返す拡張メソッドを作成しようとしています。

与えられた:

[Flags]
public enum PlanetsEnum
{
  Mercury=1,
  Venus=2,
  Earth=4,
  Mars=8,
  Jupiter=16,
  //etc....
}

選択した値のみのディクショナリを返す拡張メソッドを作成したいと思います。したがって、次の場合:

PlanetsEnum neighbors = PlanetsEnum.Mars | PlanetEnum.Venus; //10

IDictionary dict = neighbors.ToDictionary();

foreach (KeyValuePair<String, Int32> kvp in dict)
{
  Console.WriteLine(kvp.Key);
}

/*
*  Should Print:
*      Mars
*      Venus
*/

火星と金星がコンソールに書き込まれることを期待しますが、代わりにPlanetEnumのすべての値が表示されます。これが私の拡張メソッドコードです:

public static IDictionary<string, Int32> ToDictionary(this Enum enumeration)
{
  Type type = enumeration.GetType();
  return Enum.GetValues(type).Cast&lt;Int32>().ToDictionary(field => Enum.GetName(type, field));
}

誰かが私が間違っていることを見ていますか?列挙型のすべてのフィールドを返すことを知っていEnum.GetValuesますが、列挙型インスタンスのフィールドのみを返すようにするにはどうすればよいですか?

助けてくれてありがとう、

キース

4

3 に答える 3

3

これがあなたがやろうとしていることのLINQ化されたバージョンです。欠落している重要なビットは、現在の値をチェックすることです。

public static IDictionary<string, int> ToDictionary(this Enum enumeration)
{
    int value = (int)(object)enumeration;
    return Enum.GetValues(enumeration.GetType()).OfType<int>().Where(v => (v & value) == value).ToDictionary(v => Enum.GetName(enumeration.GetType(), v));
}

編集:(int)(object)enumerationキャスト を行う理由についての簡単な説明:

ビット単位の演算子は、整数型(intなど)とブール値に対してのみ機能しますが、Enumをintに直接キャストすることはできません。したがって、オブジェクトにダウンキャストし、それが実際にintを基になる型として表すと想定する必要があります。コンパイラーはオブジェクトをintにキャストできるようにします列挙が整数ベースでない場合、これは実行時例外をスローします。

于 2010-02-03T21:57:00.657 に答える
2

次のことを試してください。これは、int32である列挙型に対してのみ機能します

public static IDictionary<String, Int32> ToDictionary(this Enum enumeration)
{
    var map = new Dictionary<string, int>();
    var value = (int)(object)enumeration;
    var type = enumeration.GetType();
    foreach (int cur in Enum.GetValues(type))
    {
        if (0 != (cur & value))
        {
            map.Add(Enum.GetName(type, cur),cur);
        }
    }
    return map;
}
于 2010-02-03T21:49:23.483 に答える
1
public enum CustomerType
{
    Standard = 0,
    Trade = 1
}

ddCustomerTypes.DataSource = (new Domain.CustomerType()).ToDictionary();
ddCustomerTypes.DataBind();

public static class EnumExtensionMethods
{
    public static Dictionary<string, object> ToDictionary(this Enum enumeration)
    {
        Array names = Enum.GetNames(enumeration.GetType());

        Dictionary<string, object> dictionary = new Dictionary<string, object>();

        foreach (string name in names)
        {
            dictionary.Add(name, typeof(Domain.CustomerType).GetField(name).GetRawConstantValue() );
        }

        return dictionary;
    }

    public static List<KeyValuePair<string, object>> ToList(this Enum enumObject)
    {
        return enumObject.ToDictionary().ToList();
    }
}
于 2011-07-07T07:24:40.007 に答える