Biblioteca de clases de .NET Framework
Hashtable (Clase)

Representa una colección de pares de clave y valor organizados en función del código hash de la clave.

Espacio de nombres: System.Collections
Ensamblado: mscorlib (en mscorlib.dll)

Sintaxis

Visual Basic (Declaración)
<SerializableAttribute> _
<ComVisibleAttribute(True)> _
Public Class Hashtable
    Implements IDictionary, ICollection, IEnumerable, ISerializable, _
    IDeserializationCallback, ICloneable
Visual Basic (Uso)
Dim instance As Hashtable
C#
[SerializableAttribute] 
[ComVisibleAttribute(true)] 
public class Hashtable : IDictionary, ICollection, IEnumerable, 
    ISerializable, IDeserializationCallback, ICloneable
C++
[SerializableAttribute] 
[ComVisibleAttribute(true)] 
public ref class Hashtable : IDictionary, ICollection, IEnumerable, 
    ISerializable, IDeserializationCallback, ICloneable
J#
/** @attribute SerializableAttribute() */ 
/** @attribute ComVisibleAttribute(true) */ 
public class Hashtable implements IDictionary, ICollection, 
    IEnumerable, ISerializable, IDeserializationCallback, ICloneable
JScript
SerializableAttribute 
ComVisibleAttribute(true) 
public class Hashtable implements IDictionary, ICollection, 
    IEnumerable, ISerializable, IDeserializationCallback, ICloneable
Comentarios

Cada elemento es un par de clave y valor almacenado en un objeto DictionaryEntry. Una clave no puede ser referencia de objeto null (Nothing en Visual Basic), pero un valor sí puede serlo.

Los objetos utilizados como claves por Hashtable son necesarios para reemplazar el método Object.GetHashCode (o la interfaz IHashCodeProvider) y el método Object.Equals (o la interfaz IComparer). La implementación de ambos métodos e interfaces debe tratar la distinción entre mayúsculas y minúsculas de la misma manera; de lo contrario, el comportamiento de Hashtable podría ser incorrecto. Por ejemplo, al crear Hashtable, debe utilizar la clase CaseInsensitiveHashCodeProvider (o una implementación de IHashCodeProvider que no haga distinción entre mayúsculas y minúsculas) con la clase CaseInsensitiveComparer (o una implementación de IComparer que no haga distinción entre mayúsculas y minúsculas).

Asimismo, estos métodos deben dar los mismos resultados cuando se llamen con los mismos parámetros mientras la clave esté incluida en Hashtable. Una alternativa es utilizar un constructor de Hashtable con un parámetro de IEqualityComparer. Si la igualdad de clave fuera simplemente una igualdad de referencia, sería suficiente la implementación heredada de Object.GetHashCode y Object.Equals.

Los objetos de claves deben permanecer inmutables mientras se utilicen como claves en Hashtable.

Cuando se agrega un elemento a Hashtable, el elemento se coloca en un sector de almacenamiento en función del código hash de la clave. Las búsquedas posteriores de la clave utilizarán su código hash para buscar en un sector de almacenamiento determinado solamente; de este modo, se reducirá considerablemente el número de comparaciones de clave necesarias para encontrar un elemento.

El factor de carga de Hashtable determina la relación máxima de elementos por sectores de almacenamiento. Factores de carga más pequeños causan tiempos de búsqueda más largos a costa de un mayor consumo de memoria. El factor de carga predeterminado de 1,0 suele proporcionar el mejor equilibrio entre velocidad y tamaño. También se puede especificar un factor de carga diferente cuando se cree Hashtable.

Conforme se agregan elementos a Hashtable, va aumentando el factor de carga real de Hashtable. Cuando el factor de carga real alcanza el factor de carga especificado, el número de depósitos de Hashtable aumenta automáticamente hasta el número primo más pequeño que sea superior al doble del número actual de depósitos de Hashtable.

Cada objeto de clave de Hashtable debe proporcionar su propia función hash, a la que se tiene acceso llamando al método GetHash. Sin embargo, se puede pasar cualquier objeto que implemente IHashCodeProvider a un constructor Hashtable y utilizar esa función hash para todos los objetos de la tabla.

La capacidad de Hashtable es el número de elementos que Hashtable puede contener. La capacidad inicial predeterminada de Hashtable es cero. Conforme se agregan elementos a Hashtable, la capacidad aumenta automáticamente según lo requiera la reasignación.

La instrucción foreach del lenguaje C# (for each en Visual Basic) requiere el tipo de cada elemento de la colección. Como los elementos de Hashtable son pares de clave y valor, el tipo del elemento no se corresponde con el tipo de la clave ni con el del valor. En su lugar, el tipo del elemento es DictionaryEntry. Por ejemplo:

C#
foreach (DictionaryEntry de in myHashtable) {...}
Visual Basic
For Each de as DictionaryEntry In myHashtable
   ...
Next de

La instrucción foreach es un contenedor del enumerador, que sólo permite la lectura pero no la escritura en la colección.

Dado que la serialización y deserialización de un enumerador para un objeto Hashtable puede provocar la reordenación de los elementos, no es posible continuar con la enumeración sin llamar antes al método Reset.

Ejemplo

En el ejemplo siguiente se muestra cómo se crean, inicializan y realizan diversas funciones para Hashtable y cómo se imprimen sus claves y valores.

Visual Basic
Imports System
Imports System.Collections

Module Example

    Sub Main()

        ' Create a new hash table.
        '
        Dim openWith As New Hashtable()

        ' Add some elements to the hash table. There are no 
        ' duplicate keys, but some of the values are duplicates.
        openWith.Add("txt", "notepad.exe")
        openWith.Add("bmp", "paint.exe")
        openWith.Add("dib", "paint.exe")
        openWith.Add("rtf", "wordpad.exe")

        ' The Add method throws an exception if the new key is 
        ' already in the hash table.
        Try
            openWith.Add("txt", "winword.exe")
        Catch
            Console.WriteLine("An element with Key = ""txt"" already exists.")
        End Try

        ' The Item property is the default property, so you 
        ' can omit its name when accessing elements. 
        Console.WriteLine("For key = ""rtf"", value = {0}.", _
            openWith("rtf"))

        ' The default Item property can be used to change the value
        ' associated with a key.
        openWith("rtf") = "winword.exe"
        Console.WriteLine("For key = ""rtf"", value = {0}.", _
            openWith("rtf"))

        ' If a key does not exist, setting the default Item property
        ' for that key adds a new key/value pair.
        openWith("doc") = "winword.exe"

        ' The default Item property throws an exception if the requested
        ' key is not in the hash table.
        Try
            Console.WriteLine("For key = ""tif"", value = {0}.", _
                openWith("tif"))
        Catch
            Console.WriteLine("Key = ""tif"" is not found.")
        End Try

        ' ContainsKey can be used to test keys before inserting 
        ' them.
        If Not openWith.ContainsKey("ht") Then
            openWith.Add("ht", "hypertrm.exe")
            Console.WriteLine("Value added for key = ""ht"": {0}", _
                openWith("ht"))
        End If

        ' When you use foreach to enumerate hash table elements,
        ' the elements are retrieved as KeyValuePair objects.
        Console.WriteLine()
        For Each de As DictionaryEntry In openWith
            Console.WriteLine("Key = {0}, Value = {1}", _
                de.Key, de.Value)
        Next de

        ' To get the values alone, use the Values property.
        Dim valueColl As ICollection = openWith.Values

        ' The elements of the ValueCollection are strongly typed
        ' with the type that was specified for hash table values.
        Console.WriteLine()
        For Each s As String In valueColl
            Console.WriteLine("Value = {0}", s)
        Next s

        ' To get the keys alone, use the Keys property.
        Dim keyColl As ICollection = openWith.Keys

        ' The elements of the KeyCollection are strongly typed
        ' with the type that was specified for hash table keys.
        Console.WriteLine()
        For Each s As String In keyColl
            Console.WriteLine("Key = {0}", s)
        Next s

        ' Use the Remove method to remove a key/value pair.
        Console.WriteLine(vbLf + "Remove(""doc"")")
        openWith.Remove("doc")

        If Not openWith.ContainsKey("doc") Then
            Console.WriteLine("Key ""doc"" is not found.")
        End If

    End Sub

End Module

' This code example produces the following output:
'
'An element with Key = "txt" already exists.
'For key = "rtf", value = wordpad.exe.
'For key = "rtf", value = winword.exe.
'For key = "tif", value = .
'Value added for key = "ht": hypertrm.exe
'
'Key = dib, Value = paint.exe
'Key = txt, Value = notepad.exe
'Key = ht, Value = hypertrm.exe
'Key = bmp, Value = paint.exe
'Key = rtf, Value = winword.exe
'Key = doc, Value = winword.exe
'
'Value = paint.exe
'Value = notepad.exe
'Value = hypertrm.exe
'Value = paint.exe
'Value = winword.exe
'Value = winword.exe
'
'Key = dib
'Key = txt
'Key = ht
'Key = bmp
'Key = rtf
'Key = doc
'
'Remove("doc")
'Key "doc" is not found.
C#
using System;
using System.Collections;

class Example
{
    public static void Main()
    {
        // Create a new hash table.
        //
        Hashtable openWith = new Hashtable();
        
        // Add some elements to the hash table. There are no 
        // duplicate keys, but some of the values are duplicates.
        openWith.Add("txt", "notepad.exe");
        openWith.Add("bmp", "paint.exe");
        openWith.Add("dib", "paint.exe");
        openWith.Add("rtf", "wordpad.exe");
        
        // The Add method throws an exception if the new key is 
        // already in the hash table.
        try
        {
            openWith.Add("txt", "winword.exe");
        }
        catch
        {
            Console.WriteLine("An element with Key = \"txt\" already exists.");
        }

        // The Item property is the default property, so you 
        // can omit its name when accessing elements. 
        Console.WriteLine("For key = \"rtf\", value = {0}.", openWith["rtf"]);
        
        // The default Item property can be used to change the value
        // associated with a key.
        openWith["rtf"] = "winword.exe";
        Console.WriteLine("For key = \"rtf\", value = {0}.", openWith["rtf"]);
        
        // If a key does not exist, setting the default Item property
        // for that key adds a new key/value pair.
        openWith["doc"] = "winword.exe";

        // The default Item property throws an exception if the requested
        // key is not in the hash table.
        try
        {
            Console.WriteLine("For key = \"tif\", value = {0}.", openWith["tif"]);
        }
        catch
        {
            Console.WriteLine("Key = \"tif\" is not found.");
        }

        // ContainsKey can be used to test keys before inserting 
        // them.
        if (!openWith.ContainsKey("ht"))
        {
            openWith.Add("ht", "hypertrm.exe");
            Console.WriteLine("Value added for key = \"ht\": {0}", openWith["ht"]);
        }

        // When you use foreach to enumerate hash table elements,
        // the elements are retrieved as KeyValuePair objects.
        Console.WriteLine();
        foreach( DictionaryEntry de in openWith )
        {
            Console.WriteLine("Key = {0}, Value = {1}", de.Key, de.Value);
        }

        // To get the values alone, use the Values property.
        ICollection valueColl = openWith.Values;
        
        // The elements of the ValueCollection are strongly typed
        // with the type that was specified for hash table values.
        Console.WriteLine();
        foreach( string s in valueColl )
        {
            Console.WriteLine("Value = {0}", s);
        }

        // To get the keys alone, use the Keys property.
        ICollection keyColl = openWith.Keys;
        
        // The elements of the KeyCollection are strongly typed
        // with the type that was specified for hash table keys.
        Console.WriteLine();
        foreach( string s in keyColl )
        {
            Console.WriteLine("Key = {0}", s);
        }

        // Use the Remove method to remove a key/value pair.
        Console.WriteLine("\nRemove(\"doc\")");
        openWith.Remove("doc");
        
        if (!openWith.ContainsKey("doc"))
        {
            Console.WriteLine("Key \"doc\" is not found.");
        }
    }
}

/* This code example produces the following output:

An element with Key = "txt" already exists.
For key = "rtf", value = wordpad.exe.
For key = "rtf", value = winword.exe.
For key = "tif", value = .
Value added for key = "ht": hypertrm.exe

Key = dib, Value = paint.exe
Key = txt, Value = notepad.exe
Key = ht, Value = hypertrm.exe
Key = bmp, Value = paint.exe
Key = rtf, Value = winword.exe
Key = doc, Value = winword.exe

Value = paint.exe
Value = notepad.exe
Value = hypertrm.exe
Value = paint.exe
Value = winword.exe
Value = winword.exe

Key = dib
Key = txt
Key = ht
Key = bmp
Key = rtf
Key = doc

Remove("doc")
Key "doc" is not found.
 */
Jerarquía de herencia

System.Object
  System.Collections.Hashtable
     System.Configuration.SettingsAttributeDictionary
     System.Configuration.SettingsContext
     System.Data.PropertyCollection
Seguridad para subprocesos

La clase Hashtable es segura para la ejecución de subprocesos si la utilizan varios subprocesos de lectura o un único subproceso de escritura. No es segura para la ejecución de subprocesos cuando la utilizan varios subprocesos y alguno de ellos lleva a cabo operaciones de escritura (actualización). Para admitir varios subprocesos de escritura, todas las operaciones en Hashtable se deben realizar a través del contenedor que devuelve el método Synchronized, siempre que no haya ningún subproceso leyendo el objeto Hashtable.

La enumeración en una colección no es en esencia un procedimiento seguro para la ejecución de subprocesos. Incluso cuando una colección está sincronizada, otros subprocesos todavía pueden modificarla, lo que hace que el enumerador produzca una excepción. Con el fin de garantizar la seguridad para la ejecución de subprocesos durante la enumeración, es posible bloquear la colección durante toda la enumeración o detectar las excepciones debidas a cambios efectuados por otros subprocesos.

Plataformas

Windows 98, Windows 2000 SP4, Windows CE, Windows Millennium, Windows Mobile para Pocket PC, Windows Mobile para Smartphone, Windows Server 2003, Windows XP Media Center, Windows XP Professional x64, Windows XP SP2, Windows XP Starter Edition

.NET Framework no admite todas las versiones de cada plataforma. Para obtener una lista de las versiones admitidas, vea Requisitos del sistema.

Información de versión

.NET Framework

Compatible con: 2.0, 1.1, 1.0

.NET Compact Framework

Compatible con: 2.0, 1.0
Vea también

Etiquetas :


Page view tracker