Trabajar con colecciones seguras para subprocesos: ConcurrentStack y ConcurrentQueue

Las colecciones seguras para subprocesos se introdujeron por primera vez en .Net 4 con la introducción del espacio de nombres System.Collections.Concurrent. Los tipos de colección en el espacio de nombres System.Collections.Concurrent contienen una colección de clases de colección seguras para subprocesos.

ConcurrentStack

Una pila es una estructura de datos que funciona según LIFO (último en entrar, primero en salir). La clase ConcurrentStack es una contraparte segura para subprocesos de la clase Stack genérica. ConcurrentStack es una clase de colección genérica segura para subprocesos que se introdujo por primera vez como parte de .Net Framework 4. Aquí está la lista de los métodos importantes de esta clase que ilustran las posibles operaciones.

  1. Push (elemento T): este método se utiliza para agregar datos de tipo T.
  2. PushRange: este método se puede usar para agregar una matriz de elementos de tipo T.
  3. TryPop (out T): este método se utiliza para recuperar el primer elemento de la pila. Devuelve verdadero en caso de éxito, falso en caso contrario.
  4. TryPeek (out T): este método se usa para recuperar el siguiente elemento de la pila, pero no elimina el elemento de la pila. Tenga en cuenta que, de forma similar al método TryPop (out T), devuelve verdadero en caso de éxito y falso en caso contrario.
  5. TryPopRange: este método está sobrecargado y funciona de manera similar a TryPop, pero se usa para recuperar matrices de la pila

A continuación, se explica cómo puede crear una instancia de la clase ConcurrentStack y enviarle datos.

ConcurrentStack concurrentStack = new ConcurrentStack();

for (Int32 index = 0; index < 10; index++)

{

       concurrentStack.Push(index);

}

Para recuperar los elementos de una pila concurrente, puede aprovechar el método TryPop (out T) como se muestra a continuación.

Int32 data;

bool success = concurrentStack.TryPop(out data);

La siguiente lista de códigos ilustra cómo puede almacenar y recuperar datos desde y hacia una pila concurrente.

static void Main(string[] args)

       {

           ConcurrentStack concurrentStack = new ConcurrentStack();

           for (Int32 index = 0; index < 100; index++)

           {

               concurrentStack.Push(index);

           }

           while (concurrentStack.Count > 0)

           {

               Int32 data;

               bool success = concurrentStack.TryPop(out data);

               if (success)

              {

                   Console.WriteLine(data);

               }

           }

           Console.Read();

       }

Cuando ejecute la lista de códigos anterior, los números del 0 al 99 se mostrarán en orden inverso en la ventana de la consola.

ConcurrentQueue

Una cola es una estructura de datos que funciona sobre la base de FIFO (primero en entrar, primero en salir). La clase ConcurrentQueue en .Net actúa como una cola genérica basada en FIFO segura para subprocesos.

La siguiente es la lista de los métodos importantes de la clase ConcurrentQueue.

  1. Enqueue (elemento T): este método se utiliza para agregar un elemento de tipo T a la cola
  2. TryPeek (out T): este método se usa para recuperar el siguiente elemento de la cola, pero no elimina el elemento de la cola. Este método devuelve verdadero en caso de éxito y falso cuando falla.
  3. TryDequeue (out T): este método se utiliza para recuperar el primer elemento de la cola. Al contrario del método TryPeek (out T), elimina el elemento de la cola. Este método devuelve verdadero en caso de éxito y falso en caso contrario.

El siguiente fragmento de código muestra cómo puede crear una instancia de la clase ConcurrentQueue para almacenar enteros.

ConcurrentQueue concurrentQueue = new ConcurrentQueue();

Para almacenar elementos en la instancia de cola simultánea, puede aprovechar el método Enqueue como se muestra a continuación.

concurrentQueue.Enqueue(100);

La siguiente lista de códigos ilustra cómo puede almacenar y recuperar elementos hacia y desde una cola simultánea.

ConcurrentQueue concurrentQueue = new ConcurrentQueue();

for (int index = 0; index < 100; index++)

{

     concurrentQueue.Enqueue(index);

}

Int32 item;

while (concurrentQueue.TryDequeue(out item))

{

     Console.WriteLine(item);

}

Cuando ejecute la lista de códigos anterior, los números del 0 al 99 se mostrarán en la ventana de la consola.

Tenga en cuenta que las clases ConcurrentStack y ConcurrentQueue son seguras para subprocesos y pueden gestionar problemas de bloqueo y sincronización internamente.

También puede convertir la instancia de cola concurrente en una matriz haciendo una llamada al método ToArray (). El siguiente fragmento de código ilustra cómo se puede lograr.

ConcurrentQueue concurrentQueue = new ConcurrentQueue();

for (Int32 index = 0; index < 100; index++ )

   concurrentQueue.Enqueue(index);

Int32[] integerArray = concurrentQueue.ToArray();

foreach (int i in integerArray)

{

   Console.WriteLine(i);

}

La propiedad IsEmpty de la clase ConcurrentQueue devuelve verdadero si la colección está vacía, falso en caso contrario. El siguiente fragmento de código muestra cómo puede utilizar este método.

ConcurrentQueue concurrentQueue = new ConcurrentQueue();

for (Int32 index = 0; index < 100; index++ )

concurrentQueue.Enqueue(index);

while(!concurrentQueue.IsEmpty)

{

     Int32 result;

     concurrentQueue.TryDequeue(out result);

     Console.WriteLine(result);

}