2010-04-05 7 views
5

Soy nuevo en C# world. Estoy intentando calcular el tiempo tomado por un algoritmo para fines de comparación. El siguiente código mide el tiempo transcurrido desde que se llama a una subrutina hasta que la subrutina vuelve al programa principal. Este ejemplo se toma de "Estructuras de datos a través de C#" de Michael McMillan. Después de ejecutar este programa, el resultado es Tiempo = 0, que es incorrecto. El programa parece ser lógicamente correcto. Alguien puede ayudarme. Lo que sigue es el códigoTiempo necesario para completar un proceso

using System; 
using System.Diagnostics; 
using System.Collections.Generic; 
using System.Linq; 
using System.Text; 

namespace Chap1 
{ 
    class chap1 
    { 
     static void Main() 
     { 
      int[] nums = new int[100000]; 
      BuildArray(nums); 
      Timing tObj = new Timing(); 
      tObj.startTime(); 
      DisplayNums(nums); 
      tObj.stopTime(); 
      Console.WriteLine("Time: " + tObj.result().TotalSeconds); 
      Console.WriteLine("Start Time: " + tObj.startTime().TotalSeconds); 
      Console.WriteLine("Duration : " + tObj.result().TotalSeconds); 
      Console.ReadKey(); 
     } 
     static void BuildArray(int[] arr) 
     { 
      for (int i = 0; i <= 99999; i++) 
       arr[i] = i; 
     } 
     static void DisplayNums(int[] arr) 
     { 
      for (int i = 0; i <= arr.GetUpperBound(0); i++) 
       Console.WriteLine(arr[i]); 
     } 
    } 
class Timing 
    { 
     TimeSpan StartTiming; 
     TimeSpan duration; 
     public Timing() 
     { 
      StartTiming = new TimeSpan(0); 
      duration = new TimeSpan(0); 
     } 
     public TimeSpan startTime() 
     { 
      GC.Collect(); 


    GC.WaitForPendingFinalizers(); 
      StartTiming = Process.GetCurrentProcess().Threads[0].UserProcessorTime; 
      return StartTiming; 
     } 
     public void stopTime() 
     { 
      duration = Process.GetCurrentProcess().Threads[0].UserProcessorTime.Subtract(StartTiming); 

     } 
     public TimeSpan result() 
     { 
      return duration; 
     } 
    } 
} 
+0

No lo ejecute en modo de depuración (de acuerdo con algunos recursos en línea). – Kiril

+0

¡tuve el mismo problema! Ben Voigt tiene razón, no se puede asumir, que el hilo con índice 0 (ÍNDICE, no ID de hilo !!!) es el que le interesa. Estoy utilizando un PInvoke para GetCurrentThreadId() ahora para obtener el ID de hilo correcto . Luego recorro todos los hilos y verifico el que tiene ese ID de hilo. – Jane

Respuesta

3

El Stopwatch class está diseñado para esto.

UserProcessorTime no comienza a tener la resolución necesaria para medir el recuento a 100000 en un bucle for. Sus llamadas de WriteLine no se incluirán en la hora del usuario, ya que son tiempo de E/S. Es posible que su código no se esté ejecutando en el subproceso 0. El tiempo de usuario no se actualiza, excepto en los conmutadores de contexto. Cuando imprime startTime, está cambiando el valor almacenado. Probablemente hay otras cosas que pueden salir mal en las que no he pensado.

Sugiero que use la clase Cronómetro que aprovecha los contadores de rendimiento de la CPU.

+0

@Ben OP está preguntando por qué este ejemplo no funciona. – Kiril

+0

Querido Ben, voy a solicitar si puedes consultar el código correcto que he editado en este momento. Gracias –

+0

En el entorno .NET, cada programa se ejecuta dentro del dominio de la aplicación. Esto permite que el sistema operativo separe diferentes programas que se ejecutan en él al mismo tiempo. Dentro de un proceso, un programa o una parte de un programa se ejecuta dentro de un hilo. El tiempo de ejecución para un programa es asignado por el sistema operativo a través de hilos.Cuando estamos cronometrando el código para un programa, queremos asegurarnos de que estamos sincronizando solo el código dentro del proceso asignado para nuestro programa y no otras tareas que está realizando el sistema operativo. Usando la clase de cronómetro, estaríamos incluyendo otro tiempo en el tiempo total. –

2

Usted no usa la clase Timing cualquier lugar de su función principal y no veo donde se imprime el tiempo tampoco. ¿Es este el código EXACT que está ejecutando?

actualización por cada nuevo código:

no lo ejecute en modo de depuración ... construir su versión de lanzamiento y luego ejecutar el ejecutable de forma manual: http://social.msdn.microsoft.com/forums/en-US/vbgeneral/thread/3f10a46a-ba03-4f5a-9d1f-272a348d660c/

Probé su código y funcionó bien cuando ejecutaba la versión de lanzamiento, pero cuando la ejecutaba en el depurador no funcionaba correctamente.

+0

Lo siento por publicar un código incorrecto. Ahora publiqué el código exacto –

+0

porque la mayor parte del tiempo se usa para hacer la salida de la consola, es decir, una llamada kernel WriteFile (CONOUT $), que no está incluida en el tiempo de "usuario". –

+0

@Ben Encontré este artículo que sugiere que ejecutar el código en el modo de depuración no mostraría la hora: http://social.msdn.microsoft.com/forums/en-US/vbgeneral/thread/3f10a46a-ba03-4f5a-9d1f -272a348d660c/ – Kiril

Cuestiones relacionadas