Reputation: 20391
I'm looking to see if java has some combinatorics features that I can utilize. I want to have a dynamic list, and in a clean way, have java generate all combinations.
Given a list of objects, such as strings below. Is there an easy way/clean way/preferably something already built into core java to generate all combinations of the items? e.g. If I had:
List<String> items = new ArrayList<String>();
items.add("a");
items.add("b");
List<List<String>> result = generateCombinationOf(items);
I desire for results to contain: {{}, {"a"}, {"b"}, {"a", "b"}}
Side note: I was able to generate lists like this in mathematica in the past. I have a side project where I want to utilize java and I'm hoping to avoid integrating with mathematica if at all possible, but will if I can't find some features like the above easily available.
Upvotes: 1
Views: 1054
Reputation:
Try this.
static void generateCombinationOf(List<String> items,
List<String> selected, int index, List<List<String>> result) {
if (index >= items.size()) {
result.add(new ArrayList<>(selected));
} else {
generateCombinationOf(items, selected, index + 1, result);
selected.add(items.get(index));
generateCombinationOf(items, selected, index + 1, result);
selected.remove(selected.size() - 1);
}
}
static List<List<String>> generateCombinationOf(List<String> items) {
List<List<String>> result = new ArrayList<>();
List<String> selected = new ArrayList<>();
generateCombinationOf(items, selected, 0, result);
return result;
}
and
System.out.println(generateCombinationOf(Arrays.asList("a", "b")));
result
[[], [b], [a], [a, b]]
non-recursive version
static List<List<String>> generateCombinationOf(List<String> list) {
List<List<String>> result = new ArrayList<>();
for (int i = 0, max = 1 << list.size(); i < max; ++i) {
List<String> comb = new ArrayList<>();
for (int j = 0, k = i; k > 0; ++j, k >>= 1)
if ((k & 1) == 1)
comb.add(list.get(j));
result.add(comb);
}
return result;
}
Upvotes: 1