say I have a set of numbers \'0\', \'1\', \'2\', ..., \'9\'. I want to find all numbers that contain exactly one of each of the numbers in my set.
The problem is: Be
How many numbers, and which ones, aren't two questions. If you know which numbers, you know how many.
And the names of the numbers aren't very interesting. 1-3-14 or 0-1-2 or Foo-Bar-Baz - it is always the same problem, the same problem as the permutations of 0-1-2 and with an array, where to look up the result.
idx nums words
0 1 foo
1 3 bar
2 14 baz
The most convenient solution is, to write a generic Iterable. Then you can use the simplified for-loop, to access each permutation.
import java.util.*;
class PermutationIterator implements Iterator > {
private int current = 0;
private final long last;
private final List lilio;
public PermutationIterator (final List llo) {
lilio = llo;
long product = 1;
for (long p = 1; p <= llo.size (); ++p)
product *= p;
last = product;
}
public boolean hasNext () {
return current != last;
}
public List next () {
++current;
return get (current - 1, lilio);
}
public void remove () {
++current;
}
private List get (final int code, final List li) {
int len = li.size ();
int pos = code % len;
if (len > 1) {
List rest = get (code / len, li.subList (1, li.size ()));
List a = rest.subList (0, pos);
List res = new ArrayList ();
res.addAll (a);
res.add (li.get (0));
res.addAll (rest.subList (pos, rest.size ()));
return res;
}
return li;
}
}
class PermutationIterable implements Iterable > {
private List lilio;
public PermutationIterable (List llo) {
lilio = llo;
}
public Iterator > iterator () {
return new PermutationIterator (lilio);
}
}
class PermutationIteratorTest {
public static void main (String[] args) {
List la = Arrays.asList (new Integer [] {1, 3, 14});
PermutationIterable pi = new PermutationIterable (la);
for (List lc: pi)
show (lc);
}
public static void show (List lo) {
System.out.print ("(");
for (Object o: lo)
System.out.print (o + ", ");
System.out.println (")");
}
}