/*
 * This file is part of Nuts Framework.
 * Copyright(C) 2009-2012 Nuts Develop Team.
 *
 * Nuts Framework is free software: you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation, either version 3 of the License any later version.
 * 
 * Nuts Framework is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with Nuts Framework. If not, see <http://www.gnu.org/licenses/>.
 */
package nuts.core.algorithm;

import nuts.core.lang.Arrays;
import nuts.core.lang.Strings;

/**
 */
public class Permutater {
	protected int[] index;
	protected long count;
	
	public Permutater() {
	}
	
	/**
	 * @return the count
	 */
	public long getCount() {
		return count;
	}

	protected boolean handle() {
		System.out.println(count + ": " + Strings.join(index, " "));
		return true;
	}
	
	public long count(int size) {
		long count = 1;
		for (int i = 2; i <= size; i++) {
			count *= i;
		}
		return count;
	}

	public long permutate(int size) {
		index = new int[size];
		for (int i = 0; i < size; i++) {
			index[i] = i;
		}
		
		count = 0;
		permutate(0, size);
		return count;
	}
	
	protected boolean permutate(int m, int len) {
		if (m < len - 1) {
			if (!permutate(m + 1, len)) {
				return false;
			}

			for (int i = m + 1; i < len; i++) {
				Arrays.swap(index, m, i);

				if (!permutate(m + 1, len)) {
					return false;
				}

				Arrays.swap(index, m, i);
			}
			return true;
		} 
		else {
			count++;
			return handle();
		}
	}
}
