Run benchmark but don't print the result

故事扮演 提交于 2019-12-25 06:24:05

问题


I have a benchmark like follows:

benchmark_result = Benchmark.bm do |x|
  x.report { send(test_name) }
end

When I run this, I'm seeing output from two places:

  1. The send(test_name) in the report block. I want to continue seeing this output.
  2. The output from the Benchmark block, i.e. the resulting benchmark report is printed to the console. I don't want this to happen.

I've seen from here how to temporarily hide the console output. But the problem is that I want the inner block to continue printing its output. I just don't want to see the benchmark results.


回答1:


When you call the report method on the Benchmark::Report object sent to the block by Benchmark.bm or Benchmark.benchmark, it will print to STDOUT. If you're just interested in the benchmark metrics without printing a report, you can do this:

benchmark_result = Benchmark.measure do
  send(test_name) 
end

It returns a Benchmark::Tms object that looks like this:

 => #<Benchmark::Tms:0x007fb5b1b40118
 @cstime=0.0,
 @cutime=0.0,
 @label="",
 @real=4.5693013817071915e-05,
 @stime=0.0,
 @total=0.0,
 @utime=0.0>

If you're just interested in the elapsed real time used to execute your block, do the following (returns a Float):

benchmark_result = Benchmark.realtime do
  send(test_name) 
end



回答2:


I've accepted Amit's answer because it seems canonical, but I did figure out another way to do it in the meantime.

From this question I have added the following code (slightly modified to include the touch/rm calls on the null.txt file):

def silence_output
  # Store the original stderr and stdout in order to restore them later
  @original_stderr = $stderr
  @original_stdout = $stdout

  # Redirect stderr and stdout
  `touch null.txt`
  $stderr = File.new(File.join(File.dirname(__FILE__), 'null.txt'), 'w')
  $stdout = File.new(File.join(File.dirname(__FILE__), 'null.txt'), 'w')
end

# Replace stderr and stdout so anything else is output correctly
def enable_output
  $stderr = @original_stderr
  $stdout = @original_stdout
  @original_stderr = nil
  @original_stdout = nil
  `rm null.txt`
end

With this, I can accomplish my goal using the following:

silence_output
benchmark_result = Benchmark.bm do |x|
  x.report do   
    enable_output
    send(test_name)
    silence_output
  end
end
enable_output

Although after seeing a better way to do it, this seems very hacky.



来源:https://stackoverflow.com/questions/36969333/run-benchmark-but-dont-print-the-result

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!