Skip to content

Instantly share code, notes, and snippets.

@ioquatix
Created April 2, 2020 10:39
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save ioquatix/617757309c5c052c5d6b1a6723187f4d to your computer and use it in GitHub Desktop.
Save ioquatix/617757309c5c052c5d6b1a6723187f4d to your computer and use it in GitHub Desktop.
Compare Monads with Pure Ruby
require 'benchmark/ips'
require 'dry/monads/result'
extend Dry::Monads::Result::Mixin
def pure_square(x)
value = x ** 2
if value > 50
return :number_too_large
else
return value
end
end
def mixed_square(x)
value = x ** 2
if value > 50
return Failure(:number_too_large)
else
return Success(value)
end
end
# Taken from https://www.morozov.is/2018/09/08/monad-laws-in-ruby.html
def monad_square(x)
Success(x).bind do |value|
Success(value ** 2)
end.bind do |value|
if value > 50
Failure(:number_too_large)
else
Success(value)
end
end
end
require 'benchmark/ips'
Benchmark.ips do |x|
x.report("pure_square(10)") do |times|
while (times -= 1) >= 0
pure_square(10)
end
end
x.report("mixed_square(10)") do |times|
while (times -= 1) >= 0
mixed_square(10)
end
end
x.report("monad_square(10)") do |times|
while (times -= 1) >= 0
monad_square(10)
end
end
x.compare!
end
# Warming up --------------------------------------
# pure_square(10) 439.179k i/100ms
# mixed_square(10) 57.390k i/100ms
# monad_square(10) 30.903k i/100ms
# Calculating -------------------------------------
# pure_square(10) 18.275M (± 8.0%) i/s - 90.471M in 4.999792s
# mixed_square(10) 654.150k (± 9.1%) i/s - 3.271M in 5.050263s
# monad_square(10) 336.968k (± 5.1%) i/s - 1.700M in 5.058423s
#
# Comparison:
# pure_square(10): 18275153.1 i/s
# mixed_square(10): 654150.0 i/s - 27.94x slower
# monad_square(10): 336968.4 i/s - 54.23x slower
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment