From: David Tran Date: 2006-03-16T09:00:45+09:00 Subject: [SOLUTION] Constraint Processing (#70) Just finish my solution, I run out of time to provide an example ... define the domain as instance variable. define the rule by using block & instance variable. define the solution block by using instance variable. ( all block will exec on "Engine"'s instance_eval ) class Engine def go(&solution) solve(instance_variables, &solution) end private def method_missing(name, *args, &block) if name.to_s =~ /=$/ && block.nil? vars(name, *args) elsif args.size == 0 && !block.nil? rules(name, &block) else super end end def rules(name, &block) self.class.send(:define_method, name, &block) self.class.send(:protected, name) end def vars(name, *args) name = name.to_s.sub(/=$/, '') self.class.class_eval("attr_accessor :#{name}") args = args[0] if args.size == 1 && args[0].respond_to?(:each) instance_variable_set("@#{name}", args) end def solve(vars, &solution) if (vars.size != 0) name = vars.shift value = instance_variable_get(name) value.each { |e| instance_variable_set(name, e) solve(vars.dup, &solution) } instance_variable_set(name, value) else protected_methods.each { |method| return if !send(method) } instance_eval(&solution) end end end if __FILE__ == $0 e = Engine.new e.a = 0..4 e.b = 0..4 e.c = 0..4 e.rule1 { @a < @b } e.rule2 { @a + @b == @c } e.go { puts "a => #@a, b => #@b, c => #@c" } end __END__ -- www.doublegifts.com