keso 0.1.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,163 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
2
+
3
+
4
+ describe ImmutableSet do
5
+ describe :new do
6
+ it 'returns a new instance of ImmutableSet with the supplied values' do
7
+ ImmutableSet.new(:a).should be_instance_of ImmutableSet
8
+ ImmutableSet.new(:a).count.should eql(1)
9
+
10
+ ImmutableSet.new([:a,:b,:c,:a]).count.should eql(3)
11
+ ImmutableSet.new(ImmutableSet.new([:a,:b,:c,:a])).count.should eql(3)
12
+
13
+ ImmutableSet.new([:a,:b,:c,:a],[:z],[:y],:o).count.should eql(6)
14
+ ImmutableSet.new([:a,:b,:c,:a],[:z],[:y],ImmutableSet.new([:o])).count.should eql(6)
15
+ end
16
+ end
17
+
18
+ describe :each do
19
+ it 'iterates over each value' do
20
+ ImmutableSet.new([:a,:b,:c]).each do |value|
21
+ [:a,:b,:c].should include value
22
+ end
23
+ end
24
+ end
25
+
26
+ describe :count do
27
+ it 'returns the amount of items in the set' do
28
+ ImmutableSet.new([:a,:b,:c]).count.should eql(3)
29
+ end
30
+ end
31
+
32
+ describe :size do
33
+ it 'returns the amount of items in the set' do
34
+ ImmutableSet.new([:a,:b,:c]).size.should eql(3)
35
+ end
36
+ end
37
+
38
+ describe :include? do
39
+ it 'should be true when it contains the value' do
40
+ ImmutableSet.new([:a,:b,:c]).include?(:a).should be_true
41
+ ImmutableSet.new([:a,:b,:c]).include?(:z).should be_false
42
+ end
43
+ end
44
+
45
+ describe :eql? do
46
+ it 'returns true if the two sets are equal' do
47
+ ImmutableSet.new([:a,:b,:c]).eql?(ImmutableSet.new([:a,:b,:c])).should be_true
48
+ ImmutableSet.new([:a,:b]).eql?(ImmutableSet.new([:a,:b,:c])).should be_false
49
+ end
50
+ end
51
+
52
+ describe :hash do
53
+ it 'always returns the same value for two sets that are equal' do
54
+ ImmutableSet.new([:a,:b,:c]).hash.should eql(ImmutableSet.new([:a,:b,:c]).hash)
55
+ end
56
+ end
57
+
58
+ describe :add do
59
+ it 'should result in a new set with the supplied value' do
60
+ ImmutableSet.new(:a).add(:b).add(:a).count.should eql(2)
61
+ ImmutableSet.new(:a).add([:b,:a,:c]).add(:a).count.should eql(3)
62
+ ImmutableSet.new(:a).add(ImmutableSet.new([:d])).add(:a).count.should eql(2)
63
+
64
+ ImmutableSet.new(:a).add(:b,:f).add(:a).count.should eql(3)
65
+ ImmutableSet.new(:a).add([:b,:a,:c]).add(:a,:ue).count.should eql(4)
66
+ ImmutableSet.new(:a).add(ImmutableSet.new([:d]),:htuneo).add(:a).count.should eql(3)
67
+ end
68
+ end
69
+
70
+ describe :union do
71
+ it 'should result in a new set with the supplied value' do
72
+ ImmutableSet.new(:a).union(:b).union(:a).count.should eql(2)
73
+ ImmutableSet.new(:a).union([:b,:a,:c]).union(:a).count.should eql(3)
74
+ ImmutableSet.new(:a).union(ImmutableSet.new([:d])).union(:a).count.should eql(2)
75
+
76
+ ImmutableSet.new(:a).union(:b,:f).union(:a).count.should eql(3)
77
+ ImmutableSet.new(:a).union([:b,:a,:c]).union(:a,:ue).count.should eql(4)
78
+ ImmutableSet.new(:a).union(ImmutableSet.new([:d]),:htuneo).union(:a).count.should eql(3)
79
+ end
80
+ end
81
+
82
+ describe :delete do
83
+ it 'should delete a value from the set' do
84
+ ImmutableSet.new(:a).add(:b).delete(:a).count.should eql(1)
85
+ ImmutableSet.new([:a,:b,:c,:e]).delete(ImmutableSet.new([:a,:b])).count.should eql(2)
86
+ ImmutableSet.new([:a,:b,:c,:e]).delete([:a,:b]).count.should eql(2)
87
+
88
+ ImmutableSet.new(:a).add(:b).delete(:a,:b).count.should eql(0)
89
+ ImmutableSet.new([:a,:b,:c,:e]).delete(ImmutableSet.new([:a,:b]),:c).count.should eql(1)
90
+ ImmutableSet.new([:a,:b,:c,:e]).delete([:a,:b],:e).count.should eql(1)
91
+ end
92
+ end
93
+
94
+ describe :subset? do
95
+ it 'should return true when all values in the supplied set is also in the current set' do
96
+
97
+ ImmutableSet.new([:a,:b]).subset?(ImmutableSet.new([:a,:b,:c])).should be_true
98
+ ImmutableSet.new([:b,:c]).subset?(ImmutableSet.new([:a,:b,:c])).should be_true
99
+ ImmutableSet.new([:a,:b,:c]).subset?(ImmutableSet.new([:a,:b,:c])).should be_true
100
+ ImmutableSet.new([:a,:b,:c]).subset?(ImmutableSet.new([:b,:c,:gi])).should be_false
101
+
102
+ end
103
+ end
104
+
105
+ describe :proper_subset? do
106
+ it 'should return true when all values in the supplied set is also in the current set' do
107
+
108
+ ImmutableSet.new([:a,:b]).proper_subset?(ImmutableSet.new([:a,:b,:c])).should be_true
109
+ ImmutableSet.new([:b,:c]).proper_subset?(ImmutableSet.new([:a,:b,:c])).should be_true
110
+ ImmutableSet.new([:a,:b,:c]).proper_subset?(ImmutableSet.new([:a,:b,:c])).should be_false
111
+ ImmutableSet.new([:a,:b,:c]).proper_subset?(ImmutableSet.new([:b,:c,:gi])).should be_false
112
+
113
+ end
114
+ end
115
+
116
+ describe :proper_subset_of? do
117
+ it 'should return true when all values in the supplied set is also in the current set but they are not equal' do
118
+
119
+ ImmutableSet.new([:a,:b]).proper_subset_of?(ImmutableSet.new([:a,:b,:c])).should be_true
120
+ ImmutableSet.new([:b,:c]).proper_subset_of?(ImmutableSet.new([:a,:b,:c])).should be_true
121
+ ImmutableSet.new([:a,:b,:c]).proper_subset_of?(ImmutableSet.new([:a,:b,:c])).should be_false
122
+ ImmutableSet.new([:a,:b,:c]).proper_subset_of?(ImmutableSet.new([:b,:c,:gi])).should be_false
123
+
124
+ end
125
+ end
126
+
127
+ describe :superset? do
128
+ it 'should return true when all values in the supplied set is also in the current set but they are not equal' do
129
+
130
+ ImmutableSet.new([:a,:b,:c]).superset?(ImmutableSet.new([:a,:b])).should be_true
131
+ ImmutableSet.new([:a,:b,:c]).superset?(ImmutableSet.new([:b,:c])).should be_true
132
+ ImmutableSet.new([:a,:b,:c]).superset?(ImmutableSet.new([:a,:b,:c])).should be_true
133
+ ImmutableSet.new([:a,:b,:c]).superset?(ImmutableSet.new([:gi])).should be_false
134
+
135
+ end
136
+ end
137
+
138
+ describe :proper_superset? do
139
+ it 'should return true when all values in the supplied set is also in the current set' do
140
+
141
+ ImmutableSet.new([:a,:b,:c]).proper_superset?(ImmutableSet.new([:a,:b])).should be_true
142
+ ImmutableSet.new([:a,:b,:c]).proper_superset?(ImmutableSet.new([:b,:c])).should be_true
143
+ ImmutableSet.new([:a,:b,:c]).proper_superset?(ImmutableSet.new([:a,:b,:c])).should be_false
144
+ ImmutableSet.new([:a,:b,:c]).proper_superset?(ImmutableSet.new([:gi])).should be_false
145
+
146
+ end
147
+ end
148
+
149
+ describe :complement do
150
+ it 'should return a new set with set1 minues the values of set2' do
151
+ ImmutableSet.new([:a,:b,:c]).complement(ImmutableSet.new([:a,:b])).should eql(ImmutableSet.new([:c]))
152
+ ImmutableSet.new([:a,:b,:c]).complement(ImmutableSet.new([:a])).should eql(ImmutableSet.new([:c,:b]))
153
+ end
154
+ end
155
+
156
+ describe :intersect do
157
+ it 'should return a new set with the values that are fonud in both set1 and set2' do
158
+ ImmutableSet.new([:a,:b,:c]).intersect(ImmutableSet.new([:a,:b])).should eql(ImmutableSet.new([:a,:b]))
159
+ ImmutableSet.new([:a,:b,:c]).intersect(ImmutableSet.new([:a])).should eql(ImmutableSet.new([:a]))
160
+ end
161
+ end
162
+ end
163
+
@@ -0,0 +1,358 @@
1
+
2
+ require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
3
+
4
+ describe Relation do
5
+
6
+ describe :count do
7
+ it 'returns the tupel count in the set' do
8
+ Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).count.should eql 1
9
+ end
10
+ end
11
+
12
+ describe :add do
13
+ it 'returns a new relation with the added tuple' do
14
+ Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30})).count.should eql 2
15
+ end
16
+
17
+ it 'throws an exception as the supplied value is not a tuple' do
18
+ lambda { Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add("") }.should raise_error(ArgumentError)
19
+ end
20
+
21
+ it 'throws an exception as the supplied tuple is not of the same heading as the relation' do
22
+ lambda { Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:something => 'Emma',:age => 30})) }.should raise_error(ArgumentError)
23
+ end
24
+
25
+ it 'throws an exception as the relational value is of the wrong heading' do
26
+
27
+ person = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30}))
28
+ person_with_length = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29,:length => 155})).add(Tuple.new({:name => 'Emma',:age => 30, :length => 135}))
29
+
30
+ company = Relation.new(Tuple.new({:name => 'Test AB',:employes => person}))
31
+
32
+ lambda { company = company.add(Tuple.new({:name => 'Nordea AB',:employes => person})) }.should_not raise_error(ArgumentError)
33
+ lambda { company = company.add(Tuple.new({:name => 'SEB AB',:employes => person_with_length})) }.should raise_error(ArgumentError)
34
+
35
+
36
+ end
37
+
38
+ end
39
+
40
+ describe :subset_of? do
41
+ it 'returns return true when the supplied value is a subset' do
42
+ a = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30}))
43
+ Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).subset_of?(a).should be_true
44
+ Relation.new(Tuple.new({:name => 'Bjorn',:age => 30})).subset_of?(a).should be_false
45
+ end
46
+ end
47
+
48
+ # r1.proper_subset(r2) # boolean result
49
+ describe :proper_subset_of? do
50
+ it 'should return true when all values are also in the supplied set and they are not equal' do
51
+ a = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30}))
52
+ Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).proper_subset_of?(a).should be_true
53
+ a.proper_subset_of?(a).should be_false
54
+ end
55
+ end
56
+
57
+ # r1.superset(r2) # boolean result
58
+ describe :superset_of? do
59
+ it 'should return true when all the tuples of the supplied set can be found in this set' do
60
+ a = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30}))
61
+ a.superset_of?(Relation.new(Tuple.new({:name => 'Bjorn',:age => 29}))).should be_true
62
+ a.superset_of?(Relation.new(Tuple.new({:name => 'Bjor'}))).should be_false
63
+ a.superset_of?(a).should be_true
64
+ end
65
+ end
66
+
67
+ # r1.proper_superset(r2) # boolean result
68
+ describe :proper_superset_of? do
69
+ it 'should return true when all the tuples of the supplied set is also in this set but they are not equal' do
70
+ a = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30}))
71
+
72
+ a.proper_superset_of?(Relation.new(Tuple.new({:name => 'Bjorn',:age => 29}))).should be_true
73
+ a.proper_superset_of?(Relation.new(Tuple.new({:name => 'Bjor'}))).should be_false
74
+ a.proper_superset_of?(a).should be_false
75
+ end
76
+ end
77
+
78
+ # r1.union(r2) # r1 + r2, set result
79
+ describe :union do
80
+ it 'returns a new relation with the tuples of both' do
81
+ a = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30}))
82
+ b = Relation.new(Tuple.new({:name => 'Frida',:age => 25})).add(Tuple.new({:name => 'Marianna',:age => 32}))
83
+
84
+ c = Relation.new(Tuple.new({:name => 'Frida',:age => 25})).add(Tuple.new({:name => 'Marianna',:age => 32})).add(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30}))
85
+
86
+ a.union(b).should eql(c)
87
+ end
88
+ end
89
+
90
+ describe :eql? do
91
+ it 'returns true when two relations have the same value' do
92
+ a = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30}))
93
+ b = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30}))
94
+ a.should eql b
95
+
96
+
97
+ r1 = Relation.new(Tuple.new({:name => 'Bjorn', :person_ids => Relation.new(Tuple.new({:person_id => 12})).add(Tuple.new({:person_id => 119}))}))
98
+ r2 = Relation.new(Tuple.new({:name => 'Bjorn', :person_ids => Relation.new(Tuple.new({:person_id => 12})).add(Tuple.new({:person_id => 119}))}))
99
+ r1.should eql(r2)
100
+ end
101
+ end
102
+
103
+ describe :== do
104
+ it 'returns true when two relations have the same value' do
105
+ a = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30}))
106
+ b = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30}))
107
+ (a == b).should be_true
108
+ end
109
+ end
110
+
111
+ describe :hash do
112
+ it 'should return the same hash for the same value' do
113
+ a = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30}))
114
+ b = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30}))
115
+ a.hash.should eql b.hash
116
+ end
117
+ end
118
+
119
+ # r1.intersect(r2) # all in r1 that is also in r2, set result
120
+ describe :intersect do
121
+ it 'should return a new relation all the tuples that are found in both' do
122
+ a = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30}))
123
+ b = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Frida',:age => 25}))
124
+
125
+ a.intersect(b).should eql(Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})))
126
+ end
127
+
128
+ it 'should throw an exception as the realtions are not of the same headings' do
129
+ a = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29}))
130
+ b = Relation.new(Tuple.new({:name => 'Bjorn'}))
131
+
132
+ lambda { a.intersect(b) }.should raise_error(ArgumentError)
133
+ end
134
+ end
135
+
136
+ # r1.complement(r2) # r1 - r2, set result
137
+ describe :complement do
138
+ it 'should return a new relation that has all the tuples that where not in r2' do
139
+ a = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30}))
140
+ b = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Frida',:age => 25}))
141
+
142
+ a.complement(b).should eql(Relation.new(Tuple.new({:name => 'Emma',:age => 30})))
143
+ end
144
+
145
+ it 'should throw an exception with the text ""Not of the same heading""' do
146
+ a = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29}))
147
+ b = Relation.new(Tuple.new({:name => 'Bjorn'}))
148
+
149
+ lambda { a.complement(b) }.should raise_error(ArgumentError)
150
+ end
151
+ end
152
+
153
+ # r1.project_all_but('Name','age') # results in a relation with all attributes exepct the supplied ones, set result
154
+ describe :project_all_but do
155
+ it 'should return a new relation with all but the supplied columns' do
156
+ Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30})).project_all_but(:name).should eql(Relation.new(Tuple.new({:age => 30})).add(Tuple.new({:age => 29})))
157
+ Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30})).project_all_but(:name,:age).should eql(Relation.new())
158
+ end
159
+ end
160
+
161
+
162
+ # r1.project('Name','age') # results in a relation of only the supplied attributes, set result
163
+ describe :project do
164
+ it 'should return with a new relation with only the attributes named in the argument' do
165
+ Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30})).project(:name).should eql(Relation.new(Tuple.new({:name => 'Bjorn'})).add(Tuple.new({:name => 'Emma'})))
166
+ Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30})).project(:name,:age).should eql(Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30})))
167
+ end
168
+
169
+ it 'should throw an exception as the attribue name is not in the relation' do
170
+ lambda { Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30})).project(:names) }.should raise_error(ArgumentError)
171
+ end
172
+ end
173
+
174
+ # r1.rename('Name','PersonName') # changes the attribute name from "Name" to "PersonName", set result
175
+ describe :rename do
176
+ it 'should change the name of a tuple' do
177
+ Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30})).rename(:name,:new_name).should eql(Relation.new(Tuple.new({:new_name => 'Bjorn',:age => 29})).add(Tuple.new({:new_name => 'Emma',:age => 30})))
178
+ end
179
+
180
+ it 'should throw an exception ' do
181
+ lambda { Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30})).rename(:old_name,:new_name) }.should raise_error(ArgumentError)
182
+ lambda { Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30})).rename(:name,:age) }.should raise_error(ArgumentError)
183
+ end
184
+ end
185
+
186
+
187
+ describe :new do
188
+
189
+ it 'should accept a relation as a type' do
190
+
191
+ persons = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30}))
192
+
193
+ Relation.new(Tuple.new({:name => 'Test AB',:employes => persons})).each do |tuple|
194
+ tuple.employes.should eql(Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30})))
195
+ end
196
+ end
197
+
198
+ end
199
+
200
+ describe :each do
201
+ it 'iterates over all the tuples and executes the given block' do
202
+
203
+ names = {}
204
+
205
+ Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30})).each do |tuple|
206
+ names[tuple[:name]] = tuple[:name]
207
+ end
208
+
209
+ names['Bjorn'].should_not be_nil
210
+ names['Emma'].should_not be_nil
211
+
212
+ end
213
+ end
214
+
215
+ # r1.select do |r| r.age = 18 end
216
+ describe :select do
217
+ it 'should return only the tuples with age 29' do
218
+ result = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30})).select do |tuple|
219
+ tuple.age == 29
220
+ end
221
+
222
+ result.should eql(Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})))
223
+ end
224
+
225
+ it 'should return only the tuples with age greater than 18' do
226
+ result = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30})).select do |tuple|
227
+ tuple.age > 18
228
+ end
229
+
230
+ result.should eql(Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30})))
231
+ end
232
+ end
233
+
234
+ # r1.join(r2) do |tupel| ... end
235
+ describe :join do
236
+ it 'returns a new relation that is the result of join r1 with r2' do
237
+ r1 = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30}))
238
+ r2 = Relation.new(Tuple.new({:name => 'Bjorn',:length => 185})).add(Tuple.new({:name => 'Emma',:length => 115})).rename(:name,:name2)
239
+
240
+ result = r1.join(r2) do |tupel|
241
+ tupel.name == tupel.name2
242
+ end
243
+
244
+ r3 = Relation.new(Tuple.new({:name => 'Bjorn',:name2 => 'Bjorn',:length => 185,:age => 29})).add(Tuple.new({:name => 'Emma',:name2 => 'Emma',:length => 115, :age => 30}))
245
+
246
+ result.count.should eql(r3.count)
247
+ result.heading.should eql(r3.heading)
248
+ result.should eql(r3)
249
+
250
+ end
251
+
252
+ it 'returns a new relation that is the result of join r1 with r2' do
253
+ r1 = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30}))
254
+ r2 = Relation.new(Tuple.new({:name => 'Bjorn',:length => 185})).add(Tuple.new({:name => 'Emma',:length => 115})).rename(:name,:name2)
255
+
256
+ result = r1.join(r2) do |tupel|
257
+ tupel.name != tupel.name2
258
+ end
259
+
260
+ r3 = Relation.new(Tuple.new({:name => 'Bjorn',:name2 => 'Emma',:length => 115,:age => 29})).add(Tuple.new({:name => 'Emma',:name2 => 'Bjorn',:length => 185, :age => 30}))
261
+
262
+ result.count.should eql(r3.count)
263
+ result.heading.should eql(r3.heading)
264
+ result.should eql(r3)
265
+
266
+ end
267
+ end
268
+
269
+
270
+ # r1.cartesian_product(r2) # new relation with r1 * r2 tuples with all attributes of r1 and r2, set result
271
+ describe :cartesian_product do
272
+ it 'should return a new relation' do
273
+ r1 = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30}))
274
+ r2 = Relation.new(Tuple.new({:name => 'Bjorn',:length => 185})).add(Tuple.new({:name => 'Emma',:length => 115})).rename(:name,:name2)
275
+
276
+ result = r1.cartesian_product(r2)
277
+
278
+ r3 = Relation.new(Tuple.new({:name => 'Bjorn',:name2 => 'Emma',:length => 115,:age => 29})).add(Tuple.new({:name => 'Emma',:name2 => 'Bjorn',:length => 185, :age => 30})).add(Tuple.new({:name => 'Bjorn',:name2 => 'Bjorn',:length => 185,:age => 29})).add(Tuple.new({:name => 'Emma',:name2 => 'Emma',:length => 115, :age => 30}))
279
+
280
+ result.count.should eql(r3.count)
281
+ result.heading.should eql(r3.heading)
282
+ result.should eql(r3)
283
+
284
+ end
285
+ end
286
+
287
+ # r1.natrual_join(r2) # cartesian_product with a selection based on equal attributes having to have equal value, set result
288
+ describe :natrual_join do
289
+ it 'returns a new relation that is the result of join r1 with r2' do
290
+ r1 = Relation.new(Tuple.new({:name => 'Bjorn',:age => 29})).add(Tuple.new({:name => 'Emma',:age => 30}))
291
+ r2 = Relation.new(Tuple.new({:name => 'Bjorn',:length => 185})).add(Tuple.new({:name => 'Emma',:length => 115}))
292
+
293
+ result = r1.natrual_join(r2)
294
+
295
+ r3 = Relation.new(Tuple.new({:name => 'Bjorn',:length => 185,:age => 29})).add(Tuple.new({:name => 'Emma',:length => 115, :age => 30}))
296
+
297
+ result.count.should eql(r3.count)
298
+ result.heading.should eql(r3.heading)
299
+ result.should eql(r3)
300
+
301
+ end
302
+ end
303
+
304
+
305
+ # r1.group
306
+ # r1.project('Name','Age').group(['Age'],'Names') # results in a new relation as r{'Age' => integer, 'Names' => r{'Name' => String}}
307
+ describe :group do
308
+ it 'should return a new relatino with a relational value for the columns that was not supplied with the supplied name' do
309
+
310
+ r1 = Relation.new(Tuple.new({:name => 'Bjorn', :person_id => 12})).add(Tuple.new({:name => 'Bjorn', :person_id => 119}))
311
+ r2 = Relation.new(Tuple.new({:name => 'Bjorn', :person_ids => Relation.new(Tuple.new({:person_id => 12})).add(Tuple.new({:person_id => 119}))}))
312
+
313
+ r1.group([:name],:person_ids).should eql(r2)
314
+
315
+ end
316
+ end
317
+
318
+
319
+ # r1.ungroup
320
+ # r1.project('Name','Age').group(['Age'],'Names').ungroup('Names'[,{'Name' => 'New_name'}]) # results in a new relation as r{'Age' => integer, 'Name' => String}
321
+ describe :ungroup do
322
+ it 'should return a new relation with the person_ids relational value expended into its container relation' do
323
+
324
+ r1 = Relation.new(Tuple.new({:name => 'Bjorn', :person_id => 12})).add(Tuple.new({:name => 'Bjorn', :person_id => 119}))
325
+ r2 = Relation.new(Tuple.new({:name => 'Bjorn', :person_ids => Relation.new(Tuple.new({:person_id => 12})).add(Tuple.new({:person_id => 119}))}))
326
+
327
+ r2.ungroup(:person_ids).should eql(r1)
328
+
329
+
330
+ end
331
+ end
332
+
333
+ # r1.summarize(:name) do |tuples,new_tuple|
334
+ # new_tuple.add('avrange_age',avg(tuples,'age'))
335
+ # new_tuple.add('max_age',max(tuples,'age'))
336
+ # new_tuple.add('min_age',min(tuples,'age'))
337
+ # new_tuple.add('median_age',median(tuples,'age'))
338
+ # end
339
+ describe :summarize do
340
+ it 'returns a new relation with new columns' do
341
+
342
+ r1 = Relation.new(Tuple.new({:name => 'Bjorn', :person_id => 12})).add(Tuple.new({:name => 'Bjorn', :person_id => 119})).add(Tuple.new({:name => 'Marianna', :person_id => 9}))
343
+ r2 = Relation.new(Tuple.new({:name => 'Bjorn', :count => 2})).add(Tuple.new({:name => 'Marianna', :count => 1}))
344
+
345
+ r3 = r1.summarize(:name) do |tuple,relation|
346
+ tuple.add(:count => relation.count)
347
+ end
348
+
349
+ r3.should eql(r2)
350
+
351
+ end
352
+ end
353
+
354
+
355
+
356
+ end
357
+
358
+