Permalink
Browse files

If the pair coverage is the same for the candiates pick the ones that…

… are most different to those already generated.
  • Loading branch information...
1 parent 29bb212 commit 960ffb7018d4e68926456d9268fe0951d93edd07 @josephwilk committed Aug 22, 2012
@@ -13,16 +13,15 @@ Feature: Customizing pairwise output format
When I run pairwise inputs.yml --format csv
Then I should see the output
"""
- event with image,event without image,media
- Football,Football,Image
- Football,Basketball,Video
- Football,Soccer,Music
- Basketball,Football,Video
- Basketball,Basketball,Image
- Basketball,Soccer,Image
- Soccer,Football,Music
- Soccer,Basketball,Image
- Soccer,Soccer,Video
- Basketball,Basketball,Music
+ event with image,event without image,media
+ Football,Football,Image
+ Football,Basketball,Music
+ Football,Soccer,Video
+ Basketball,Football,Music
+ Basketball,Basketball,Video
+ Basketball,Soccer,Image
+ Soccer,Football,Video
+ Soccer,Basketball,Image
+ Soccer,Soccer,Music
"""
@@ -20,17 +20,16 @@ Feature: Generating pairwise data
When I run pairwise inputs.yml
Then I should see the output
"""
- | event with image | event without image | media |
- | Football | Football | Image |
- | Football | Basketball | Video |
- | Football | Soccer | Music |
- | Basketball | Football | Video |
- | Basketball | Basketball | Image |
- | Basketball | Soccer | Image |
- | Soccer | Football | Music |
- | Soccer | Basketball | Image |
- | Soccer | Soccer | Video |
- | Basketball | Basketball | Music |
+ | event with image | event without image | media |
+ | Football | Football | Image |
+ | Football | Basketball | Music |
+ | Football | Soccer | Video |
+ | Basketball | Football | Music |
+ | Basketball | Basketball | Video |
+ | Basketball | Soccer | Image |
+ | Soccer | Football | Video |
+ | Soccer | Basketball | Image |
+ | Soccer | Soccer | Music |
"""
@@ -44,17 +43,16 @@ Feature: Generating pairwise data
When I run pairwise inputs.yml
Then I should see the output
"""
- | event with image | event without image | media |
- | Football | Football | Image |
- | Football | Basketball | Video |
- | Football | Soccer | Music |
- | Basketball | Football | Video |
- | Basketball | Basketball | Image |
- | Basketball | Soccer | Image |
- | Soccer | Football | Music |
- | Soccer | Basketball | Image |
- | Soccer | Soccer | Video |
- | Basketball | Basketball | Music |
+ | event with image | event without image | media |
+ | Football | Football | Image |
+ | Football | Basketball | Music |
+ | Football | Soccer | Video |
+ | Basketball | Football | Music |
+ | Basketball | Basketball | Video |
+ | Basketball | Soccer | Image |
+ | Soccer | Football | Video |
+ | Soccer | Basketball | Image |
+ | Soccer | Soccer | Music |
"""
@@ -83,17 +81,16 @@ Feature: Generating pairwise data
When I run pairwise inputs.csv
Then I should see the output
"""
- | event with image | event without image | media |
- | Football | Football | Image |
- | Football | Basketball | Video |
- | Football | Soccer | Music |
- | Basketball | Football | Video |
- | Basketball | Basketball | Image |
- | Basketball | Soccer | Image |
- | Soccer | Football | Music |
- | Soccer | Basketball | Image |
- | Soccer | Soccer | Video |
- | Basketball | Basketball | Music |
+ | event with image | event without image | media |
+ | Football | Football | Image |
+ | Football | Basketball | Music |
+ | Football | Soccer | Video |
+ | Basketball | Football | Music |
+ | Basketball | Basketball | Video |
+ | Basketball | Soccer | Image |
+ | Soccer | Football | Video |
+ | Soccer | Basketball | Image |
+ | Soccer | Soccer | Music |
"""
@@ -109,13 +106,13 @@ Feature: Generating pairwise data
"""
| A | B | C |
| A1 | B1 | C1 |
- | A1 | B2 | C2 |
+ | A1 | B2 | C3 |
| A2 | B1 | C3 |
- | A2 | B2 | C1 |
+ | A2 | B2 | C2 |
| A3 | B1 | C2 |
- | A3 | B2 | C3 |
- | A3 | any_value_of_B | C1 |
- | A2 | any_value_of_B | C2 |
- | A1 | any_value_of_B | C3 |
+ | A3 | B2 | C1 |
+ | A2 | any_value_of_B | C1 |
+ | A1 | any_value_of_B | C2 |
+ | A3 | any_value_of_B | C3 |
"""
@@ -7,7 +7,6 @@ class << self
def growth(input_combinations, input_values_for_growth, previously_grown_input_values)
uncovered_pairs = PairCollection.new(input_values_for_growth, previously_grown_input_values, previously_grown_input_values.size)
input_combinations, uncovered_pairs = grow_input_combinations_and_remove_covered_pairs(input_combinations, input_values_for_growth, uncovered_pairs)
-
[input_combinations, uncovered_pairs]
end
@@ -3,6 +3,7 @@ class PairCollection < Array
def initialize(input_parameter_values, input_value_lists, input_parameter_index)
pairs = generate_pairs_between(input_parameter_values, input_value_lists, input_parameter_index)
+ @combination_history = []
super(pairs)
end
@@ -12,9 +13,19 @@ def remove_pairs_covered_by!(extended_input_list)
def input_combination_that_covers_most_pairs(input_combination, input_values_for_growth)
candidates = input_values_for_growth.map{|value| input_combination + [value]}
- candidates.max {|combination_1, combination_2| pairs_covered_count(combination_1) <=> pairs_covered_count(combination_2)}
- end
+ max_combination = candidates.max {|combination_1, combination_2| pairs_covered_count(combination_1) <=> pairs_covered_count(combination_2)}
+ possible_max_combinations = candidates.select{|combination| pairs_covered_count(max_combination) == pairs_covered_count(combination)}
+ winner = if possible_max_combinations.size > 1 && !@combination_history.empty?
+ #Looking back across the picked values find the combination with the greatest difference
+ max_difference(possible_max_combinations, @combination_history)
+ else
+ possible_max_combinations[0]
+ end
+ @combination_history << winner
+ winner
+ end
+
def to_a
self.map{|list| list.to_a}
end
@@ -39,5 +50,27 @@ def pairs_covered_count(input_combination)
covered_count
end
end
+
+ def max_difference(options, previous_choices)
+ scores = options.map do |option|
+ score(option, previous_choices)
+ end.flatten
+
+ _, winner_index = *scores.each_with_index.max
+ options[winner_index]
+ end
+
+ def score(option, previous_choices)
+ #O(n^2)
+ previous_choices.map do |choice|
+ i = 0
+ option.each_with_index.reduce(0) do |sum, value|
+ value != choice[i] ? sum : sum = sum+=1
+ i+=1
+ sum
+ end
+ end.max
+ end
+
end
end
@@ -13,6 +13,7 @@ def initialize(p1_position, p2_position, p1, p2)
end
def covered_by?(test_pair)
+ debugger unless test_pair
test_pair[@p1_position] == @p1 &&
test_pair[@p2_position] == @p2
end
@@ -12,7 +12,7 @@ module IPO
test_set, _ = Horizontal.growth(input_combinations, data[1], data[0..1])
- test_set.should == [[:A1, :B1, :C1], [:A1, :B2, :C2]]
+ test_set.should == [[:A1, :B1, :C1], [:A1, :B2, :C3]]
end
end
@@ -25,19 +25,13 @@ module IPO
it "should return pairs extended with C's inputs" do
test_set, _ = Horizontal.growth(@test_pairs, @data[2], @data[0..1])
- test_set.should == [[:A1, :B1, :C1],
- [:A1, :B2, :C2],
- [:A2, :B1, :C3],
- [:A2, :B2, :C1]]
+ test_set.should == [[:A1, :B1, :C1], [:A1, :B2, :C3], [:A2, :B1, :C3], [:A2, :B2, :C2]]
end
it "should return all the uncovered pairs" do
_, pi = Horizontal.growth(@test_pairs, @data[2], @data[0..1])
- # We are getting the uncovered pairs in reverse
- #pi.should == [[:A2, :C2],[:A1, :C3],[:B1, :C2],[:B2, :C3]]
- # Cheat and check we get the list in reverse
- pi.to_a.should == [[:C2, :A2], [:C2, :B1], [:C3, :A1], [:C3, :B2]]
+ pi.to_a.should == [[:C1, :A2], [:C1, :B2], [:C2, :A1], [:C2, :B1]]
end
end
View
@@ -70,12 +70,7 @@
it "should generate all pairs for 3 parameters of 1,2,3 values" do
data = [[:A1], [:B1, :B2], [:C1, :C2, :C3]]
- Pairwise.combinations(*data).should == [[:A1, :B1, :C1],
- [:A1, :B2, :C2],
- [:A1, :B2, :C1],
- [:A1, :B1, :C2],
- [:A1, :B1, :C3],
- [:A1, :B2, :C3]]
+ Pairwise.combinations(*data).should == [[:A1, :B1, :C1], [:A1, :B2, :C3], [:A1, :B2, :C1], [:A1, :B1, :C2], [:A1, :B2, :C2], [:A1, :B1, :C3]]
end
it "should generate all pairs for 3 parameters of 2,1,2 values" do
@@ -96,39 +91,30 @@
it "should generate all pairs for 4 parameters of 2,1,2,2 values" do
data = [[:A1, :A2], [:B1], [:C1, :C2], [:D1, :D2]]
- Pairwise.combinations(*data).should == [[:A1, :B1, :C1, :D1],
- [:A2, :B1, :C2, :D2],
- [:A2, :B1, :C1, :D1],
- [:A1, :B1, :C2, :D1],
- [:A1, :B1, :C1, :D2]]
+ Pairwise.combinations(*data).should == [[:A1, :B1, :C1, :D1], [:A2, :B1, :C2, :D2], [:A2, :B1, :C1, :D2], [:A1, :B1, :C2, :D2], [:A2, :B1, :C2, :D1]]
end
it "should generate pairs for three parameters" do
data = [[:A1, :A2],
[:B1, :B2],
[:C1 , :C2 , :C3 ]]
- Pairwise.combinations(*data).should == [[:A1, :B1, :C1],
- [:A1, :B2, :C2],
- [:A2, :B1, :C2],
- [:A2, :B2, :C1],
- [:A1, :B2, :C3],
- [:A2, :B1, :C3]]
+ Pairwise.combinations(*data).should == [[:A1, :B1, :C1], [:A1, :B2, :C3], [:A2, :B1, :C3], [:A2, :B2, :C2], [:A2, :B2, :C1], [:A1, :B1, :C2]]
end
describe "replacing wildcards which could have more than one option" do
it "should generate pairs for 2 parameters of 3,2,3 values" do
Pairwise.combinations([:A1, :A2, :A3],
[:B1, :B2],
- [:C1, :C2, :C3]).should == [[:A1, :B1, :C1],
- [:A1, :B2, :C2],
- [:A2, :B1, :C3],
- [:A2, :B2, :C1],
- [:A3, :B1, :C2],
- [:A3, :B2, :C3],
- [:A3, :B1, :C1], #B1 is a wildcard replacement
- [:A2, :B1, :C2], #B1 is a wildcard replacement
- [:A1, :B1, :C3]] #B1 is a wildcard replacement
+ [:C1, :C2, :C3]).should == [[:A1, :B1, :C1],
+ [:A1, :B2, :C3],
+ [:A2, :B1, :C3],
+ [:A2, :B2, :C2],
+ [:A3, :B1, :C2],
+ [:A3, :B2, :C1],
+ [:A2, :B1, :C1],
+ [:A1, :B1, :C2],
+ [:A3, :B1, :C3]]
end
end
end

0 comments on commit 960ffb7

Please sign in to comment.