रूबी तरीकों के लिए उपाय और बेंचमार्क समय


87

मैं रूबी में उस विधि और अलग-अलग कथनों द्वारा लिए गए समय को कैसे माप सकता हूं। यदि आप नीचे दी गई विधि को देखते हैं तो मैं विधि द्वारा लिया गया कुल समय और डेटाबेस एक्सेस और रेडिस एक्सेस के लिए लिया गया समय मापना चाहता हूं। मैं हर बयान से पहले बेंचमार्क.मेयर नहीं लिखना चाहता। क्या रूबी दुभाषिया हमें ऐसा करने के लिए कोई हुक देता है?

def foo
# code to access database
# code to access redis. 
end

new Date()जावास्क्रिप्ट के समान कुछ है जो माणिक के पास है, लेकिन मुझे सही वाक्यविन्यास याद नहीं है। आप एक सभ्य लिस्टिंग गूगल देना चाहिए, हालांकि
रीगन

1
@Phani क्या आप कृपया एक सही उत्तर चुन सकते हैं? 8 साल बाद, मुझे लगता है कि यहां कुछ ठोस जवाब हैं। धन्यवाद।
जोशुआ पिंटर

जवाबों:


112

आप Timeऑब्जेक्ट का उपयोग कर सकते हैं । ( समय डॉक्स )

उदाहरण के लिए,

start = Time.now
# code to time
finish = Time.now

diff = finish - start

diff फ्लोटिंग पॉइंट नंबर के रूप में सेकंड में होगा।

EDIT: endआरक्षित है।


13
बस एक मामूली सुधार। endआरक्षित है, इसलिए कुछ अन्य चर नाम का उपयोग करें।
जेसन किम

4
Time.nowसिस्टम घड़ी में समायोजन से प्रभावित होता है, इसलिए इसके Process.clock_gettime(Process::CLOCK_MONOTONIC)बजाय इसका उपयोग करना सबसे अच्छा अभ्यास है । लेकिन किसी न किसी गणना के लिए यह कोई मायने नहीं रखता है। blog.dnsimple.com/2018/03/elapsed-time-with-ruby-the-right-way
पैट्रिक ब्रिंच-लैंग्लोइस

102

सबसे सरल तरीका:

require 'benchmark'

def foo
 time = Benchmark.measure {
  code to test
 }
 puts time.real #or save it to logs
end

नमूना उत्पादन:

2.2.3 :001 > foo
  5.230000   0.020000   5.250000 (  5.274806)

मान हैं: सीपीयू समय, सिस्टम समय, कुल और वास्तविक बीता हुआ समय।

स्रोत: गहरे लाल रंग का डॉक्स


40
तुम भी Benchmark.realtime { block }अगर तुम सिर्फ realtime चाहते हो सकता है
jmccure

35

Benchmarkरिपोर्ट का उपयोग करें

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

यह निम्नलिखित की तरह कुछ उत्पादन करेगा:

                        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: This is not shown in output.

अधिक जानकारी यहां पाई जा सकती है


2
मैं बस अपने जवाब पर वापस आया और फिर से प्रभावित हुआ (फिर से) कि कैसे बेंचमार्क इसे संभालता है। रूबी को प्यार करो।
जोशुआ पिंटर

2
यह पसंदीदा उत्तर होना चाहिए: क्योंकि, रूबी 2.2 के रूप में, Benchmarkक्लास एक मोनोटोनिक घड़ी का उपयोग करता है, जैसा कि अन्य उत्तरों में चर्चा की गई है। उदाहरण के लिए निम्न स्रोत कोड देखें, और लाइन 286 पर "
डिफ

17

जवाब में से कई का उपयोग करने का सुझाव देते हैं Time.now। लेकिन यह जागरूक होने के लायक है जो Time.nowबदल सकता है। सिस्टम क्लॉक बहाव कर सकता है और सिस्टम के एडमिनिस्ट्रेटर या NTP के माध्यम से सही हो सकता है। इसलिए यह संभव है कि Time.now आगे या पीछे कूद जाए और अपने बेंचमार्किंग के गलत परिणाम दे।

एक बेहतर समाधान ऑपरेटिंग सिस्टम की मोनोटोनिक घड़ी का उपयोग करना है, जो हमेशा आगे बढ़ रहा है। रूबी 2.1 और ऊपर के माध्यम से इस तक पहुँच प्रदान करते हैं:

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

आप यहां अधिक विवरण पढ़ सकते हैं । इसके अलावा आप लोकप्रिय रूबी परियोजना, साइडकीक देख सकते हैं, जिसने मोनोटोनिक घड़ी पर स्विच किया है ।


7

एक दूसरा विचार, माप को परिभाषित करें () रूबी कोड ब्लॉक तर्क के साथ फ़ंक्शन समय उपाय कोड को सरल बनाने में मदद कर सकता है:

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

अपनी परिभाषा में आप इसे कहते हैं benchmark। जब आप इसका उपयोग करते हैं तो इसे कहा जाता है measure। कृपया इसे ठीक करें।
सैंड्रो एल

4

Wquist के उत्तर की भावना में , लेकिन थोड़ा सरल, आप इसे नीचे की तरह भी कर सकते हैं:

start = Time.now
# code to time
Time.now - start

यह उत्तर प्रश्न का उत्तर देने का एक (थोड़ा) अलग तरीका है। सिर्फ इसलिए कि आप इसका पता लगा सकते हैं @ wquist के जवाब का मतलब यह नहीं है कि यह मान्य नहीं है।
thesecretmaster

3

में देखो ruby-prof पैकेज, यह आप क्या जरूरत नहीं होनी चाहिए। यह समय के साथ विशाल कॉल स्टैक्स बनाएगा।

http://ruby-prof.rubyforge.org/

यह बहुत दानेदार हो सकता है, जिस स्थिति में सिर्फ बड़े वर्गों को लपेटना Benchmark.measureएक अच्छा तरीका हो सकता है।


0

रील्स कंसोल में बेंचमार्क कोड को स्वचालित रूप से उपयोग करने का एक और तरीका इस रत्न का उपयोग कर रहा है: https://github.com/igorkasyanchuk/execution_time

आप लॉग में अनुरोधों से मिलते-जुलते जानकारी देखेंगे

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.