计算n个组有n种排列方式的几种算法

转载自:https://blog.csdn.net/Mikchy/article/details/91383798

题目:
把一个数组里的数的组合全部列出,比如1和2列来为1,2,12,21.

分析:
这道题有多种扩展

1,没有重复元素的数的组合

2,有重复元素的数的组合

3,没有重复元素的数的全排列

4,有重复元素的数的全排列

1,没有重复元素的数的组合
第一种情况下,没有重复元素的数的组合,利用DFS直接求,因为没有重复元素,所以不会出现一样的,将数组元素存在LinkedList里(方便删除),遍历List,删除当前元素并把此元素加入结果,如果结果长度不为0,则输出,以此递归。

public static void DFS(List<Integer> candidate, String prefix){
	if(prefix.length()!=0){
		System.out.println(prefix);
	}
	
	
	for(int i=0; i<candidate.size(); i++){
		
		List<Integer> temp = new LinkedList<Integer>(candidate);
		int item = (int)temp.remove(i);  // 取出被删除的元素,这个元素当作一个组合用掉了
		DFS(temp, prefix+item);
	}
}
public static void main(String[] args) {
	
	Integer[] array = {1,2};
	List<Integer> list = Arrays.asList(array);
	DFS(list, "");
}

2,有重复元素的数的组合
第二种情况,存在重复元素,如果直接用第一种情况的代码直接使用,可能会存在重复的,这里的处理方法是把结果保存在一个HashSet里,每得到一个结果,检查HashSet里是否已经存在,不存在才输出。

public static void DFS(List<Integer> candidate, String prefix, HashSet<String> hs){
	if(prefix.length()!=0 && !hs.contains(prefix)){
		System.out.println(prefix);
		hs.add(prefix);
	}
	
	
	for(int i=0; i<candidate.size(); i++){
		
		List<Integer> temp = new LinkedList<Integer>(candidate);
		int item = (int)temp.remove(i);
		DFS(temp, prefix+item, hs);
	}
}
public static void main(String[] args) {
	
	Integer[] array = {1,1,2};
	List<Integer> list = Arrays.asList(array);
	HashSet<String> hs = new HashSet<String>();
	DFS(list, "", hs);
}

3,没有重复元素的数的全排列
这种情况是全排列,所以只需要在第一种情况的输出时,多加一个判断条件,此时的输入List 中无数据(说明已经全部使用来排列了)。

public static void DFS(List<Integer> candidate, String prefix){
	if(prefix.length()!=0 && candidate.size()==0){
		System.out.println(prefix);
	}
	
	
	for(int i=0; i<candidate.size(); i++){
		
		List<Integer> temp = new LinkedList<Integer>(candidate);
		int item = (int)temp.remove(i);  // 取出被删除的元素,这个元素当作一个组合用掉了
		DFS(temp, prefix+item);
	}
}
public static void main(String[] args) {
	
	Integer[] array = {1,2};
	List<Integer> list = Arrays.asList(array);
	DFS(list, "");
}

4,有重复元素的数的全排列
这种情况是全排列,有重复元素,是第二种情况的扩展,所以只需要在第二种情况的输出时,多加一个判断条件,此时的输入List 中无数据(说明已经全部使用来排列了)。

public static void DFS(List<Integer> candidate, String prefix, HashSet<String> hs){
	if(prefix.length()!=0 && !hs.contains(prefix) && candidate.size()==0){
		System.out.println(prefix);
		hs.add(prefix);
	}
	
	
	for(int i=0; i<candidate.size(); i++){
		
		List<Integer> temp = new LinkedList<Integer>(candidate);
		int item = (int)temp.remove(i);
		DFS(temp, prefix+item, hs);
	}
}
public static void main(String[] args) {
	
	Integer[] array = {1,1,2};
	List<Integer> list = Arrays.asList(array);
	HashSet<String> hs = new HashSet<String>();
	DFS(list, "", hs);
}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章