gecoder-with-gecode 0.7.1-mswin32

Sign up to get free protection for your applications and to get access to all the features.
Files changed (159) hide show
  1. data/CHANGES +81 -0
  2. data/COPYING +17 -0
  3. data/LGPL-LICENSE +458 -0
  4. data/README +45 -0
  5. data/Rakefile +13 -0
  6. data/example/example_helper.rb +1 -0
  7. data/example/magic_sequence.rb +43 -0
  8. data/example/queens.rb +43 -0
  9. data/example/raw_bindings.rb +42 -0
  10. data/example/send_more_money.rb +43 -0
  11. data/example/send_most_money.rb +58 -0
  12. data/example/square_tiling.rb +84 -0
  13. data/example/sudoku-set.rb +110 -0
  14. data/example/sudoku.rb +61 -0
  15. data/lib/gecode.dll +0 -0
  16. data/lib/gecoder.rb +5 -0
  17. data/lib/gecoder/bindings.rb +54 -0
  18. data/lib/gecoder/bindings/bindings.rb +2210 -0
  19. data/lib/gecoder/interface.rb +8 -0
  20. data/lib/gecoder/interface/binding_changes.rb +313 -0
  21. data/lib/gecoder/interface/branch.rb +152 -0
  22. data/lib/gecoder/interface/constraints.rb +397 -0
  23. data/lib/gecoder/interface/constraints/bool/boolean.rb +246 -0
  24. data/lib/gecoder/interface/constraints/bool/linear.rb +29 -0
  25. data/lib/gecoder/interface/constraints/bool_enum/boolean.rb +84 -0
  26. data/lib/gecoder/interface/constraints/bool_enum_constraints.rb +8 -0
  27. data/lib/gecoder/interface/constraints/bool_var_constraints.rb +75 -0
  28. data/lib/gecoder/interface/constraints/int/arithmetic.rb +71 -0
  29. data/lib/gecoder/interface/constraints/int/domain.rb +78 -0
  30. data/lib/gecoder/interface/constraints/int/linear.rb +295 -0
  31. data/lib/gecoder/interface/constraints/int_enum/arithmetic.rb +72 -0
  32. data/lib/gecoder/interface/constraints/int_enum/channel.rb +100 -0
  33. data/lib/gecoder/interface/constraints/int_enum/count.rb +92 -0
  34. data/lib/gecoder/interface/constraints/int_enum/distinct.rb +69 -0
  35. data/lib/gecoder/interface/constraints/int_enum/element.rb +82 -0
  36. data/lib/gecoder/interface/constraints/int_enum/equality.rb +38 -0
  37. data/lib/gecoder/interface/constraints/int_enum/sort.rb +126 -0
  38. data/lib/gecoder/interface/constraints/int_enum_constraints.rb +37 -0
  39. data/lib/gecoder/interface/constraints/int_var_constraints.rb +58 -0
  40. data/lib/gecoder/interface/constraints/reifiable_constraints.rb +78 -0
  41. data/lib/gecoder/interface/constraints/set/cardinality.rb +75 -0
  42. data/lib/gecoder/interface/constraints/set/connection.rb +193 -0
  43. data/lib/gecoder/interface/constraints/set/domain.rb +109 -0
  44. data/lib/gecoder/interface/constraints/set/operation.rb +132 -0
  45. data/lib/gecoder/interface/constraints/set/relation.rb +178 -0
  46. data/lib/gecoder/interface/constraints/set_enum/channel.rb +18 -0
  47. data/lib/gecoder/interface/constraints/set_enum/distinct.rb +80 -0
  48. data/lib/gecoder/interface/constraints/set_enum/operation.rb +60 -0
  49. data/lib/gecoder/interface/constraints/set_enum/selection.rb +217 -0
  50. data/lib/gecoder/interface/constraints/set_enum_constraints.rb +34 -0
  51. data/lib/gecoder/interface/constraints/set_var_constraints.rb +72 -0
  52. data/lib/gecoder/interface/enum_matrix.rb +64 -0
  53. data/lib/gecoder/interface/enum_wrapper.rb +153 -0
  54. data/lib/gecoder/interface/model.rb +251 -0
  55. data/lib/gecoder/interface/search.rb +123 -0
  56. data/lib/gecoder/interface/variables.rb +254 -0
  57. data/lib/gecoder/version.rb +4 -0
  58. data/specs/binding_changes.rb +76 -0
  59. data/specs/bool_var.rb +74 -0
  60. data/specs/branch.rb +170 -0
  61. data/specs/constraints/arithmetic.rb +266 -0
  62. data/specs/constraints/bool_enum.rb +140 -0
  63. data/specs/constraints/boolean.rb +232 -0
  64. data/specs/constraints/cardinality.rb +154 -0
  65. data/specs/constraints/channel.rb +126 -0
  66. data/specs/constraints/connection.rb +373 -0
  67. data/specs/constraints/constraint_helper.rb +180 -0
  68. data/specs/constraints/constraints.rb +74 -0
  69. data/specs/constraints/count.rb +139 -0
  70. data/specs/constraints/distinct.rb +218 -0
  71. data/specs/constraints/element.rb +106 -0
  72. data/specs/constraints/equality.rb +31 -0
  73. data/specs/constraints/int_domain.rb +69 -0
  74. data/specs/constraints/int_relation.rb +78 -0
  75. data/specs/constraints/linear.rb +332 -0
  76. data/specs/constraints/reification_sugar.rb +96 -0
  77. data/specs/constraints/selection.rb +292 -0
  78. data/specs/constraints/set_domain.rb +181 -0
  79. data/specs/constraints/set_operation.rb +285 -0
  80. data/specs/constraints/set_relation.rb +201 -0
  81. data/specs/constraints/sort.rb +175 -0
  82. data/specs/distribution.rb +14 -0
  83. data/specs/enum_matrix.rb +43 -0
  84. data/specs/enum_wrapper.rb +122 -0
  85. data/specs/int_var.rb +144 -0
  86. data/specs/logging.rb +24 -0
  87. data/specs/model.rb +190 -0
  88. data/specs/search.rb +246 -0
  89. data/specs/set_var.rb +68 -0
  90. data/specs/spec_helper.rb +93 -0
  91. data/tasks/all_tasks.rb +1 -0
  92. data/tasks/building.howto +65 -0
  93. data/tasks/distribution.rake +156 -0
  94. data/tasks/rcov.rake +17 -0
  95. data/tasks/specs.rake +15 -0
  96. data/tasks/svn.rake +11 -0
  97. data/tasks/website.rake +51 -0
  98. data/vendor/gecode/win32/lib/libgecodeint.dll +0 -0
  99. data/vendor/gecode/win32/lib/libgecodekernel.dll +0 -0
  100. data/vendor/gecode/win32/lib/libgecodeminimodel.dll +0 -0
  101. data/vendor/gecode/win32/lib/libgecodesearch.dll +0 -0
  102. data/vendor/gecode/win32/lib/libgecodeset.dll +0 -0
  103. data/vendor/rust/README +28 -0
  104. data/vendor/rust/bin/cxxgenerator.rb +93 -0
  105. data/vendor/rust/include/rust_checks.hh +115 -0
  106. data/vendor/rust/include/rust_conversions.hh +102 -0
  107. data/vendor/rust/rust.rb +67 -0
  108. data/vendor/rust/rust/attribute.rb +51 -0
  109. data/vendor/rust/rust/bindings.rb +172 -0
  110. data/vendor/rust/rust/class.rb +339 -0
  111. data/vendor/rust/rust/constants.rb +48 -0
  112. data/vendor/rust/rust/container.rb +110 -0
  113. data/vendor/rust/rust/cppifaceparser.rb +129 -0
  114. data/vendor/rust/rust/cwrapper.rb +72 -0
  115. data/vendor/rust/rust/cxxclass.rb +98 -0
  116. data/vendor/rust/rust/element.rb +81 -0
  117. data/vendor/rust/rust/enum.rb +63 -0
  118. data/vendor/rust/rust/function.rb +407 -0
  119. data/vendor/rust/rust/namespace.rb +61 -0
  120. data/vendor/rust/rust/templates/AttributeDefinition.rusttpl +17 -0
  121. data/vendor/rust/rust/templates/AttributeInitBinding.rusttpl +9 -0
  122. data/vendor/rust/rust/templates/BindingsHeader.rusttpl +24 -0
  123. data/vendor/rust/rust/templates/BindingsUnit.rusttpl +46 -0
  124. data/vendor/rust/rust/templates/CWrapperClassDefinitions.rusttpl +64 -0
  125. data/vendor/rust/rust/templates/ClassDeclarations.rusttpl +7 -0
  126. data/vendor/rust/rust/templates/ClassInitialize.rusttpl +6 -0
  127. data/vendor/rust/rust/templates/ConstructorStub.rusttpl +21 -0
  128. data/vendor/rust/rust/templates/CxxClassDefinitions.rusttpl +91 -0
  129. data/vendor/rust/rust/templates/CxxMethodStub.rusttpl +12 -0
  130. data/vendor/rust/rust/templates/CxxStandaloneClassDefinitions.rusttpl +26 -0
  131. data/vendor/rust/rust/templates/EnumDeclarations.rusttpl +3 -0
  132. data/vendor/rust/rust/templates/EnumDefinitions.rusttpl +29 -0
  133. data/vendor/rust/rust/templates/FunctionDefinition.rusttpl +9 -0
  134. data/vendor/rust/rust/templates/FunctionInitAlias.rusttpl +5 -0
  135. data/vendor/rust/rust/templates/FunctionInitBinding.rusttpl +9 -0
  136. data/vendor/rust/rust/templates/MethodInitBinding.rusttpl +9 -0
  137. data/vendor/rust/rust/templates/ModuleDeclarations.rusttpl +3 -0
  138. data/vendor/rust/rust/templates/ModuleDefinitions.rusttpl +3 -0
  139. data/vendor/rust/rust/templates/StandaloneClassDeclarations.rusttpl +7 -0
  140. data/vendor/rust/rust/templates/VariableFunctionCall.rusttpl +14 -0
  141. data/vendor/rust/rust/type.rb +98 -0
  142. data/vendor/rust/test/Makefile +4 -0
  143. data/vendor/rust/test/constants.rb +36 -0
  144. data/vendor/rust/test/cppclass.cc +45 -0
  145. data/vendor/rust/test/cppclass.hh +67 -0
  146. data/vendor/rust/test/cppclass.rb +59 -0
  147. data/vendor/rust/test/cwrapper.c +74 -0
  148. data/vendor/rust/test/cwrapper.h +41 -0
  149. data/vendor/rust/test/cwrapper.rb +56 -0
  150. data/vendor/rust/test/dummyclass.hh +31 -0
  151. data/vendor/rust/test/lib/extension-test.rb +98 -0
  152. data/vendor/rust/test/operators.cc +41 -0
  153. data/vendor/rust/test/operators.hh +39 -0
  154. data/vendor/rust/test/operators.rb +39 -0
  155. data/vendor/rust/test/test-constants.rb +43 -0
  156. data/vendor/rust/test/test-cppclass.rb +82 -0
  157. data/vendor/rust/test/test-cwrapper.rb +80 -0
  158. data/vendor/rust/test/test-operators.rb +42 -0
  159. metadata +293 -0
@@ -0,0 +1,106 @@
1
+ require File.dirname(__FILE__) + '/../spec_helper'
2
+ require File.dirname(__FILE__) + '/constraint_helper'
3
+
4
+ class ElementSampleProblem < Gecode::Model
5
+ attr :prices
6
+ attr :store
7
+ attr :price
8
+ attr :fixnum_prices
9
+
10
+ def initialize
11
+ prices = [17, 63, 45, 63]
12
+ @fixnum_prices = wrap_enum(prices)
13
+ @prices = int_var_array(4, prices)
14
+ @store = int_var(0...prices.size)
15
+ @price = int_var(prices)
16
+ branch_on wrap_enum([@store])
17
+ end
18
+ end
19
+
20
+ describe Gecode::Constraints::IntEnum::Element do
21
+ before do
22
+ @model = ElementSampleProblem.new
23
+ @prices = @model.prices
24
+ @target = @price = @model.price
25
+ @store = @model.store
26
+ @fixnum_prices = @model.fixnum_prices
27
+
28
+ # Creates an expectation corresponding to the specified input.
29
+ @expect = lambda do |element, relation, target, strength, reif_var, negated|
30
+ @model.allow_space_access do
31
+ target = an_instance_of(Gecode::Raw::IntVar) if target.respond_to? :bind
32
+ element = an_instance_of(Gecode::Raw::IntVar) if element.respond_to? :bind
33
+ if reif_var.nil?
34
+ if !negated and relation == Gecode::Raw::IRT_EQ and
35
+ !target.kind_of? Fixnum
36
+ Gecode::Raw.should_receive(:element).once.with(
37
+ an_instance_of(Gecode::Raw::Space),
38
+ an_instance_of(Gecode::Raw::IntVarArray),
39
+ element, target, strength)
40
+ else
41
+ Gecode::Raw.should_receive(:element).once.with(
42
+ an_instance_of(Gecode::Raw::Space),
43
+ an_instance_of(Gecode::Raw::IntVarArray),
44
+ element, an_instance_of(Gecode::Raw::IntVar), strength)
45
+ Gecode::Raw.should_receive(:rel).once.with(
46
+ an_instance_of(Gecode::Raw::Space),
47
+ an_instance_of(Gecode::Raw::IntVar), relation, target, strength)
48
+ end
49
+ else
50
+ Gecode::Raw.should_receive(:element).once.with(
51
+ an_instance_of(Gecode::Raw::Space),
52
+ an_instance_of(Gecode::Raw::IntVarArray),
53
+ element, an_instance_of(Gecode::Raw::IntVar), strength)
54
+ Gecode::Raw.should_receive(:rel).once.with(
55
+ an_instance_of(Gecode::Raw::Space),
56
+ an_instance_of(Gecode::Raw::IntVar), relation, target,
57
+ an_instance_of(Gecode::Raw::BoolVar), strength)
58
+ end
59
+ end
60
+ end
61
+
62
+ # For constraint option spec.
63
+ @invoke_options = lambda do |hash|
64
+ @prices[@store].must_be.greater_than(@price, hash)
65
+ @model.solve!
66
+ end
67
+ @expect_options = lambda do |strength, reif_var|
68
+ @expect.call(@store, Gecode::Raw::IRT_GR, @price, strength, reif_var,
69
+ false)
70
+ end
71
+
72
+ # For composite spec.
73
+ @invoke_relation = lambda do |relation, target, negated|
74
+ if negated
75
+ @prices[@store].must_not.send(relation, target)
76
+ else
77
+ @prices[@store].must.send(relation, target)
78
+ end
79
+ @model.solve!
80
+ end
81
+ @expect_relation = lambda do |relation, target, negated|
82
+ @expect.call(@store, relation, target, Gecode::Raw::ICL_DEF, nil, negated)
83
+ end
84
+ end
85
+
86
+ it 'should not disturb normal array access' do
87
+ @fixnum_prices[2].should_not be_nil
88
+ @prices[2].should_not be_nil
89
+ end
90
+
91
+ it 'should handle fixnum enums as enumeration' do
92
+ @fixnum_prices[@store].must == @fixnum_prices[2]
93
+ @model.solve!.store.value.should equal(2)
94
+ end
95
+
96
+ it 'should translate reification when using equality' do
97
+ bool_var = @model.bool_var
98
+ @expect.call(@store, Gecode::Raw::IRT_EQ, @target, Gecode::Raw::ICL_DEF,
99
+ bool_var, false)
100
+ @prices[@store].must_be.equal_to(@target, :reify => bool_var)
101
+ @model.solve!
102
+ end
103
+
104
+ it_should_behave_like 'composite constraint'
105
+ it_should_behave_like 'constraint with options'
106
+ end
@@ -0,0 +1,31 @@
1
+ require File.dirname(__FILE__) + '/../spec_helper'
2
+ require File.dirname(__FILE__) + '/constraint_helper'
3
+
4
+ describe Gecode::Constraints::IntEnum::Equality do
5
+ before do
6
+ @model = Gecode::Model.new
7
+ @vars = @model.int_var_array(4, -2..2)
8
+ @invoke_options = lambda do |hash|
9
+ @vars.must_be.equal(hash)
10
+ @model.solve!
11
+ end
12
+ @expect_options = lambda do |strength, reif_var|
13
+ Gecode::Raw.should_receive(:eq).once.with(
14
+ an_instance_of(Gecode::Raw::Space),
15
+ anything, strength)
16
+ end
17
+ end
18
+
19
+ it 'should translate equality constraints' do
20
+ @expect_options.call(Gecode::Raw::ICL_DEF, nil)
21
+ @invoke_options.call({})
22
+ @vars.must_be.equal
23
+ end
24
+
25
+ it 'should not allow negation' do
26
+ lambda{ @vars.must_not_be.equal }.should raise_error(
27
+ Gecode::MissingConstraintError)
28
+ end
29
+
30
+ it_should_behave_like 'constraint with strength option'
31
+ end
@@ -0,0 +1,69 @@
1
+ require File.dirname(__FILE__) + '/../spec_helper'
2
+ require File.dirname(__FILE__) + '/constraint_helper'
3
+
4
+ describe Gecode::Constraints::Int::Domain do
5
+ before do
6
+ @model = Gecode::Model.new
7
+ @domain = 0..3
8
+ @x = @model.int_var(@domain)
9
+ @range_domain = 1..2
10
+ @three_dot_range_domain = 1...2
11
+ @non_range_domain = [1, 3]
12
+
13
+ @invoke_options = lambda do |hash|
14
+ @x.must_be.in(@non_range_domain, hash)
15
+ @model.solve!
16
+ end
17
+ @expect_options = lambda do |strength, reif_var|
18
+ @model.allow_space_access do
19
+ if reif_var.nil?
20
+ Gecode::Raw.should_receive(:dom).once.with(
21
+ an_instance_of(Gecode::Raw::Space),
22
+ an_instance_of(Gecode::Raw::IntVar),
23
+ an_instance_of(Gecode::Raw::IntSet), strength)
24
+ else
25
+ Gecode::Raw.should_receive(:dom).once.with(
26
+ an_instance_of(Gecode::Raw::Space),
27
+ an_instance_of(Gecode::Raw::IntVar),
28
+ an_instance_of(Gecode::Raw::IntSet),
29
+ an_instance_of(Gecode::Raw::BoolVar), strength)
30
+ end
31
+ end
32
+ end
33
+ end
34
+
35
+ it 'should translate domain constraints with range domains' do
36
+ Gecode::Raw.should_receive(:dom).once.with(
37
+ an_instance_of(Gecode::Raw::Space),
38
+ an_instance_of(Gecode::Raw::IntVar), @range_domain.first,
39
+ @range_domain.last, Gecode::Raw::ICL_DEF)
40
+ @x.must_be.in @range_domain
41
+ @model.solve!
42
+ end
43
+
44
+ it 'should translate domain constraints with three dot range domains' do
45
+ Gecode::Raw.should_receive(:dom).once.with(
46
+ an_instance_of(Gecode::Raw::Space),
47
+ an_instance_of(Gecode::Raw::IntVar), @three_dot_range_domain.first,
48
+ @three_dot_range_domain.last, Gecode::Raw::ICL_DEF)
49
+ @x.must_be.in @three_dot_range_domain
50
+ @model.solve!
51
+ end
52
+
53
+ it 'should translate domain constraints with non-range domains' do
54
+ @expect_options.call(Gecode::Raw::ICL_DEF, nil)
55
+ @invoke_options.call({})
56
+ end
57
+
58
+ it 'should handle negation' do
59
+ @x.must_not_be.in @range_domain
60
+ @model.solve!
61
+ @x.should have_domain(@domain.to_a - @range_domain.to_a)
62
+ end
63
+
64
+ it 'should raise error if the right hand side is not an enumeration' do
65
+ lambda{ @x.must_be.in 'hello' }.should raise_error(TypeError)
66
+ end
67
+
68
+ it_should_behave_like 'constraint with options'
69
+ end
@@ -0,0 +1,78 @@
1
+ require File.dirname(__FILE__) + '/../spec_helper'
2
+ require File.dirname(__FILE__) + '/constraint_helper'
3
+
4
+ describe Gecode::Constraints::Int::Linear, ' (simple ones)' do
5
+ before do
6
+ @model = Gecode::Model.new
7
+ @x = @model.int_var(1..2)
8
+ @int = 4
9
+ @y = @model.int_var(1..2)
10
+
11
+ # For constraint option spec.
12
+ @invoke_options = lambda do |hash|
13
+ @x.must_be.greater_than(3, hash)
14
+ @model.solve!
15
+ end
16
+ @expect_options = lambda do |strength, reif_var|
17
+ if reif_var.nil?
18
+ Gecode::Raw.should_receive(:rel).once.with(
19
+ an_instance_of(Gecode::Raw::Space),
20
+ anything, Gecode::Raw::IRT_GR, anything,
21
+ strength)
22
+ else
23
+ Gecode::Raw.should_receive(:rel).once.with(
24
+ an_instance_of(Gecode::Raw::Space),
25
+ an_instance_of(Gecode::Raw::IntVar), Gecode::Raw::IRT_GR, anything,
26
+ an_instance_of(Gecode::Raw::BoolVar), strength)
27
+ end
28
+ end
29
+ end
30
+
31
+ Gecode::Constraints::Util::RELATION_TYPES.each_pair do |relation, type|
32
+ it "should translate #{relation} with constant to simple relation" do
33
+ Gecode::Raw.should_receive(:rel).once.with(
34
+ an_instance_of(Gecode::Raw::Space),
35
+ an_instance_of(Gecode::Raw::IntVar), type, @int, Gecode::Raw::ICL_DEF)
36
+ @x.must.send(relation, @int)
37
+ @model.solve!
38
+ end
39
+ end
40
+
41
+ Gecode::Constraints::Util::NEGATED_RELATION_TYPES.each_pair do |relation, type|
42
+ it "should translate negated #{relation} with constant to simple relation" do
43
+ Gecode::Raw.should_receive(:rel).once.with(
44
+ an_instance_of(Gecode::Raw::Space),
45
+ an_instance_of(Gecode::Raw::IntVar), type, @int, Gecode::Raw::ICL_DEF)
46
+ @x.must_not.send(relation, @int)
47
+ @model.solve!
48
+ end
49
+ end
50
+
51
+ Gecode::Constraints::Util::RELATION_TYPES.each_pair do |relation, type|
52
+ it "should translate #{relation} with variables to simple relation" do
53
+ Gecode::Raw.should_receive(:rel).once.with(
54
+ an_instance_of(Gecode::Raw::Space),
55
+ an_instance_of(Gecode::Raw::IntVar), type,
56
+ an_instance_of(Gecode::Raw::IntVar), Gecode::Raw::ICL_DEF)
57
+ @x.must.send(relation, @y)
58
+ @model.solve!
59
+ end
60
+ end
61
+
62
+ Gecode::Constraints::Util::NEGATED_RELATION_TYPES.each_pair do |relation, type|
63
+ it "should translate negated #{relation} with variable to simple relation" do
64
+ Gecode::Raw.should_receive(:rel).once.with(
65
+ an_instance_of(Gecode::Raw::Space),
66
+ an_instance_of(Gecode::Raw::IntVar), type,
67
+ an_instance_of(Gecode::Raw::IntVar), Gecode::Raw::ICL_DEF)
68
+ @x.must_not.send(relation, @y)
69
+ @model.solve!
70
+ end
71
+ end
72
+
73
+ it 'should raise error on arguments of the wrong type' do
74
+ lambda{ @x.must == 'hello' }.should raise_error(TypeError)
75
+ end
76
+
77
+ it_should_behave_like 'constraint with options'
78
+ end
@@ -0,0 +1,332 @@
1
+ require File.dirname(__FILE__) + '/../spec_helper'
2
+ require File.dirname(__FILE__) + '/constraint_helper'
3
+
4
+ class LinearSampleProblem < Gecode::Model
5
+ attr :x
6
+ attr :y
7
+ attr :z
8
+
9
+ def initialize(x_dom, y_dom, z_dom)
10
+ @x = self.int_var(x_dom)
11
+ @y = self.int_var(y_dom)
12
+ @z = self.int_var(z_dom)
13
+ branch_on wrap_enum([@x, @y, @z])
14
+ end
15
+ end
16
+
17
+ class BoolLinearSampleProblem < Gecode::Model
18
+ attr :x
19
+ attr :y
20
+ attr :z
21
+
22
+ def initialize
23
+ @x = self.bool_var
24
+ @y = self.bool_var
25
+ @z = self.bool_var
26
+ branch_on wrap_enum([@x, @y, @z])
27
+ end
28
+ end
29
+
30
+ class TrueClass
31
+ def to_i
32
+ 1
33
+ end
34
+ end
35
+
36
+ class FalseClass
37
+ def to_i
38
+ 0
39
+ end
40
+ end
41
+
42
+ describe Gecode::Constraints::Int::Linear do
43
+ before do
44
+ @x_dom = 0..2
45
+ @y_dom = -3..3
46
+ @z_dom = 0..10
47
+ @model = LinearSampleProblem.new(@x_dom, @y_dom, @z_dom)
48
+ @x = @model.x
49
+ @y = @model.y
50
+ @z = @model.z
51
+
52
+ # For constraint option spec.
53
+ @invoke_options = lambda do |hash|
54
+ (@x + @y).must_be.greater_than(@z, hash)
55
+ @model.solve!
56
+ end
57
+ @expect_options = lambda do |strength, reif_var|
58
+ # TODO: this is hard to spec from this level.
59
+ end
60
+ end
61
+
62
+ it 'should handle addition with a variable' do
63
+ (@x + @y).must == 0
64
+ sol = @model.solve!
65
+ x = sol.x.value
66
+ y = sol.y.value
67
+ (x + y).should be_zero
68
+ end
69
+
70
+ it 'should handle addition with multiple variables' do
71
+ (@x + @y + @z).must == 0
72
+ sol = @model.solve!
73
+ x = sol.x.value
74
+ y = sol.y.value
75
+ z = sol.z.value
76
+ (x + y + z).should be_zero
77
+ end
78
+
79
+ it 'should handle subtraction with a variable' do
80
+ (@x - @y).must == 0
81
+ sol = @model.solve!
82
+ x = sol.x.value
83
+ y = sol.y.value
84
+ (x - y).should be_zero
85
+ end
86
+
87
+ it 'should handle non-zero constants as right hand side' do
88
+ (@x + @y).must == 1
89
+ sol = @model.solve!
90
+ x = sol.x.value
91
+ y = sol.y.value
92
+ (x + y).should equal(1)
93
+ end
94
+
95
+ it 'should handle variables as right hand side' do
96
+ (@x + @y).must == @z
97
+ sol = @model.solve!
98
+ x = sol.x.value
99
+ y = sol.y.value
100
+ z = sol.z.value
101
+ (x + y).should equal(z)
102
+ end
103
+
104
+ it 'should handle linear expressions as right hand side' do
105
+ (@x + @y).must == @z + @y
106
+ sol = @model.solve!
107
+ x = sol.x.value
108
+ y = sol.y.value
109
+ z = sol.z.value
110
+ (x + y).should equal(z + y)
111
+ end
112
+
113
+ it 'should raise error on invalid right hand sides' do
114
+ lambda{ ((@x + @y).must == 'z') }.should raise_error(TypeError)
115
+ end
116
+
117
+ it 'should handle coefficients other than 1' do
118
+ (@x * 2 + @y).must == 0
119
+ sol = @model.solve!
120
+ x = sol.x.value
121
+ y = sol.y.value
122
+ (2*x + y).should equal(0)
123
+ end
124
+
125
+ it 'should handle addition with constants' do
126
+ (@y + 2).must == 1
127
+ sol = @model.solve!
128
+ y = sol.y.value
129
+ (y + 2).should equal(1)
130
+ end
131
+
132
+ it 'should handle subtraction with a constant' do
133
+ (@x - 2).must == 0
134
+ sol = @model.solve!
135
+ x = sol.x.value
136
+ (x - 2).should be_zero
137
+ end
138
+
139
+ it 'should a single variable as left hande side' do
140
+ @x.must == @y + @z
141
+ sol = @model.solve!
142
+ x = sol.x.value
143
+ y = sol.y.value
144
+ z = sol.z.value
145
+ x.should equal(y + z)
146
+ end
147
+
148
+ it 'should handle parenthesis' do
149
+ (@x - (@y + @z)).must == 1
150
+ sol = @model.solve!
151
+ x = sol.x.value
152
+ y = sol.y.value
153
+ z = sol.z.value
154
+ (x - (y + z)).should equal(1)
155
+ end
156
+
157
+ it 'should handle multiplication of parenthesis' do
158
+ (((@x + @y*10)*10 + @z)*10).must == 0
159
+ sol = @model.solve!
160
+ x = sol.x.value
161
+ y = sol.y.value
162
+ z = sol.z.value
163
+ (((x + y*10)*10 + z)*10).should equal(0)
164
+ end
165
+
166
+ relations = ['>', '>=', '<', '<=', '==']
167
+
168
+ relations.each do |relation|
169
+ it "should handle #{relation} with constant integers" do
170
+ (@x + @y).must.send(relation, 1)
171
+ sol = @model.solve!
172
+ sol.should_not be_nil
173
+ (sol.x.value + sol.y.value).should.send(relation, 1)
174
+ end
175
+ end
176
+
177
+ relations.each do |relation|
178
+ it "should handle negated #{relation} with constant integers" do
179
+ (@x + @y).must_not.send(relation, 1)
180
+ sol = @model.solve!
181
+ sol.should_not be_nil
182
+ (sol.x.value + sol.y.value).should_not.send(relation, 1)
183
+ end
184
+ end
185
+
186
+ it 'should not interfere with other defined multiplication methods' do
187
+ (@x * :foo).should be_nil
188
+ end
189
+
190
+ it_should_behave_like 'constraint with options'
191
+ end
192
+
193
+ describe Gecode::Constraints::Int::Linear, '(with booleans)' do
194
+ before do
195
+ @model = BoolLinearSampleProblem.new
196
+ @x = @model.x
197
+ @y = @model.y
198
+ @z = @model.z
199
+
200
+ # For constraint option spec.
201
+ @invoke_options = lambda do |hash|
202
+ (@x + @y).must_be.greater_than(@z, hash)
203
+ @model.solve!
204
+ end
205
+ @expect_options = lambda do |strength, reif_var|
206
+ # TODO: this is hard to spec from this level.
207
+ end
208
+ end
209
+
210
+ it 'should handle addition with a variable' do
211
+ (@x + @y).must == 0
212
+ sol = @model.solve!
213
+ x = sol.x.value.to_i
214
+ y = sol.y.value.to_i
215
+ (x + y).should be_zero
216
+ end
217
+
218
+ it 'should handle addition with multiple variables' do
219
+ (@x + @y + @z).must == 0
220
+ sol = @model.solve!
221
+ x = sol.x.value.to_i
222
+ y = sol.y.value.to_i
223
+ z = sol.z.value.to_i
224
+ (x + y + z).should be_zero
225
+ end
226
+
227
+ it 'should handle subtraction with a variable' do
228
+ (@x - @y).must == 0
229
+ sol = @model.solve!
230
+ x = sol.x.value.to_i
231
+ y = sol.y.value.to_i
232
+ (x - y).should be_zero
233
+ end
234
+
235
+ it 'should handle non-zero constants as right hand side' do
236
+ (@x + @y).must == 1
237
+ sol = @model.solve!
238
+ x = sol.x.value.to_i
239
+ y = sol.y.value.to_i
240
+ (x + y).should equal(1)
241
+ end
242
+
243
+ it 'should handle variables as right hand side' do
244
+ (@x + @y).must == @z
245
+ sol = @model.solve!
246
+ x = sol.x.value.to_i
247
+ y = sol.y.value.to_i
248
+ z = sol.z.value.to_i
249
+ (x + y).should equal(z)
250
+ end
251
+
252
+ it 'should handle linear expressions as right hand side' do
253
+ (@x + @y).must == @z + @y
254
+ sol = @model.solve!
255
+ x = sol.x.value.to_i
256
+ y = sol.y.value.to_i
257
+ z = sol.z.value.to_i
258
+ (x + y).should equal(z + y)
259
+ end
260
+
261
+ it 'should raise error on invalid right hand sides' do
262
+ lambda{ ((@x + @y).must == 'z') }.should raise_error(TypeError)
263
+ end
264
+
265
+ it 'should handle coefficients other than 1' do
266
+ (@x * 2 + @y).must == 0
267
+ sol = @model.solve!
268
+ x = sol.x.value.to_i
269
+ y = sol.y.value.to_i
270
+ (2*x + y).should equal(0)
271
+ end
272
+
273
+ it 'should handle addition with constants' do
274
+ (@y + 1).must == 1
275
+ sol = @model.solve!
276
+ y = sol.y.value.to_i
277
+ (y + 1).should equal(1)
278
+ end
279
+
280
+ it 'should handle subtraction with a constant' do
281
+ (@x - 1).must == 0
282
+ sol = @model.solve!
283
+ x = sol.x.value.to_i
284
+ (x - 1).should be_zero
285
+ end
286
+
287
+ it 'should handle parenthesis' do
288
+ (@x - (@y + @z)).must == 1
289
+ sol = @model.solve!
290
+ x = sol.x.value.to_i
291
+ y = sol.y.value.to_i
292
+ z = sol.z.value.to_i
293
+ (x - (y + z)).should equal(1)
294
+ end
295
+
296
+ it 'should handle multiplication of parenthesis' do
297
+ (((@x + @y*10)*10 + @z)*10).must == 0
298
+ sol = @model.solve!
299
+ x = sol.x.value.to_i
300
+ y = sol.y.value.to_i
301
+ z = sol.z.value.to_i
302
+ (((x + y*10)*10 + z)*10).should equal(0)
303
+ end
304
+
305
+ relations = ['>', '>=', '<', '<=', '==']
306
+
307
+ relations.each do |relation|
308
+ it "should handle #{relation} with constant integers" do
309
+ (@x + @y).must.send(relation, 1)
310
+ sol = @model.solve!
311
+ sol.should_not be_nil
312
+ (sol.x.value.to_i + sol.y.value.to_i).should.send(relation, 1)
313
+ end
314
+ end
315
+
316
+ relations.each do |relation|
317
+ it "should handle negated #{relation} with constant integers" do
318
+ (@x + @y).must_not.send(relation, 1)
319
+ sol = @model.solve!
320
+ sol.should_not be_nil
321
+ (sol.x.value.to_i + sol.y.value.to_i).should_not.send(relation, 1)
322
+ end
323
+ end
324
+
325
+ it 'should not interfere with other defined multiplication methods' do
326
+ (@x * :foo).should be_nil
327
+ end
328
+
329
+ it_should_behave_like 'constraint with options'
330
+ end
331
+
332
+