2012-08-25 42 views
9

Me sorprendió lo lento que es DateTime.Parse. Este código tarda alrededor de 100 segundos en ejecutarse; si uso la versión de regex demora 100 milisegundos. ¿Qué está pasando aquí?¿Por qué DateTime.Parse es tan lento?

Stopwatch sw = new Stopwatch(); 
sw.Start(); 
var re = new Regex(@"(\d\d)/(\d\d)/(\d\d\d\d) (\d\d):(\d\d):(\d\d)", RegexOptions.Compiled); 
for (int i = 0; i < 100000; i++) 
{ 
    //var m = re.Match("08/01/2012 23:10:12"); 
    DateTime.Parse("08/01/2012 23:10:12", CultureInfo.CreateSpecificCulture("en-US")); 
} 
sw.Stop(); 
Console.WriteLine(sw.ElapsedMilliseconds); 

Editar: Mark es derecha, moviendo el CultureInfo.CreateSpecificCulture("en-US") fuera del bucle ayudó. La razón por la que no lo hice antes es que he perfilado este código con VS Profiler y mostró siguiente resultado:

enter image description here

Respuesta

23

No es una prueba justa.

  1. La llamada a CultureInfo.CreateSpecificCulture("en-US") es la parte lenta. Muévelo fuera del ciclo, almacene el resultado y vuelva a utilizarlo.

  2. Su expresión regular solo maneja un formato específico, pero DateTime.Parse puede manejar muchos formatos de entrada diferentes. Tiene que decidir cuál de los muchos formatos que entiende es el correcto para usar. Si sabe de antemano cuál es el formato, utilice DateTime.ParseExact en lugar de DateTime.Parse.

El código fijo es el siguiente:

CultureInfo ci = CultureInfo.CreateSpecificCulture("en-US"); 
for (int i = 0; i < 100000; i++) 
{ 
    DateTime.ParseExact("08/01/2012 23:10:12", "MM/dd/yyyy HH:mm:ss", ci); 
} 

Con estos dos cambios, consigo que el DateTime.ParseExact y el enfoque de expresiones regulares son casi los mismos.

Y su expresión regular acepta algunas fechas que no son válidas, como 00/00/0000 99:99:99. Si lo arreglas para que solo acepte fechas de tiempo válidas, sería más lento.

+1

Oooh, me siento tan estúpido, realmente moviendo 'CreateSpecificCulture' fuera del rendimiento fijo del bucle. La razón por la que no lo hice antes porque utilicé VS Profiler y mostró que el problema está en 'Parse', vea la captura de pantalla en edit. – Andrey

+0

Estoy de acuerdo, por supuesto, que usar Regex es una especie de trampa aquí, pero consideré cambiarlo porque estaba 100% seguro de que los datos de entrada son válidos y el rendimiento era más importante. – Andrey