2013-06-05 658 views
1

我這有,但它是如此短暫,我幾乎肯定我失去了一些東西:如何檢查兩個字典是否包含相同的值?

public static bool ValueEquals<TKey, TValue> 
    (this IDictionary<TKey, TValue> source, IDictionary<TKey, TValue> toCheck) 
{ 
    if (object.ReferenceEquals(source, toCheck)) 
     return true; 
    if (source == null || toCheck == null || source.Count != toCheck.Count) 
     return false; 
    return source.OrderBy(t => t.Key).SequenceEqual(toCheck.OrderBy(t => t.Key)); 
} 

所以基本上,如果他們有一個平等的引用,返回true。如果它們中的任何一個是null或者它們的計數不同,則返回false。然後返回,如果序列(按鍵,然後它們的值排序)是相同的。我必須缺少的東西,因爲它太短,不夠好。

+0

對不起!我不小心按下了輸入!它尚未完成! –

+2

只是爲了澄清,你想要相同的值*爲相同的鍵*? (你的問題標題只提及值,這是不同的。) –

+0

@JonSkeet我的意思是一般意義上的值,而不是'Dictionary'的價值意義。所以如果我有兩個'string'和'bool'字典,它們是'{「true」,true},{「false」,false},另一個是'{「false」,false},{ 「真實的」,「真實的」,他們會是平等的。抱歉,模棱兩可。 –

回答

4

是的,只要所有的密鑰都實現IComparable,並且密鑰和值都有一個Equals方法來比較您想要比較的內容,那麼您的代碼將起作用。如果鍵或值沒有這些方法的適當實現,那麼這將不起作用。

您的方法也不提供自定義的IComparerIEqualityComparer對象的功能,以解決對象沒有合理實現其中一種方法的情況。無論這是你的特定情況下的問題,我們不能說。

您的解決方案也需要排序的所有值,這是有點比的設定等於其他可能的實施效率較低的,但它不是大幅差,所以如果你沒有特別大的集合是不該」這是一個巨大的問題。

相媲美的功能,你的方法,但改善的速度會(讓你擁有前兩個檢查):

return !source.Except(toCheck).Any(); 

由於這種方法不依賴於排序它也提供不需要的好處TKey執行IComparable

一個重要原因,無論這種方法,你的方法效果是由於KeyValuePair覆蓋它的EqualsGetHashCode定義是基於它自己的參考,而是對密鑰並將其包裝價值的事實。如果密鑰和值都相等,則兩個KeyValuePairs是相等的,並且哈希碼包含密鑰和值的哈希碼。

+0

感謝此:) –

+0

速度可以進一步提高,我想如果通過一個字典枚舉,試圖從另一個字典中讀取每個值,並確保讀取了一個值,並且它與源中的值匹配。不需要建立交集。 – supercat

+0

@supercat如果它們相同,它們會變得更快並且速度更慢,但是如果它們是相同的,我會將它們包括在內,這可能是值得的。 – Servy

相關問題