我想将KeyValuePair<T,U>
添加到Dictionary<T, U>
,但我不能。我必须分别传递密钥和值,这必然意味着Add方法必须创建一个新的KeyValuePair对象来插入,这不是非常有效。我无法相信Add方法上没有Add(KeyValuePair<T, U>)
重载。任何人都可以提出这种明显疏忽的可能原因吗?
答案 0 :(得分:32)
您可以使用提供IDictionary<TKey,TValue>
方法的Add(KeyValuePair<TKey,TValue>)
界面:
IDictionary<int, string> dictionary = new Dictionary<int, string>();
dictionary.Add(new KeyValuePair<int,string>(0,"0"));
dictionary.Add(new KeyValuePair<int,string>(1,"1"));
答案 1 :(得分:32)
备份一分钟......在走向疏忽之路之前,你应该确定创建一个新的KeyValuePair是否真的如此低效。
首先,Dictionary类在内部不是作为一组键/值对实现的,而是作为一堆数组实现的。除此之外,让我们假设它只是一组KeyValuePairs并着眼于效率。
首先要注意的是KeyValuePair是一个结构。真正的含义是必须将它从堆栈复制到堆中才能作为方法参数传递。当KeyValuePair添加到字典中时,必须再次复制它以确保值类型语义。
为了将Key和Value作为参数传递,每个参数可以是值类型或引用类型。如果它们是值类型,则性能将与KeyValuePair路由非常相似。如果它们是引用类型,这实际上可以是更快的实现,因为只需要传递地址并且必须进行非常少的复制。在最佳情况和最差情况下,由于KeyValuePair结构本身的开销增加,此选项略好于KeyValuePair选项。
答案 2 :(得分:14)
有这样一种方法 - ICollection<KeyValuePair<K, T>>.Add
但是因为显式实现了你需要将你的字典对象转换为该接口来访问它。
((ICollection<KeyValuePair<KeyType, ValueType>>)myDict).Add(myPair);
见
Dictionary<K, T>
文档页面上的显式接口实现列表(您需要向下滚动)。此方法的page包含一个示例。
答案 3 :(得分:2)
如果有人真的想这样做,这里有一个扩展
public static void Add<T, U>(this IDictionary<T, U> dic, KeyValuePair<T, U> KVP)
{
dic.Add(KVP.Key, KVP.Value);
}
但如果没有真正需要这样做,我建议不要这样做
答案 4 :(得分:2)
除非我弄错了,否则.NET 4.5和4.6增加了将KeyValuePair添加到Dictionary的功能。 (如果我错了,请通知我,我会删除这个答案。)
https://msdn.microsoft.com/en-us/library/cc673027%28v=vs.110%29.aspx
从上面的链接中,相关的信息就是这个代码示例:
public static void Main()
{
// Create a new dictionary of strings, with string keys, and
// access it through the generic ICollection interface. The
// generic ICollection interface views the dictionary as a
// collection of KeyValuePair objects with the same type
// arguments as the dictionary.
//
ICollection<KeyValuePair<String, String>> openWith =
new Dictionary<String, String>();
// Add some elements to the dictionary. When elements are
// added through the ICollection<T> interface, the keys
// and values must be wrapped in KeyValuePair objects.
//
openWith.Add(new KeyValuePair<String,String>("txt", "notepad.exe"));
openWith.Add(new KeyValuePair<String,String>("bmp", "paint.exe"));
openWith.Add(new KeyValuePair<String,String>("dib", "paint.exe"));
openWith.Add(new KeyValuePair<String,String>("rtf", "wordpad.exe"));
...
}
可以看出,创建了一个类型为Dictionary的新对象,并将其称为openWith
。然后创建一个新的KVP对象,并使用openWith
方法将其添加到.Add
。
答案 5 :(得分:1)
只是因为Dictionary类的枚举器返回KeyValuePair,并不意味着它是如何在内部实现的。
如果你真的需要传递KVP,请使用IDictionary,因为你已经以这种格式获得了它们。否则使用赋值或只使用Add方法。
答案 6 :(得分:0)
将它作为扩展名添加到项目中会出现什么问题?
namespace System.Collection.Generic
{
public static class DictionaryExtensions
{
public static void AddKeyValuePair<K,V>(this IDictionary<K, V> me, KeyValuePair<K, V> other)
{
me.Add(other.Key, other.Value);
}
}
}
答案 7 :(得分:-2)
我不是百分百肯定,但我认为Dictionary的内部实现是一个哈希表,这意味着键被转换为哈希以执行快速查找。
如果您想了解有关哈希表的更多信息,请阅读此处