Module: Rumonade::Monad

Includes:
Enumerable
Included in:
Either::LeftProjection, Either::RightProjection, Option
Defined in:
lib/rumonade/monad.rb

Overview

Mix-in for common monad functionality dependent on implementation of monadic methods unit and bind

Notes:

  • classes should include this module AFTER defining the monadic methods unit and bind

Constant Summary collapse

METHODS_TO_REPLACE =

:nodoc:

[:flat_map, :flatten]

Class Method Summary collapse

Instance Method Summary collapse

Class Method Details

.included(base) ⇒ Object

:nodoc:



10
11
12
13
14
15
16
17
18
19
20
21
# File 'lib/rumonade/monad.rb', line 10

def self.included(base) # :nodoc:
  base.class_eval do
    # optimization: replace flat_map with an alias for bind, as they are identical
    alias_method :flat_map_with_monad, :bind

    # force only a few methods to be aliased to monad versions; others can stay with native or Enumerable versions
    METHODS_TO_REPLACE.each do |method_name|
      alias_method "#{method_name}_without_monad".to_sym, method_name if public_instance_methods.include? method_name
      alias_method method_name, "#{method_name}_with_monad".to_sym
    end
  end
end

Instance Method Details

#each(lam = nil, &blk) ⇒ Object

Applies the given procedure to each element in this monad



26
27
28
# File 'lib/rumonade/monad.rb', line 26

def each(lam = nil, &blk)
  bind { |v| (lam || blk).call(v) }; nil
end

#flat_map_with_monad(lam = nil, &blk) ⇒ Object

Returns the results of applying the given function to each element in this monad



36
37
38
# File 'lib/rumonade/monad.rb', line 36

def flat_map_with_monad(lam = nil, &blk)
  bind(lam || blk)
end

#flatten_with_monadObject

Returns a monad whose elements are the ultimate (non-monadic) values contained in all nested monads

[1] == [[Some(Some(1)), Some(Some(None))], [None]].flatten
=> true


45
46
47
# File 'lib/rumonade/monad.rb', line 45

def flatten_with_monad
  bind { |x| x.is_a?(Monad) ? x.flatten_with_monad : self.class.unit(x) }
end

#map(lam = nil, &blk) ⇒ Object

Returns a monad whose elements are the results of applying the given function to each element in this monad



31
32
33
# File 'lib/rumonade/monad.rb', line 31

def map(lam = nil, &blk)
  bind { |v| self.class.unit((lam || blk).call(v)) }
end

#select(lam = nil, &blk) ⇒ Object Also known as: find_all

Returns a monad whose elements are all those elements of this monad for which the given predicate returned true



50
51
52
# File 'lib/rumonade/monad.rb', line 50

def select(lam = nil, &blk)
  bind { |x| (lam || blk).call(x) ? self.class.unit(x) : self.class.empty }
end

#shallow_flattenObject

Returns a monad whose elements are the values contained in the first level of nested monads

This method is equivalent to the Scala flatten call (single-level flattening), whereas #flatten is in keeping with the native Ruby flatten calls (multiple-level flattening).



60
61
62
# File 'lib/rumonade/monad.rb', line 60

def shallow_flatten
  bind { |x| x.is_a?(Monad) ? x : self.class.unit(x) }
end