ruby timer

¿Cómo sincronizar una operación en milisegundos en Ruby?



timer (9)

Debería echar un vistazo al módulo de referencia para realizar puntos de referencia. Sin embargo, como un método de temporización rápido y sucio puede usar algo como esto:

def time now = Time.now.to_f yield endd = Time.now.to_f endd - now end

Tenga en cuenta el uso de Time.now.to_f , que a diferencia de to_i, no se truncará en segundos.

Estoy deseando saber cuántos milisegundos usa una función en particular. Así que miré alto y bajo, pero no pude encontrar la manera de pasar el tiempo en Ruby con una precisión de milisegundos.

¿Cómo haces esto? En la mayoría de los lenguajes de programación es algo así como

start = now.milliseconds myfunction() end = now.milliseconds time = end - start


El uso de Time.now.to_i devuelve el segundo aprobado desde 1970/01/01. Sabiendo esto, puedes hacer

date1 = Time.now.to_f date2 = Time.now.to_f diff = date2 - date1

Con esto tendrás diferencia en segunda magnitud. Si lo quiere en milisegundos , simplemente agregue al código

diff = diff * 1000


La gema absolute_time es un reemplazo directo para Benchmark, pero usa instrucciones nativas para ser mucho más preciso.


Puedes usar la clase de Time de ruby. Por ejemplo:

t1 = Time.now # processing... t2 = Time.now delta = t2 - t1 # in seconds

Ahora, delta es un objeto float y puede obtener un resultado tan fino como la clase proporcionará.


Si utiliza

date = Time.now.to_i

Estás obteniendo tiempo en segundos, eso está lejos de ser preciso, especialmente si estás cronometrando pequeños trozos de código.


También puede usar la función incorporada Benchmark.measure:

require "benchmark" puts(Benchmark.measure { sleep 0.5 })

Huellas dactilares:

0.000000 0.000000 0.000000 ( 0.501134)


Tengo una gema que puede perfilar su método Ruby (instancia o clase) - https://github.com/igorkasyanchuk/benchmark_methods .

No más códigos como este:

t = Time.now user.calculate_report puts Time.now - t

Ahora puedes hacer:

benchmark :calculate_report # in class

Y solo llame a su método

user.calculate_report


Usar Time.now (que devuelve la hora del reloj de pared) como líneas base tiene un par de problemas que pueden provocar un comportamiento inesperado. Esto se debe al hecho de que el tiempo de reloj de pared está sujeto a cambios como segundos intercalares insertados o giro de tiempo para ajustar la hora local a un tiempo de referencia.

Si hay, por ejemplo, un segundo intercalar insertado durante la medición, se desactivará por un segundo. Del mismo modo, dependiendo de las condiciones del sistema local, es posible que tenga que lidiar con los horarios de ahorro de energía, los relojes que corren más rápido o más lento, o que el reloj retroceda en el tiempo, lo que da como resultado una duración negativa y muchos otros problemas.

Una solución a este problema es usar un reloj diferente: un reloj monótono. Este tipo de reloj tiene diferentes propiedades que el reloj de pared. Se incrementa monitonicamente, es decir, nunca retrocede y aumenta a una velocidad constante. Con eso, no representa el reloj de pared (es decir, el tiempo que lees de un reloj en tu pared), sino una marca de tiempo que puedes comparar con una marca de tiempo posterior para obtener una diferencia.

En Ruby, puede usar dicha marca de tiempo con Process.clock_gettime(Process::CLOCK_MONOTONIC) siguiente manera:

t1 = Process.clock_gettime(Process::CLOCK_MONOTONIC) # => 63988.576809828 sleep 1.5 # do some work t2 = Process.clock_gettime(Process::CLOCK_MONOTONIC) # => 63990.08359163 delta = t2 - t1 # => 1.5067818019961123 delta_in_milliseconds = delta * 1000 # => 1506.7818019961123

El método Process.clock_gettime devuelve una marca de tiempo como un flotante con segundos fraccionarios. El número real devuelto no tiene un significado definido (en el que debe confiar). Sin embargo, puede estar seguro de que la próxima llamada devolverá un número mayor y al comparar los valores, puede obtener la diferencia de tiempo real.

Estos atributos hacen que el método sea un candidato ideal para medir las diferencias de tiempo sin ver su programa fallar en los momentos menos oportunos (por ejemplo, a la medianoche en la víspera de Año Nuevo cuando se inserta otro segundo intercalar).


Use Time.now.to_f