2008-09-22 8 views
7

Soy un novato total, pero estaba escribiendo un pequeño programa que funcionaba con cadenas en C# y noté que si hacía algunas cosas de manera diferente, el código se ejecutaba mucho más rápido.¿Está probando su código de velocidad?

Así que me pregunto, ¿cómo haces para controlar la velocidad de ejecución de tu código? ¿Hay utilidades (gratuitas)? ¿Lo haces a la vieja usanza con un System.Timer y lo haces tú mismo?

Respuesta

12

Lo que está describiendo se conoce como perfil de rendimiento. Hay muchos programas que puede obtener para hacer esto, como Jetbrains profiler o Ants profiler, aunque la mayoría ralentizará su aplicación mientras se encuentra en el proceso de medir su rendimiento.

Para realizar manualmente su propio perfil de rendimiento, puede usar System.Diagnostics.Stopwatch y una consola simple. WriteLine, como usted describió.

Además, tenga en cuenta que el compilador C# JIT optimiza el código según el tipo y la frecuencia a la que se llama, así que juegue con bucles de diferentes tamaños y métodos, como llamadas recursivas para obtener una idea de lo que funciona mejor.

+0

+1: Ese cronómetro es una pequeña utilidad práctica para controles rápidos, ¡gracias! –

0

Hago lo siguiente: 1) Uso ticks (por ejemplo, en VB.Net Now.ticks) para medir la hora actual. Restamos los ticks de inicio del valor de los ticks finalizados y los dividimos por TimeSpan.TicksPerSecond para obtener la cantidad de segundos que tomó. 2) Evito las operaciones de IU (como console.writeline). 3) Ejecuto el código en un bucle sustancial (como 100.000 iteraciones) para factorizar las variables de uso/SO lo mejor que puedo.

11

ANTS Profiler from RedGate es un perfilador de rendimiento muy agradable. dotTrace Profiler from JetBrains también es genial. Estas herramientas le permitirán ver las métricas de rendimiento que se pueden explorar en cada línea individual.

Pedregal tiro de hormigas Profiler: ANTS http://www.red-gate.com/products/ants_profiler/images/app/timeline_calltree3.gif

Si desea asegurarse de que un método específico se mantiene dentro de un umbral de rendimiento específico durante las pruebas unitarias, me gustaría utilizar el Stopwatch class para controlar el tiempo de ejecución de un uno o método muchas veces en un bucle y calcular el promedio y luego Assert contra el resultado.

+0

Usamos esto. ¡Es muy efectivo para encontrar la única rutina que toma el 95% del tiempo! –

0

Puede usar los métodos de la clase StopWatch to time. Recuerde que la primera vez suele ser lenta debido a que el código debe ser jodido.

7

Solo un recordatorio: asegúrese de compilar en Relase, no en Debug! (He visto este error cometido por desarrolladores experimentados, es fácil de olvidar).

+0

Discuto un poco. Para encontrar aceleraciones, lo mejor es trabajar en modo de depuración. Cuando todo haya terminado con eso, cambia al modo de lanzamiento. La razón es que si el código hace cosas tontas como llamar a ciertas funciones más de lo necesario, o asignando/liberando la memoria más que necesita, o haciendo E/S que no se dio cuenta, el modo de lanzamiento no lo arreglará. Solo hará que sea difícil de encontrar. –

2

Lo que está describiendo es 'Ajuste del rendimiento'. Cuando hablamos de ajuste de rendimiento hay dos ángulos. (a) Tiempo de respuesta: cuánto tiempo lleva ejecutar una solicitud/programa particular. (b) Rendimiento - Cuántas solicitudes puede ejecutar en un segundo. Cuando normalmente 'optimizamos' - cuando eliminamos el procesamiento innecesario, tanto el tiempo de respuesta como el rendimiento mejoran.Sin embargo, si tiene eventos de espera en su código (como Thread.sleep(), espera de E/S, etc.), su tiempo de respuesta se ve afectado, sin embargo, el rendimiento no se ve afectado. Al adoptar el procesamiento paralelo (engendrando múltiples hilos) podemos mejorar el tiempo de respuesta pero el rendimiento no mejorará. Normalmente, para la aplicación del lado del servidor, tanto el tiempo de respuesta como el rendimiento son importantes. Para aplicaciones de escritorio (como IDE) el rendimiento no es importante, solo el tiempo de respuesta es importante.

Puede medir el tiempo de respuesta mediante 'Prueba de rendimiento' - solo anota el tiempo de respuesta para todas las transacciones clave. Puede medir el rendimiento mediante 'Load Testing': necesita bombear solicitudes continuamente desde un número suficientemente grande de subprocesos/clientes, de forma que el uso de la CPU de la máquina del servidor sea del 80-90%. Cuando realizamos una solicitud de bomba, necesitamos mantener la relación entre diferentes transacciones (llamada mezcla de transacción), por ejemplo: en un sistema de reserva habrá 10 reservas por cada 100 búsquedas. habrá una cancelación por cada 10 reservas, etc.

Después de identificar las transacciones que requieren ajuste para el tiempo de respuesta (prueba de rendimiento), puede identificar los puntos calientes mediante el uso de un generador de perfiles. Puede identificar los puntos críticos para el rendimiento comparando el tiempo de respuesta * fracción de esa transacción. Supongamos que en el escenario de búsqueda, reserva, cancelación, la relación es 89: 10: 1. El tiempo de respuesta es 0.1 segundos, 10 segundos y 15 segundos. carga para la búsqueda - 0.1 * .89 = 0.089 carga para la reserva- 10 * .1 = 1 carga para cancell = 15 * .01 = 0.15 Aquí la reserva de sintonía tendrá un impacto máximo en el rendimiento. También puede identificar los puntos calientes para el rendimiento al tomar tiradas de subprocesos (en el caso de aplicaciones basadas en Java) repetidamente.

0

Existe una opción .NET nativa (Team Edition para Desarrolladores de software) que podría abordar algunas necesidades de análisis de rendimiento. En el menú .NET 2005 IDE, seleccione Herramientas> Rendimiento Herramientas-> Asistente de rendimiento ...

[GSS es probablemente correcta que debe tener Team Edition]

0

Este es un ejemplo simple para la velocidad de código de prueba. Espero que te haya ayudado

class Program { 
    static void Main(string[] args) { 
     const int steps = 10000; 
     Stopwatch sw = new Stopwatch(); 

     ArrayList list1 = new ArrayList(); 
     sw.Start(); 
     for(int i = 0; i < steps; i++) { 
      list1.Add(i); 
     } 
     sw.Stop(); 
     Console.WriteLine("ArrayList:\tMilliseconds = {0},\tTicks = {1}", sw.ElapsedMilliseconds, sw.ElapsedTicks); 

     MyList list2 = new MyList(); 
     sw.Start(); 
     for(int i = 0; i < steps; i++) { 
      list2.Add(i); 
     } 
     sw.Stop(); 
     Console.WriteLine("MyList: \tMilliseconds = {0},\tTicks = {1}", sw.ElapsedMilliseconds, sw.ElapsedTicks);