Comment puis-je mesurer le temps pris par une méthode et les instructions individuelles de cette méthode dans Ruby. Si vous voyez la méthode ci-dessous, je veux mesurer le temps total pris par la méthode et le temps pris pour l'accès à la base de données et l'accès redis. Je ne veux pas écrire Benchmark.measure avant chaque déclaration. L'interprète Ruby nous donne-t-il des crochets pour ce faire?
def foo
# code to access database
# code to access redis.
end
Vous pouvez utiliser l'objet Time
. ( Time Docs )
Par exemple,
start = Time.now
# code to time
finish = Time.now
diff = finish - start
diff
serait en secondes, sous forme de nombre à virgule flottante.
EDIT: end
est réservé.
La manière la plus simple:
require 'benchmark'
def foo
time = Benchmark.measure {
code to test
}
puts time.real #or save it to logs
end
Exemple de sortie:
2.2.3 :001 > foo
5.230000 0.020000 5.250000 ( 5.274806)
Les valeurs sont les suivantes: temps processeur, temps système, temps total et temps réel écoulé.
Source: Ruby docs .
require 'benchmark' # Might be necessary.
def foo
Benchmark.bm(20) do |bm| # The 20 is the width of the first column in the output.
bm.report("Access Database:") do
# Code to access database.
end
bm.report("Access Redis:") do
# Code to access redis.
end
end
end
Cela produira quelque chose comme ceci:
user system total real
Access Database: 0.020000 0.000000 0.020000 ( 0.475375)
Access Redis: 0.000000 0.000000 0.000000 ( 0.000037)
<------ 20 -------> # This is where the 20 comes in. NOTE: Not shown in output.
Plus d'informations peuvent être trouvées ici .
Une deuxième réflexion, définissez la fonction measure () avec Ruby peut aider à simplifier le code de mesure du temps:
def measure(&block)
start = Time.now
block.call
Time.now - start
end
# t1 and t2 is the executing time for the code blocks.
t1 = measure { sleep(1) }
t2 = measure do
sleep(2)
end
De nombreuses réponses suggèrent l'utilisation de Time.now
. Mais il faut savoir que Time.now
Peut changer. Les horloges du système peuvent dériver et peuvent être corrigées par l'administrateur du système ou via NTP. Il est donc possible pour Time.now de sauter en avant ou en arrière et de donner à votre benchmarking des résultats inexacts.
Une meilleure solution consiste à utiliser l'horloge monotone du système d'exploitation, qui va toujours de l'avant. Ruby 2.1 et supérieur donnent accès à cela via:
start = Process.clock_gettime(Process::CLOCK_MONOTONIC)
# code to time
finish = Process.clock_gettime(Process::CLOCK_MONOTONIC)
diff = finish - start # gets time is seconds as a float
Vous pouvez lire plus de détails ici . Vous pouvez également voir le populaire Ruby, Sidekiq, est passé à horloge monotone .
Regardez dans le Ruby-prof
package, il devrait avoir ce dont vous avez besoin. Il créera d'énormes piles d'appels avec des horaires.
http://Ruby-prof.rubyforge.org/
Il peut être trop granulaire, auquel cas il suffit d'envelopper de plus grandes sections dans Benchmark.measure
pourrait être une bonne façon de procéder.
Dans l'esprit de réponse de wquist , mais un peu plus simple, vous pouvez également le faire comme ci-dessous:
start = Time.now
# code to time
Time.now - start