C# 字典和哈希表的区别

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/876656/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-05 05:05:49  来源:igfitidea点击:

Difference between Dictionary and Hashtable

c#collections

提问by blitzkriegz

Possible Duplicate:
Why Dictionary is preferred over hashtable in C#?

可能的重复:
为什么字典比 C# 中的哈希表更受欢迎?

What is the difference between Dictionary and Hashtable. How to decide which one to use?

字典和哈希表有什么区别。如何决定使用哪一个?

采纳答案by Marc Gravell

Simply, Dictionary<TKey,TValue>is a generic type, allowing:

简单地说,Dictionary<TKey,TValue>是一个泛型类型,允许:

  • static typing (and compile-time verification)
  • use without boxing
  • 静态类型(和编译时验证)
  • 不使用拳击

If you are .NET 2.0 or above, you should preferDictionary<TKey,TValue>(and the other generic collections)

如果你是 .NET 2.0 或更高版本,你应该更喜欢Dictionary<TKey,TValue>(和其他泛型集合)

A subtle but important difference is that Hashtablesupports multiple reader threads with a single writer thread, while Dictionaryoffers no thread safety. If you need thread safety with a generic dictionary, you must implement your own synchronization or (in .NET 4.0) use ConcurrentDictionary<TKey, TValue>.

一个微妙但重要的区别是,它Hashtable支持多个读取器线程和一个写入器线程,但不Dictionary提供线程安全。如果您需要通用字典的线程安全,则必须实现自己的同步或(在 .NET 4.0 中)使用ConcurrentDictionary<TKey, TValue>.

回答by Frans Bouma

Dictionary is typed (so valuetypes don't need boxing), a Hashtable isn't (so valuetypes need boxing). Hashtable has a nicer way of obtaining a value than dictionary IMHO, because it always knows the value is an object. Though if you're using .NET 3.5, it's easy to write an extension method for dictionary to get similar behavior.

字典是类型化的(所以值类型不需要装箱),哈希表不是(所以值类型需要装箱)。Hashtable 具有比字典 IMHO 更好的获取值的方法,因为它始终知道该值是一个对象。虽然如果您使用 .NET 3.5,很容易为字典编写扩展方法以获得类似的行为。

If you need multiple values per key, check out my sourcecode of MultiValueDictionary here: multimap in .NET

如果每个键需要多个值,请在此处查看我的 MultiValueDictionary 源代码: multimap in .NET

回答by SO User

The Hashtable class is a specific type of dictionary class that uses an integer value (called a hash) to aid in the storage of its keys. The Hashtable class uses the hash to speed up the searching for a specific key in the collection. Every object in .NET derives from the Object class. This class supports the GetHash method, which returns an integer that uniquely identifies the object. The Hashtable class is a very efficient collection in general. The only issue with the Hashtable class is that it requires a bit of overhead, and for small collections (fewer than ten elements) the overhead can impede performance.

Hashtable 类是一种特定类型的字典类,它使用整数值(称为散列)来帮助存储其键。Hashtable 类使用散列来加快在集合中搜索特定键的速度。.NET 中的每个对象都派生自 Object 类。该类支持 GetHash 方法,该方法返回唯一标识对象的整数。Hashtable 类通常是一个非常有效的集合。Hashtable 类的唯一问题是它需要一些开销,并且对于小集合(少于十个元素),开销可能会影响性能。

There is Some special difference between two which must be considered:

HashTable: is non-generic collection ,the biggest overhead of this collection is that it does boxing automatically for your values and in order to get your original value you need to perform unboxing , these to decrease your application performance as penalty.

Dictionary: This is generic type of collection where no implicit boxing, so no need to unboxing you will always get your original values which you were stored so it will improve your application performance.

the Second Considerable difference is:

if your were trying to access a value on from hash table on the basis of key that does not exist it will return null.But in the case of Dictionary it will give you KeyNotFoundException.

必须考虑两者之间的一些特殊区别:

HashTable:是非通用集合,这个集合的最大开销是它自动为您的值进行装箱,为了获得您的原始值,您需要执行拆箱,这些会降低您的应用程序性能作为惩罚。

字典:这是没有隐式装箱的通用类型的集合,因此无需拆箱,您将始终获得存储的原始值,因此它将提高您的应用程序性能。

第二个相当大的区别是:

如果您试图根据不存在的键访问哈希表中的值,它将返回 null。但在 Dictionary 的情况下,它将给您 KeyNotFoundException。

回答by Rohit Gupta

There is one more important difference between a HashTable and Dictionary. If you use indexers to get a value out of a HashTable, the HashTable will successfully return null for a non-existent item, whereas the Dictionary will throw an error if you try accessing a item using a indexer which does not exist in the Dictionary

HashTable 和 Dictionary 之间还有一个更重要的区别。如果您使用索引器从 HashTable 中获取值,则 HashTable 将成功为不存在的项目返回 null,而如果您尝试使用字典中不存在的索引器访问项目,则字典将抛出错误

回答by shiv govind

ILookup Interface is used in .net 3.5 with linq.

ILookup 接口用于 .net 3.5 和 linq。

The HashTable is the base class that is weakly type; the DictionaryBase abstract class is stronly typed and uses internally a HashTable.

HashTable 是弱类型的基类;DictionaryBase 抽象类是严格类型化的,并在内部使用 HashTable。

I found a a strange thing about Dictionary, when we add the multiple entries in Dictionary, the order in which the entries are added is maintained. Thus if I apply a foreach on the Dictionary, I will get the records in the same order I have inserted them.

我发现Dictionary有个奇怪的地方,当我们在Dictionary中添加多个条目时,条目的添加顺序是保持不变的。因此,如果我在字典上应用 foreach,我将按照插入它们的相同顺序获取记录。

Whereas, this is not true with normal HashTable, as when I add same records in Hashtable the order is not maintained. As far as my knowledge goes, Dictionary is based on Hashtable, if this is true, why my Dictionary maintains the order but HashTable does not?

然而,这对于普通的 HashTable 来说并非如此,因为当我在 Hashtable 中添加相同的记录时,不会保持顺序。据我所知,Dictionary 是基于 Hashtable 的,如果这是真的,为什么我的 Dictionary 维护顺序而 HashTable 没有?

As to why they behave differently, it's because Generic Dictionary implements a hashtable, but is not based on System.Collections.Hashtable. The Generic Dictionary implementation is based on allocating key-value-pairs from a list. These are then indexed with the hashtable buckets for random access, but when it returns an enumerator, it just walks the list in sequential order - which will be the order of insertion as long as entries are not re-used.

至于为什么它们的行为不同,那是因为通用字典实现了一个哈希表,而不是基于 System.Collections.Hashtable。通用字典实现基于从列表中分配键值对。然后用哈希表桶对它们进行索引以进行随机访问,但是当它返回一个枚举器时,它只是按顺序遍历列表——只要条目不被重用,这就是插入的顺序。

shiv govind Birlasoft.:)

shiv govind Birlasoft。:)

回答by Pritom Nandy

Lets give an example that would explain the difference between hashtable and dictionary.

让我们举一个例子来解释哈希表和字典之间的区别。

Here is a method that implements hashtable

这是一个实现哈希表的方法

public void MethodHashTable()
{
    Hashtable objHashTable = new Hashtable();
    objHashTable.Add(1, 100);    // int
    objHashTable.Add(2.99, 200); // float
    objHashTable.Add('A', 300);  // char
    objHashTable.Add("4", 400);  // string

    lblDisplay1.Text = objHashTable[1].ToString();
    lblDisplay2.Text = objHashTable[2.99].ToString();
    lblDisplay3.Text = objHashTable['A'].ToString();
    lblDisplay4.Text = objHashTable["4"].ToString();


    // ----------- Not Possible for HashTable ----------
    //foreach (KeyValuePair<string, int> pair in objHashTable)
    //{
    //    lblDisplay.Text = pair.Value + " " + lblDisplay.Text;
    //}
}

The following is for dictionary

以下是字典

  public void MethodDictionary()
  {
    Dictionary<string, int> dictionary = new Dictionary<string, int>();
    dictionary.Add("cat", 2);
    dictionary.Add("dog", 1);
    dictionary.Add("llama", 0);
    dictionary.Add("iguana", -1);

    //dictionary.Add(1, -2); // Compilation Error

    foreach (KeyValuePair<string, int> pair in dictionary)
    {
        lblDisplay.Text = pair.Value + " " + lblDisplay.Text;
    }
  }

回答by Pranav Singh

Want to add a difference:

想补充一点:

Trying to acess a inexistent key gives runtime error in Dictionary but no problem in hashtable as it returns null instead of error.

尝试访问不存在的键会在 Dictionary 中产生运行时错误,但在哈希表中没有问题,因为它返回 null 而不是错误。

e.g.

例如

       //No strict type declaration
        Hashtable hash = new Hashtable();
        hash.Add(1, "One");
        hash.Add(2, "Two");
        hash.Add(3, "Three");
        hash.Add(4, "Four");
        hash.Add(5, "Five"); 
        hash.Add(6, "Six");
        hash.Add(7, "Seven");
        hash.Add(8, "Eight");
        hash.Add(9, "Nine");
        hash.Add("Ten", 10);// No error as no strict type

        for(int i=0;i<=hash.Count;i++)//=>No error for index 0
        {
            //Can be accessed through indexers
            Console.WriteLine(hash[i]);
        }
        Console.WriteLine(hash["Ten"]);//=> No error in Has Table

here no error for key 0 & also for key "ten"(note: t is small)

这里没有错误,键 0 和键“十”也没有错误(注意:t 很小)

//Strict type declaration
        Dictionary<int,string> dictionary= new Dictionary<int, string>();
        dictionary.Add(1, "One");
        dictionary.Add(2, "Two");
        dictionary.Add(3, "Three");
        dictionary.Add(4, "Four");
        dictionary.Add(5, "Five");
        dictionary.Add(6, "Six");
        dictionary.Add(7, "Seven");
        dictionary.Add(8, "Eight");
        dictionary.Add(9, "Nine");
        //dictionary.Add("Ten", 10);// error as only key, value pair of type int, string can be added

        //for i=0, key doesn't  exist error
        for (int i = 1; i <= dictionary.Count; i++)
        {
            //Can be accessed through indexers
            Console.WriteLine(dictionary[i]);
        }
        //Error : The given key was not present in the dictionary.
        //Console.WriteLine(dictionary[10]);

here error for key 0 & also for key 10 as both are inexistent in dictionary, runtime error, while try to acess.

这里是键 0 和键 10 的错误,因为两者都在字典中不存在,运行时错误,同时尝试访问。