TupleCombinationGenerator { public static <T> List<List<T>> generateCombinations(List<? extends Iterable<T>> inputLists) { if (inputLists.isEmpty()) { return Collections.emptyList(); } List<List<T>> results = new ArrayList<List<T>>(); Iterable<T> currentList = inputLists.get(0); if (inputLists.size() == 1) { for (T object : currentList) { results.add(new LinkedList<T>(Collections.singleton(object))); } } else { for (T object : currentList) { List<? extends Iterable<T>> tail = inputLists.subList(1, inputLists.size()); for (List<T> permutations : generateCombinations(tail)) { permutations.add(0, object); results.add(permutations); } } } return results; } TupleCombinationGenerator(); static List<List<T>> generateCombinations(List<? extends Iterable<T>> inputLists);  }
@Test public void testGenerateCombinations_EmptyOuterList() { List<List<Object>> permutations = TupleCombinationGenerator.generateCombinations(Collections.<List<Object>>emptyList()); Assert.assertTrue(permutations.isEmpty()); }
@Test public void testGenerateCombinations_AscendingListSize() { List<List<Object>> inputLists = new ArrayList<List<Object>>() {{ add(Arrays.<Object>asList(1)); add(Arrays.<Object>asList("bar", "baz")); add(Arrays.<Object>asList(2.0, 3.0, 4.0)); }}; List<List<Object>> permutations = TupleCombinationGenerator.generateCombinations(inputLists); Assert.assertEquals( "[[1, bar, 2.0], [1, bar, 3.0], [1, bar, 4.0], [1, baz, 2.0], [1, baz, 3.0], [1, baz, 4.0]]", permutations.toString() ); }
@Test public void testGenerateCombinations_EqualListSize() { List<List<Object>> inputLists = new ArrayList<List<Object>>() {{ add(Arrays.<Object>asList(1, 2)); add(Arrays.<Object>asList("bar", "baz")); add(Arrays.<Object>asList(3.0, 4.0)); }}; List<List<Object>> permutations = TupleCombinationGenerator.generateCombinations(inputLists); Assert.assertEquals( "[[1, bar, 3.0], [1, bar, 4.0], [1, baz, 3.0], [1, baz, 4.0], [2, bar, 3.0], [2, bar, 4.0], [2, baz, 3.0], [2, baz, 4.0]]", permutations.toString() ); }
@Test public void testGenerateCombinations_DescendingListSize() { List<List<Object>> inputLists = new ArrayList<List<Object>>() {{ add(Arrays.<Object>asList(1, 2, 3)); add(Arrays.<Object>asList("bar", "baz")); add(Arrays.<Object>asList(2.0)); }}; List<List<Object>> permutations = TupleCombinationGenerator.generateCombinations(inputLists); Assert.assertEquals( "[[1, bar, 2.0], [1, baz, 2.0], [2, bar, 2.0], [2, baz, 2.0], [3, bar, 2.0], [3, baz, 2.0]]", permutations.toString() ); }
@Test public void testGenerateCombinations_EmptySubList1() { List<List<Object>> inputLists = new ArrayList<List<Object>>() {{ add(Collections.emptyList()); add(Arrays.<Object>asList("bar", "baz")); add(Arrays.<Object>asList(2.0, 3.0, 4.0)); }}; List<List<Object>> permutations = TupleCombinationGenerator.generateCombinations(inputLists); Assert.assertTrue(permutations.isEmpty()); }
@Test public void testGenerateCombinations_EmptySubList2() { List<List<Object>> inputLists = new ArrayList<List<Object>>() {{ add(Arrays.<Object>asList(1)); add(Collections.emptyList()); add(Arrays.<Object>asList(2.0, 3.0, 4.0)); }}; List<List<Object>> permutations = TupleCombinationGenerator.generateCombinations(inputLists); Assert.assertTrue(permutations.isEmpty()); }
@Test public void testGenerateCombinations_EmptySubList3() { List<List<Object>> inputLists = new ArrayList<List<Object>>() {{ add(Arrays.<Object>asList(1)); add(Arrays.<Object>asList("bar", "baz")); add(Collections.emptyList()); }}; List<List<Object>> permutations = TupleCombinationGenerator.generateCombinations(inputLists); Assert.assertTrue(permutations.isEmpty()); }