#-- # $Id: tc_monad.rb 31 2006-12-28 02:28:28Z prelude $ # # # This file is part of the Prelude library that provides tools to # enable Haskell style functional programming in Ruby. # # http://prelude.rubyforge.org # # Copyright (C) 2006 APP Design, Inc. # # This library is free software; you can redistribute it and/or # modify it under the terms of the GNU Lesser General Public # License as published by the Free Software Foundation; either # version 2.1 of the License, or (at your option) any later version. # # This library is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # Lesser General Public License for more details. # # You should have received a copy of the GNU Lesser General Public # License along with this library; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA #++ require 'prelude' # A test class representing a genesis of a possible cloned animal class Cloned include Prelude::Monad attr_reader :name, :mother, :father def initialize(n, m, f) @name = n @mother = m @father = f end def to_s self.nil? ? 'null' : name end # Traditional versions def maternalGrandfather mother ? mother.father : nil end def mothersPaternalGrandfather mother ? (mother.father ? mother.father.father : nil) : nil end # Monadic versions def m_maternalGrandfather wrap >> :mother >> :father >> unwrap end def m_mothersPaternalGrandfather wrap.bind(:mother).bind(:father).bind(:father).unwrap end end # Cloned class TestMonad < Test::Unit::TestCase def setup @grandgrandpa = Cloned.new('Grandgrandpa', nil, nil) @grandma = Cloned.new('Grandma', nil, @grandgrandpa) @grandpa = Cloned.new('Grandpa', nil, nil) @daddy = Cloned.new('Daddy', @grandma, nil) @mommy = Cloned.new('Mommy', nil, @grandpa) @sheep = Cloned.new('Dolly', @mommy, @daddy) end # setup def teardown # Nothing end # teardown def test_monad result = [nil, nil] expect = [nil, nil] assert_equal(expect, result) end def test_no_bind result = @sheep.maternalGrandfather expect = @grandpa assert_equal(expect, result) result = @sheep.mothersPaternalGrandfather expect = nil assert_equal(expect, result) end def test_bind # Wrap and >> result = @sheep.wrap >> :mother >> :father >> @sheep.unwrap expect = @grandpa assert_equal(expect, result) # Wrap and bind result = @sheep.wrap.bind(:mother).bind(:father).bind(:father).unwrap expect = nil assert_equal(expect, result) # Auto-wrap and >> result = @sheep >> :mother >> :father >> @sheep.unwrap expect = @grandpa assert_equal(expect, result) # Auto-wrap and bind result = @sheep.bind(:mother).bind(:father).bind(:father).unwrap expect = nil assert_equal(expect, result) end end # TestMonad