hashtable vs dictionary c#




Perché il dizionario è preferito su Hashtable? (12)

Cordiali saluti: In .NET, Hashtable è thread-safe per l'utilizzo da più thread di lettura e un singolo thread di scrittura, mentre nel Dictionary i membri statici pubblici sono thread-safe, ma i membri di ogni istanza non sono garantiti come thread-safe.

Abbiamo dovuto cambiare tutti i nostri dizionari di Hashtable causa di questo.

Nella maggior parte dei linguaggi di programmazione, i dizionari sono preferiti rispetto agli hashtables. Quali sono le ragioni dietro a questo?


In .NET, la differenza tra Dictionary<,> e HashTable è principalmente che il primo è un tipo generico, quindi ottieni tutti i vantaggi dei generici in termini di controllo del tipo statico (e boxing ridotto, ma non è così grande come le persone tendono a pensare in termini di prestazioni - anche se il costo della boxe è definito in modo definitivo).


Le persone dicono che un dizionario è lo stesso di una tabella hash.

Questo non è necessariamente vero. Una tabella hash è un'implementazione di un dizionario. Un tipico a quello, e potrebbe essere quello predefinito in. NET, ma non è per definizione l'unico.

Potresti ugualmente implementare un dizionario con un elenco collegato o un albero di ricerca, ma non sarebbe altrettanto efficiente (per alcuni parametri di efficienza).


Per quello che vale, un dizionario è (concettualmente) una tabella hash.

Se intendevi "perché usiamo la classe Dictionary<TKey, TValue> invece della classe Hashtable ?", Allora è una risposta facile: il Dictionary<TKey, TValue> è un tipo generico, Hashtable no. Ciò significa che si ottiene la sicurezza del tipo con Dictionary<TKey, TValue> , perché non è possibile inserire alcun oggetto casuale in esso e non è necessario eseguire il cast dei valori che si estrapolano.

È interessante notare che l'implementazione del Dictionary<TKey, TValue> in .NET Framework è basata su Hashtable , come si può notare da questo commento nel suo codice sorgente:

Il dizionario generico è stato copiato dalla fonte di Hashtable

Source


Poiché .NET Framework 3.5 include anche un HashSet<T> che fornisce tutti i vantaggi del Dictionary<TKey, TValue> se sono necessarie solo le chiavi e nessun valore.

Pertanto, se si utilizza un Dictionary<MyType, object> e si imposta sempre il valore su null per simulare il tipo hash table sicuro, è consigliabile prendere in considerazione il passaggio a HashSet<T> .


Secondo ciò che vedo usando .NET Reflector :

[Serializable, ComVisible(true)]
public abstract class DictionaryBase : IDictionary, ICollection, IEnumerable
{
    // Fields
    private Hashtable hashtable;

    // Methods
    protected DictionaryBase();
    public void Clear();
.
.
.
}
Take note of these lines
// Fields
private Hashtable hashtable;

Quindi possiamo essere sicuri che DictionaryBase utilizzi internamente una HashTable.


Un oggetto Hashtable è composto da bucket che contengono gli elementi della raccolta. Un bucket è un sottogruppo virtuale di elementi all'interno di Hashtable, che rende la ricerca e il recupero più facili e veloci rispetto alla maggior parte delle raccolte .

La classe Dictionary ha la stessa funzionalità della classe Hashtable. Un dizionario di un tipo specifico (diverso da Object) ha prestazioni migliori rispetto a un Hashtable per i tipi di valore poiché gli elementi di Hashtable sono di tipo Object e, di conseguenza, il pugilato e l'unboxing si verificano in genere se si memorizza o si recupera un tipo di valore.

Per ulteriori informazioni: Hashtable e tipi di raccolta dei dizionari


Un'altra differenza che posso capire è:

Non possiamo usare il dizionario <KT, VT> (generici) con i servizi web. Il motivo è che nessuno standard di servizi Web supporta lo standard generico.


Collections e Generics sono utili per gestire gruppi di oggetti. In .NET, tutti gli oggetti delle raccolte si IEnumerable nell'interfaccia IEnumerable , che a sua volta ha ArrayList(Index-Value)) e HashTable(Key-Value) . Dopo .NET framework 2.0, ArrayList e HashTable sono stati sostituiti con List & Dictionary . Ora, Arraylist e HashTable non sono più utilizzati nei progetti di oggi.

Venendo alla differenza tra HashTable e Dictionary , il Dictionary è generico dove Hastable non è generico. Possiamo aggiungere qualsiasi tipo di oggetto a HashTable , ma durante il recupero dobbiamo lanciarlo al tipo richiesto. Quindi, non è sicuro. Ma per il dictionary , pur dichiarandosi, possiamo specificare il tipo di chiave e valore, quindi non è necessario eseguire il cast durante il recupero.

Diamo un'occhiata a un esempio:

HashTable

class HashTableProgram
{
    static void Main(string[] args)
    {
        Hashtable ht = new Hashtable();
        ht.Add(1, "One");
        ht.Add(2, "Two");
        ht.Add(3, "Three");
        foreach (DictionaryEntry de in ht)
        {
            int Key = (int)de.Key; //Casting
            string value = de.Value.ToString(); //Casting
            Console.WriteLine(Key + " " + value);
        }

    }
}

Dizionario,

class DictionaryProgram
{
    static void Main(string[] args)
    {
        Dictionary<int, string> dt = new Dictionary<int, string>();
        dt.Add(1, "One");
        dt.Add(2, "Two");
        dt.Add(3, "Three");
        foreach (KeyValuePair<int, String> kv in dt)
        {
            Console.WriteLine(kv.Key + " " + kv.Value);
        }
    }
}

Dictionary<> è un tipo generico e quindi è sicuro.

Puoi inserire qualsiasi tipo di valore in HashTable e questo a volte può generare un'eccezione. Ma Dictionary<int> accetterà solo valori interi e allo stesso modo Dictionary<string> accetterà solo stringhe.

Quindi, è meglio usare il Dictionary<> invece di HashTable .


Dictionary <<< >>> differenze di Hashtable :

  • Generico <<< >>> Non generico
  • Richiede la sincronizzazione del thread proprio <<< >>> Offre la versione thread-safe tramite il metodo Synchronized()
  • Elemento KeyValuePair : KeyValuePair <<< >>> Elemento KeyValuePair : DictionaryEntry
  • Più recenti (> .NET 2.0 ) <<< >>> Più vecchi (da .NET 1.0 )
  • è in System.Collections.Generic <<< >>> è in System.Collections
  • Richiesta alla chiave non esistente genera un'eccezione <<< >>> Richiesta di chiavi non esistenti restituisce null
  • potenzialmente un po ' più veloce per i tipi di valore <<< >>> più lento (necessita di boxing / unboxing) per i tipi di valore

Dictionary / similarità di Hashtable :

  • Entrambi sono internamente hashtables == accesso rapido ai dati di molti articoli in base alla chiave
  • Entrambi hanno bisogno di chiavi immutabili e uniche
  • Le chiavi di entrambi hanno bisogno del proprio metodo GetHashCode()

Collezioni .NET simili (candidati da utilizzare al posto di Dictionary e Hashtable):

  • ConcurrentDictionary - thread safe (accessibile in modo sicuro da più thread contemporaneamente)
  • HybridDictionary : prestazioni ottimizzate (per pochi articoli e anche per molti articoli)
  • OrderedDictionary : è possibile accedere ai valori tramite l'indice int (in base all'ordine in cui sono stati aggiunti gli articoli)
  • SortedDictionary : elementi ordinati automaticamente
  • StringDictionary : fortemente tipizzato e ottimizzato per le stringhe

Dizionario:

  • Restituisce / genera Eccezione se proviamo a trovare una chiave che non esiste.

  • È più veloce di un Hashtable perché non c'è boxe e unboxing.

  • Solo i membri statici pubblici sono thread-safe.

  • Il dizionario è un tipo generico che significa che possiamo usarlo con qualsiasi tipo di dati (durante la creazione, deve specificare i tipi di dati per entrambe le chiavi e valori).

    Esempio: Dictionary<string, string> <NameOfDictionaryVar> = new Dictionary<string, string>();

  • Dictionay è un'implementazione sicura per tipo di Hashtable, Keys e Values sono fortemente tipizzati.

hashtable:

  • Restituisce null se proviamo a trovare una chiave che non esiste.

  • È più lento del dizionario perché richiede il pugilato e l'unboxing.

  • Tutti i membri di un Hashtable sono thread-safe,

  • Hashtable non è un tipo generico,

  • Hashtable è una struttura di dati con caratteri generici, possiamo aggiungere chiavi e valori di qualsiasi tipo.







data-structures