class Apriori {

	static <T> Set<Set<T>> aprioriGen(Set<Set<T>> itemsets) {
		Set<Set<T>> candidates = new HashSet<>();
		for (Set<T> s1 : itemsets) {
			for (Set<T> s2 : itemsets) {
				Set<T> union = new HashSet<>(s1);
				union.addAll(s2);
				if (union.size() == s1.size() + 1) {
					candidates.add(union);
				}
			}
		}
		// prune; remove those candidates, where not all k-1 subsets are
		// contained in the provided itemsets
		Iterator<Set<T>> iterator = candidates.iterator();
		while (iterator.hasNext()) {
			Set<T> candidate = iterator.next();
			for (Set<T> subset : kMinusOneSubsets(candidate)) {
				if (!itemsets.contains(subset)) {
					iterator.remove();
					break;
				}
			}
		}
		return candidates;
	}

	private  Apriori();

}