| .. | ||
| mrblib | ||
| test | ||
| mrbgem.rake | ||
| README.md | ||
mruby-benchmark
Benchmarking and profiling tools for mruby.
Overview
The mruby-benchmark gem provides simple and lightweight benchmarking capabilities for measuring execution time and memory usage in mruby applications. It is designed for embedded systems and resource-constrained environments.
Installation
Add the following line to your build_config.rb:
conf.gem :core => 'mruby-benchmark'
API
Benchmark Module
The main interface for benchmarking operations.
Benchmark.measure { block } → Benchmark::Tms
Measures the execution time of the given block and returns a Benchmark::Tms object containing timing information.
result = Benchmark.measure do
# code to benchmark
1000.times { "string interpolation: #{42}" }
end
puts result # Prints formatted timing information
Benchmark.realtime { block } → Float
Returns only the real (wall-clock) time in seconds as a floating-point number.
time = Benchmark.realtime do
sleep(0.1)
end
puts "Took #{time} seconds" # => "Took 0.100... seconds"
Benchmark.bm(label_width = 0) { |x| ... }
Performs formatted benchmark comparisons with aligned output.
Benchmark.bm(10) do |x|
x.report("array:") { 1000.times { [1, 2, 3, 4, 5] } }
x.report("hash:") { 1000.times { {a: 1, b: 2, c: 3} } }
x.report("string:") { 1000.times { "hello" * 100 } }
end
Output example:
user system total real
array: 0.010000 0.000000 0.010000 ( 0.012345)
hash: 0.015000 0.000000 0.015000 ( 0.016789)
string: 0.008000 0.000000 0.008000 ( 0.009012)
Benchmark.measure(memory: true) { block } → Benchmark::Tms
Measures both execution time and memory allocation when memory: true is specified.
result = Benchmark.measure(memory: true) do
array = []
1000.times { |i| array << i }
end
puts "Objects allocated: #{result.objects}"
puts "Memory used: #{result.memory} bytes"
Benchmark::Tms Class
Holds timing measurement results. Provides methods to access individual timing components.
Attributes
utime- User CPU time in seconds (Float)stime- System CPU time in seconds (Float)cutime- User CPU time of child processes (Float, usually 0 in mruby)cstime- System CPU time of child processes (Float, usually 0 in mruby)real- Real (wall-clock) time in seconds (Float)objects- Number of objects allocated (Integer, when memory tracking enabled)memory- Memory allocated in bytes (Integer, when memory tracking enabled)
Methods
total → Float
Returns the total CPU time (user + system).
result = Benchmark.measure { heavy_computation }
puts "Total CPU time: #{result.total} seconds"
to_s → String
Returns formatted string representation of timing results.
result = Benchmark.measure { sleep(0.1) }
puts result.to_s
# => " 0.000000 0.000000 0.000000 ( 0.100123)"
format(format_str) → String
Returns timing results formatted according to the format string.
Format specifiers:
%u- User CPU time%s- System CPU time%t- Total CPU time%r- Real time%o- Objects allocated (if memory tracking enabled)%m- Memory allocated (if memory tracking enabled)%n- Label name
result = Benchmark.measure { computation }
puts result.format("Real: %rs, CPU: %ts")
# => "Real: 0.123s, CPU: 0.100s"
Benchmark::Report Class
Used within Benchmark.bm for formatted reporting.
report(label = "") { block }
Executes and reports on a single benchmark within a bm block.
Benchmark.bm do |x|
x.report("first test") { code1 }
x.report("second test") { code2 }
end
Usage Examples
Basic Timing
require 'benchmark'
# Simple timing
time = Benchmark.realtime do
sum = 0
1000000.times { |i| sum += i }
end
puts "Calculation took #{time} seconds"
# Detailed timing
result = Benchmark.measure do
arr = (1..10000).to_a
arr.sort!
end
puts result
Comparing Implementations
require 'benchmark'
Benchmark.bm(15) do |x|
x.report("Array#each:") do
arr = (1..1000).to_a
sum = 0
arr.each { |n| sum += n }
end
x.report("Array#inject:") do
arr = (1..1000).to_a
arr.inject(0) { |sum, n| sum + n }
end
x.report("Numeric#times:") do
sum = 0
1000.times { |n| sum += n }
end
end
Memory Profiling
require 'benchmark'
# Track memory allocation
result = Benchmark.measure(memory: true) do
strings = []
1000.times { |i| strings << "string_#{i}" }
end
puts "Execution time: #{result.real}s"
puts "Objects created: #{result.objects}"
puts "Memory allocated: #{result.memory} bytes"
Performance Testing in Tests
# In test files
assert('String concatenation performance') do
time = Benchmark.realtime do
1000.times { "hello" + "world" }
end
# Assert it completes within reasonable time
assert_true time < 0.1, "String concat should be fast"
end
Implementation Notes
Time Measurement
mruby-benchmark uses Process.clock_gettime (via mruby-time) for high-resolution timing when available. User and system CPU times are measured using platform-specific APIs where available, otherwise both are set to 0.
Memory Tracking
Memory profiling uses ObjectSpace.count_objects (via mruby-objectspace) to track object allocation. Memory size estimation is based on typical object overhead and may not be exact for all platforms.
Limitations
- Child process timing (
cutime,cstime) is not supported in most mruby environments and always returns 0 - System CPU time may not be available on all platforms
- Memory measurements are estimates and may not reflect actual heap usage
- GC activity during benchmarking may affect timing results
Dependencies
- mruby-time - Required for timing measurements
- mruby-objectspace - Required for memory profiling
License
MIT License
Authors
mruby developers