sábado, 5 de julio de 2014

Receta Multithreading en C# No. 1-5: Obtener el Estado de un Thread

Tabla de Contenido

0. Introducción
1. Problema
2. Solución
3. Discusión de la Solución
3.1 Enumeración ThreadState
3.1.1 Notas sobre el uso de la enumeración ThreadState
3.2 Propiedad Thread.ThreadState
4. Práctica: Código Fuente C#
5. Conclusiones
6. Glosario
7. Literatura & Enlaces

0. Introducción

En recetas multithreading anteriores aprendimos cómo crear, pausar, poner en espera, o abortar un thread; en esta oportunidad aprenderemos a conocer el estado de un thread a través del miembro (propiedad) ThreadState que representa un valor de la enumeración homónima. Comprenderemos su uso a través de ejemplos didácticos de ejecución paso a paso de aplicaciones consola; además de hacer una descripción de la enumeración ThreadState.

1. Problema

Una vez iniciemos la ejecución de un thread o realicemos otras acciones como poner en espera, o abortarlo, es necesario e imprescindible conocer su estado.

2. Solución

La clase Thread (N:System.Threading) cuenta con la propiedad de solo lectura ThreadState para obtener una representación o valor del estado actual de un thread.

3. Discusión de la Solución

Presento los artefactos integrales (enumeraciones, propiedades) para la determinación del estado de un thread.

3.1 Enumeración ThreadState


La enumeración ThreadState [4] localizada en el nombre de espacios System.Threading contiene los miembros que representan o especifican el estado de un instancia de la clase Thread. (Los miembros pertenecientes a esta enumeración se enumeran en la Figura 1.)
Miembros de la enumeración ThreadState
Figura 1. Miembros de la enumeración ThreadState.

Como se observa en la figura anterior, este conjunto de estados representa los 10 posibles estados en los que se puede hallar un thread. Sin embargo, es vital mencionar (a partir de [4]) que un thread puede encontrarse en más de un estado en un tiempo dado. Por ejemplo, este grupo de acciones pueden llevar al estado WaitSleepJoin y AbortRequested en un momento dado:
  1. Bloqueo del thread con la invocación al método Wait [5].
  2. Invocación al método Abort [6] (cfr. Abortar un Thread en Ejecución) sobre el thread bloqueado (paso anterior).
Por otro lado, una vez que un thread es creado se hallará en uno de los estados enumerados en la Figura 1. De acuerdo con [4] cualquiera de los threads creados en la CLR (Common Language Runtime), por defecto, se hallarán en el estado Unstarted. Los demás threads provenientes de fuentes externas serán iniciarán en el estado Running. Respecto al cambio de estado de un thread, que puede ser el resultado de un conjunto de acciones establecidas desde código cliente o por la generación de una excepción en tiempo de ejecución se muestran en la Figura 2.
Conjunto de accesiones que alteran el estado de un Thread
Figura 2. Conjunto de accesiones que alteran el estado de un thread.

3.1.1 Notas sobre el uso de la enumeración ThreadState

Desde [4] se pueden enumerar las siguientes recomendaciones de uso del estado de un thread:
  • «The ThreadState enumeration is of interest only in a few debugging scenarios. Your code should never use the thread state to synchronize the activities of threads.»
  • «In addition to the states noted above (Figura 1), there is also the Background state, which indicates whether the thread is running in the background or foreground.»

3.2 Propiedad Thread.ThreadState

La propiedad de instancia ThreadState [3] de solo lectura que representa el estado actual de un thread. Esta es su firma:

public ThreadState ThreadState { get; }

Esta propiedad retorna de los estados (miembros) de la enumeración ThreadState (ver sección 3.1). El estado por defecto de un thread una vez se cree es Unstarted.


En [3] nos reiteran la advertencia sobre el uso de esta propiedad:
Nota importante sobre el uso de la propiedad ThreadState de Thread
Figura 3. Nota importante sobre el uso de la propiedad ThreadState de Thread.
Vale mencionar que esta propiedad provee información más específica que la propiedad IsAlive [9], la cual sólo indica el estado actual de ejecución de un thread: true si el thread se iniciado y no finalizado ni ha sido abortado, en caso contrario false.

Ejemplo de uso:

Archivo C# UsoPropiedadThreadState.cs [enlace alternativo]:



En la línea 10 creamos un nuevo thread y pasamos como argumento al constructor de Thread el método ImprimirNumerosConRetraso (líneas 35-45) para el delegado ThreadStart. Iniciamos la ejecución del thread threadNuevo en la línea 16; casi enseguida abortamos la ejecución de este thread invocando al método Abort (línea 19). Identificamos su estado actual con la salida generada en la línea 22.



Continuando, sobre la línea 25 recreamos el thread threadNuevo y lo iniciamos en la línea 26. Esperamos a que finalice su ejecución con el método Join (línea 29). Finalmente mostramos el estado final del thread threadNuevo (línea 32).


Compilación:


  1. csc /target:exe UsoPropiedadThreadState.cs

Ejecución assembly:


  1. .\UsoPropiedadThreadState.exe

> Prueba de ejecución (idione.com).

> Prueba de ejecución (local):
Ejecución assembly UsoPropiedadThreadState.exe
Figura 4. Ejecución assembly UsoPropiedadThreadState.exe.

4. Práctica: Código Fuente C#

Creemos un ejemplo práctico para retomar varios de los conceptos vistos en la sección anterior.


Compilación:


  1. csc /target:exe EstadosThread.cs

Ejecución assembly:


  1. .\EstadosThread.exe

> Prueba de ejecución (ideone.com).

> Prueba de ejecución (local):
Ejecución assembly EstadosThread.exe
Figura 5. Ejecución assembly EstadosThread.exe.

Conclusiones

Hemos entendido que a través de la propiedad ThreadState de la clase Thread podemos obtener le estado de un thread creado sobre la CLR. El uso de esta propiedad sólo se precisa para cuestiones de depuración, y se desaconseja su uso para la sincronización de las acciones de los threads. Para la próxima oportunidad nos adentraremos en otro tema interesante: establecimiento de la prioridad de un thread.

Glosario

  • CLR
  • Debugging
  • Depuración
  • Estado
  • Common Language Runtime
  • Thread

Literatura & Enlaces

[1]: Multithreading in C# 5.0 Cookbook by Eugene Agafonov. Copyright 2013 Eugene Agafonov, 978-1-84969-764-4.
[2]: how to use thread state in C# programming - YouTube - https://www.youtube.com/watch?v=3VJDd3GHHa4
[3]: Thread.ThreadState Property (System.Threading) - http://msdn.microsoft.com/en-us/library/system.threading.thread.threadstate(v=vs.110).aspx
[4]: ThreadState Enumeration (System.Threading) - http://msdn.microsoft.com/en-us/library/system.threading.threadstate(v=vs.110).aspx
[5]: Monitor.Wait Method (System.Threading) - http://msdn.microsoft.com/en-us/library/system.threading.monitor.wait(v=vs.110).aspx
[6]: Thread.Abort Method (System.Threading) - http://msdn.microsoft.com/en-us/library/system.threading.thread.abort(v=vs.110).aspx
[7]: Receta Multithreading en C# No. 1-4: Abortar un Thread en Ejecución | OrtizOL - Experiencias Construcción Software (xCSw) - http://ortizol.blogspot.com/2014/06/receta-multithreading-en-csharp-no-1-4-abortar-un-thread-en-ejecucion.html
[8]: Receta Multithreading No. 1-1 en C#: Cómo Crear un Thread - http://ortizol.blogspot.com/2014/06/receta-multithreading-no-1-1-en-csharp-como-crear-un-thread.html
[9]: Thread.IsAlive Property (System.Threading) - http://msdn.microsoft.com/en-us/library/system.threading.thread.isalive(v=vs.110).aspx


S

No hay comentarios:

Publicar un comentario

Envíe sus comentarios, dudas, sugerencias, críticas. Gracias.