"Florian Weber" <csshsh / structbench.com> schrieb im Newsbeitrag news:D83A07D2-AE5C-11D8-A68B-000A95BD142E / structbench.com... > hi! > > im trying to define a set of rules with ruby, however i cant find a more > ruby-like way to do so.. > > instead of doing something like > > my_set.add(NotNamedRule("orange").new) > my_set.add(HasPropertyRule("color").new) > my_set.add(OrRule(HasPropertyRule("size").new, > HasPropertyRule("weight").new)) > > (i know this is a horrible example. excuse the awful 'design'. its > justs to illustrate > what i not wanna have ; ) > > i wanna do something like > > my_set.rules = !name("orange") && hasProperty("color") && > (hasProperty("size") || hasProperty("weight")) You won't be able to make this work as rule creation because of short circuit evaluation of '&&' and '||'. > can anybody think of a nice way to do this? You could do: #!/#!/usr/bin/ruby module Rule def self.create(&b) def b.===(obj) call obj end b end def self.and(*rules) def rules.===(obj) all? {|r| r === obj} end rules end def self.or(*rules) def rules.===(obj) any? {|r| r === obj} end rules end end r1 = Rule.create {|o| o.name != "orange" && o.color && (o.size || o.weight) } r2 = Rule.create {|o| o.name == "orange" && o.color && (o.size || o.weight) } require 'ostruct' obj = OpenStruct.new obj.name = "green" obj.color = "yellow" obj.size = 10 p r1 === obj p Rule.and( r1, r2 ) === obj p Rule.or( r1, r2 ) === obj R#!/usr/bin/ruby module Rule def self.create(&b) def b.===(obj) call obj end b end def self.and(*rules) def rules.===(obj) all? {|r| r === obj} end rules end def self.or(*rules) def rules.===(obj) any? {|r| r === obj} end rules end end r1 = Rule.create {|o| o.name != "orange" && o.color && (o.size || o.weight) } r2 = Rule.create {|o| o.name == "orange" && o.color && (o.size || o.weight) } # testing... require 'ostruct' obj = OpenStruct.new obj.name = "green" obj.color = "yellow" obj.size = 10 p r1 === obj p Rule.and( r1, r2 ) === obj p Rule.or( r1, r2 ) === obj Regards robert