-
-
Save anonymous/21e3aed658edd7b0f785 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/usr/bin/env ruby | |
# http://clojure.org/runtime_polymorphism | |
=begin | |
(defmulti encounter (fn [x y] [(:Species x) (:Species y)])) | |
(defmethod encounter [:Bunny :Lion] [b l] :run-away) | |
(defmethod encounter [:Lion :Bunny] [l b] :eat) | |
(defmethod encounter [:Lion :Lion] [l1 l2] :fight) | |
(defmethod encounter [:Bunny :Bunny] [b1 b2] :mate) | |
(def b1 {:Species :Bunny :other :stuff}) | |
(def b2 {:Species :Bunny :other :stuff}) | |
(def l1 {:Species :Lion :other :stuff}) | |
(def l2 {:Species :Lion :other :stuff}) | |
(encounter b1 b2) | |
-> :mate | |
(encounter b1 l1) | |
-> :run-away | |
(encounter l1 b1) | |
-> :eat | |
(encounter l1 l2) | |
-> :fight | |
=end | |
class DefMulti | |
def initialize &block | |
@dispatcher = block | |
@methods = [] | |
end | |
def defmethod pattern, &block | |
@methods << [pattern,block] | |
end | |
def dispatch *args | |
_pattern = @dispatcher.call *args | |
@methods.each do |pattern,method| | |
return method.call *args if _pattern == pattern | |
end | |
end | |
end | |
encounter = DefMulti.new { |x,y| [x[:Species],y[:Species]] } | |
encounter.defmethod([:Bunny,:Lion]){|b,l| :run_away } | |
encounter.defmethod([:Lion,:Bunny]){|l,b| :eat } | |
encounter.defmethod([:Lion,:Lion]){|l1,l2| :fight } | |
encounter.defmethod([:Bunny,:Bunny]){|b1,b2| :mate } | |
b1={:Species => :Bunny, :other => :stuff} | |
b2={:Species => :Bunny, :other => :stuff} | |
l1={:Species => :Lion, :other => :stuff} | |
l2={:Species => :Lion, :other => :stuff} | |
puts encounter.dispatch b1, b2 | |
puts encounter.dispatch b1, l1 | |
puts encounter.dispatch l1, b1 | |
puts encounter.dispatch l1, l2 | |
=begin | |
# Output | |
mate | |
run_away | |
eat | |
fight | |
=end |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment