web-dev-qa-db-ja.com

値で辞書のキーを取得

C#の値で辞書キーを取得する方法

Dictionary<string, string> types = new Dictionary<string, string>()
{
            {"1", "one"},
            {"2", "two"},
            {"3", "three"}
};

私はこのようなものが欲しい:

getByValueKey(string value);

getByValueKey("one")"1"を返す必要があります。

これを行う最良の方法は何ですか?たぶんHashTable、SortedLists?

311
loviji

値は必ずしも一意である必要はないので、ルックアップを行う必要があります。あなたはこのようなことをすることができます:

var myKey = types.FirstOrDefault(x => x.Value == "one").Key;

値が一意で、読み取りよりも挿入頻度が低い場合は、値がキーでキーが値である逆辞書を作成します。

559
Kimi

あなたはそれをすることができます:

  1. ディクショナリ内のすべてのKeyValuePair<TKey, TValue>をループすることにより(ディクショナリに多数のエントリがある場合、これはかなりのパフォーマンスの低下になります)
  2. 2つの辞書を使用します。1つは値からキーへのマッピング用、もう1つはキーから値へのマッピング用です(メモリ内で2倍のスペースを占有します)。

パフォーマンスを考慮しない場合は方法1を、メモリを考慮しない場合は方法2を使用してください。

また、すべてのキーは一意である必要がありますが、値が一意である必要はありません。指定した値を持つキーが複数ある可能性があります。

キーと値の関係を逆にできない理由はありますか?

24
Zach Johnson

私は、Linqバインディングが利用できず、ラムダを明示的に拡張しなければならない状況にありました。それは簡単な関数に帰着しました:

public static string KeyByValue(Dictionary<string, string> dict, string val)
{
    string key = null;
    foreach (KeyValuePair<string, string> pair in dict)
    {
        if (pair.Value == val)
        { 
            key = pair.Key; 
            break; 
        }
    }
    return key;
}

次のように呼んでください。

public static void Main()
{
    Dictionary<string, string> dict = new Dictionary<string, string>()
    {
        {"1", "one"},
        {"2", "two"},
        {"3", "three"}
    };

    string key = KeyByValue(dict, "two");       
    Console.WriteLine("Key: " + key);
}

.NET 2.0およびその他の限られた環境で動作します。

2
Boris Zinchenko