Wartość domyślna dla KeyValuePair

392

Mam obiekt typu IEnumerable<KeyValuePair<T,U>> keyValueList, którego używam

 var getResult= keyValueList.SingleOrDefault();
 if(getResult==/*default */)
 {
 }
 else
 {
 } 

Jak mogę sprawdzić, czy getResultjest to ustawienie domyślne, w przypadku gdy nie mogę znaleźć właściwego elementu?

Nie mogę sprawdzić, czy tak jest, nullczy nie, ponieważ KeyValuePairjest strukturą.

Grawiton
źródło
1
Oto podobne pytanie z kilkoma interesującymi odpowiedziami: stackoverflow.com/q/793897/323071
Andre Luus
2
Możesz także powiedzieć getResult.Key! = Null, aby sprawdzić, czy lista jest pusta, tak jakby to był klucz, zawsze będzie pusta
pengibot
3
@pengibot Zakłada, że ​​klucz jest zerowalny.
Justin Skiles,

Odpowiedzi:

542

Spróbuj tego:

if (getResult.Equals(new KeyValuePair<T,U>()))

albo to:

if (getResult.Equals(default(KeyValuePair<T,U>)))
Andrew Hare
źródło
5
Możesz skorzystać z koncepcji opcji „nowa” tutaj, ale unikaj konieczności ponownego określania typu: if (getResult.Equals (Activator.CreateInstance (getResult.GetType ())))
kevinpo
3
myślę, że if (getResult.Equals(default))również działa
Simon
2
@ Simon nie nie. defaultrówna się zero. I default(KeyValuePair<T,U>)to rzeczywista KeyValuePair, która zawiera null, null. Sam tego doświadczyłem.
Yokovaski
100

Możesz utworzyć ogólną (i ogólną) metodę rozszerzenia, taką jak ta:

public static class Extensions
{
    public static bool IsDefault<T>(this T value) where T : struct
    {
        bool isDefault = value.Equals(default(T));

        return isDefault;
    }
}

Stosowanie:

// We have to set explicit default value '0' to avoid build error:
// Use of unassigned local variable 'intValue'
int intValue = 0;
long longValue = 12;
KeyValuePair<String, int> kvp1 = new KeyValuePair<String, int>("string", 11);
KeyValuePair<String, int> kvp2 = new KeyValuePair<String, int>();
List<KeyValuePair<String, int>> kvps = new List<KeyValuePair<String, int>> { kvp1, kvp2 };
KeyValuePair<String, int> kvp3 = kvps.FirstOrDefault(kvp => kvp.Value == 11);
KeyValuePair<String, int> kvp4 = kvps.FirstOrDefault(kvp => kvp.Value == 15);

Console.WriteLine(intValue.IsDefault()); // results 'True'
Console.WriteLine(longValue.IsDefault()); // results 'False'
Console.WriteLine(kvp1.IsDefault()); // results 'False'
Console.WriteLine(kvp2.IsDefault()); // results 'True'
Console.WriteLine(kvp3.IsDefault()); // results 'False'
Console.WriteLine(kvp4.IsDefault()); // results 'True'
pholpar
źródło
27

Spróbuj tego:

KeyValuePair<string,int> current = this.recent.SingleOrDefault(r => r.Key.Equals(dialog.FileName) == true);

if (current.Key == null)
    this.recent.Add(new KeyValuePair<string,int>(dialog.FileName,0));
Piotr
źródło
3
Oczywiście działa to tylko wtedy, gdy nigdy (przypadkowo lub celowo) nie dodasz wartości null jako klucza. Ale powiedziałbym, że to prawda przez większość czasu, więc dobry pomysł. Jest to zdecydowanie sposób na łatwiejszą kontrolę niż większość kontroli tutaj.
neminem,
3
Tak długo, jak klucz jest zerowalny.
Uri Abramson,
10
if(getResult.Key.Equals(default(T)) && getResult.Value.Equals(default(U)))
ChaosPandion
źródło
Jedyną rzeczą jest to, że się nie kompiluje. Zamiast tego należy użyć znaku równości.
Tamas Ionut
8

Polecam więcej zrozumienia sposobu przy użyciu metody rozszerzenia:

public static class KeyValuePairExtensions
{
    public static bool IsNull<T, TU>(this KeyValuePair<T, TU> pair)
    {
        return pair.Equals(new KeyValuePair<T, TU>());
    }
}

A następnie użyj:

var countries = new Dictionary<string, string>
{
    {"cz", "prague"},
    {"de", "berlin"}
};

var country = countries.FirstOrDefault(x => x.Key == "en");

if(country.IsNull()){

}
Miroslav Holec
źródło
7

Z oryginalnego kodu wygląda to tak, jakbyś chciał sprawdzić, czy lista była pusta:

var getResult= keyValueList.SingleOrDefault();
if (keyValueList.Count == 0)
{
   /* default */
}
else
{
}
Stephen Westlake - Infuzja
źródło
Możesz po prostu pominąć pierwszą linię, ponieważ nie jest używana.
HeyJude
0

Aby uniknąć boksowania KeyValuePair.Equals(object), możesz użyć ValueTuple.

if ((getResult.Key, getResult.Value) == default)
Jonas Nyrup
źródło