2011-06-17 10 views
5

Şu an için zaman ölçümleri yapıyorum, kullanıcı zamanını veya sistem süresini Benchmark sınıfını veya komut satırını kullanmadan ölçmenin mümkün olup olmadığını merak ettim yarar time.Kullanıcı zamanını veya Ruby'de Benchmark olmadan sistem saatini ölçün veya süre

Time sınıfını kullanmak yalnızca sistem saati ve saati değil, duvar saati süresini gösterir, ancak aynı esnekliğe sahip bir çözüm arıyorum, örn.

time = TimeUtility.now 
# some code 
user, system, real = TimeUtility.now - time 

nedeni

sadece sayıları döndüremez çünkü ben bir şekilde, Benchmark sevmediğim olmasıdır ( DÜZENLEME: Yanılmışım - bu aşağıdaki yanıtlara göz atın olabilir..). Tabii, çıktıyı ayrıştırabilirim, ama bu doğru hissetmiyor. * NIX sistemlerinden gelen time yardımcı programı benim de sorunumu çözmeli, ancak Ruby'de bir çeşit sarıcı olup olmadığını öğrenmek istedim, bu yüzden bu sistem çağrılarını kendim yapmam gerekiyor.

Çok teşekkürler!

cevap

8

Benchmark belgelerini yeniden okudum ve bunun measure adlı bir yöntemi olduğunu gördüm. Bu yöntem istediğim tam olarak ne yapar: kodunuzu ihtiyacı süresini ölçün ve kullanıcı zamanını içeren bir nesne, sistem saati, çocuk vb sistem saatini dönen öğrendim kadar kolay süreçte

require 'benchmark' 
measurement = Benchmark.measure do 
    # your code goes here 
end 

gibi öyle Kıyaslama çıktısına özel satırlar ekleyebilirsiniz.

require 'benchmark' 

measurements = [] 
10.times { measurements << Benchmark.measure { 1_000_000.times { a = "1" } } } 

# measurements.sum or measurements.inject(0){...} does not work, since the 
# array contains Benchmark instances, which cannot be coerced into Fixnum's 
# Array#sum will work if you are using Rails 
sum = measurements.inject(nil) { |sum, t| sum.nil? ? sum = t : sum += t } 
avg = sum/measurements.size 

# 7 is the width reserved for the description "sum:" and "avg:" 
Benchmark.bm(7, "sum:", "avg:") do |b| 
    [sum, avg] 
end 

sonuç aşağıdaki gibi görünecektir:

   user  system  total  real 
sum:  2.700000 0.000000 2.700000 ( 2.706234) 
avg:  0.270000 0.000000 0.270000 ( 0.270623) 
+0

Sadece "talep" kriterleri için kısayol olsaydı keşke; Benchmark.measure {...} ' – dolzenko

+0

Anlamıyorum, alıntı yapılan bölüm oldukça kısa. Ne almak isterdiniz? (Pseduo-Code;) –

+0

emin, muhtemelen bundan daha kısa olamaz, sadece yazarak kaydetmek için ruby ​​ile sağlanan bazı kısayol eksikliği eksikti. + Her zaman unuyorum, 'ölçü' veya 'bm' veya bmbm' veya başka bir şey :) – dolzenko

2

Kullanıcı zamanını/sistem zamanını döndüren Process::times işlevini kullanabilirsiniz. (Duvar saati saatini rapor etmez, bunun için başka bir şeye ihtiyacınız vardır). Yine de biraz sürümü veya işletim sistemi bağımlı görünüyor. Bu benim sistemi (linux, yakut 1.8.7) raporları ne

:

$ irb 
irb(main):001:0> t = Process.times 
=> #<struct Struct::Tms utime=0.01, stime=0.0, cutime=0.0, cstime=0.0> 

docs olsa nedenle bazı sürümleri bu göstermek/uygulamaları sadece ilk iki sahip olabilir:

t = Process.times 
[ t.utime, t.stime ] #=> [0.0, 0.02] 

Linux'taki temel çağrı için bkz times.

class SysTimes 

    attr_accessor :user, :system 

    def initialize 
     times = Process.times 
     @user = times.utime 
     @system = times.stime 
    end 

    def -(other) 
     diff = SysTimes.new 
     diff.user = @user - other.user 
     diff.system = @system - other.system 
     diff 
    end 
end 

size sizin bağlamda güzel çalışması için fikirler vermeli:

İşte gerçekten berbat tür - destekler sarıcı var.

+0

Ne yazık ki 'yanıt bilmeyen bir yapı var -', böylece' süresi = Process.times; user, system = Process.times - time' bir hata verir. Ancak, bu yöntemi daha önce bilmiyordum ve yaklaşımı beğendim, çünkü programımın ne kadar sürede çalıştığına bakabilirim. :) Katkınız için teşekkürler! –

0

Bu taş aşağıdaki şekilde iki dünyanın (özel zaman ölçümleri ve sonunda güzel çıktı) iyi olsun için kullanabilir yardımcı olabilir: https://github.com/igorkasyanchuk/benchmark_methods

böyle Artık kodu:

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

Şimdi yapabilirsiniz: senin yöntem

benchmark :calculate_report # in class 

Ve diyoruz

user.calculate_report 
İlgili konular