标签:
Given a collection of distinct numbers, return all possible permutations.
For example,[1,2,3]
have the following permutations:
[ [1,2,3], [1,3,2], [2,1,3], [2,3,1], [3,1,2], [3,2,1] ]
分析:
当array里没有重复数的时候,要找出所有的排列,我们可以把每个数放在第一位,然后获得后面的数排列。利用递归原理,为了获得后面的数的排列,把剩余的数都逐个放在第二位,,,,直到一个新的数组填满。
1 public class Solution { 2 public List<List<Integer>> permute(int[] nums) { 3 List<List<Integer>> list = new ArrayList<List<Integer>>(); 4 permutation(nums, 0, nums.length, list); 5 return list; 6 } 7 8 void swap(int[] arr, int idx1, int idx2) { 9 int temp = arr[idx1]; 10 arr[idx1] = arr[idx2]; 11 arr[idx2] = temp; 12 } 13 14 void permutation(int[] arr, int index, int size, List<List<Integer>> list) { 15 if (index == size) { //填满了 16 addToList(arr, list); 17 } else { 18 for (int i = index; i < size; i++) { 19 swap(arr, i, index); // 把每个数都放在当前数组的“第一位” 20 permutation(arr, index + 1, size, list); //获得后面的数的排列 21 swap(arr, i, index); 22 } 23 } 24 } 25 26 void addToList(int[] arr, List<List<Integer>> list) { 27 ArrayList<Integer> temp = new ArrayList<Integer>(); 28 for (int i : arr) { 29 temp.add(i); 30 } 31 list.add(temp); 32 } 33 }
Permutations II
Given a collection of numbers that might contain duplicates, return all possible unique permutations.
For example,[1,1,2]
have the following unique permutations:
[ [1,1,2], [1,2,1], [2,1,1] ]
分析:
在这个问题里,因为有了重复数字的出现,所以,当把每个数字放在当前数组的第一位的时候,我们需要确保没有重复,我们可以用hashset来check是否重复。
1 public class Solution { 2 /* 3 *cnblogs.com/beiyeqingteng 4 */ 5 6 public List<List<Integer>> permuteUnique(int[] nums) { 7 List<List<Integer>> list = new ArrayList<List<Integer>>(); 8 Arrays.sort(nums); 9 permutation(nums, 0, nums.length, list); 10 return list; 11 } 12 13 void swap(int[] arr, int idx1, int idx2) { 14 int temp = arr[idx1]; 15 arr[idx1] = arr[idx2]; 16 arr[idx2] = temp; 17 } 18 19 void permutation(int[] arr, int index, int size, List<List<Integer>> list) { 20 if (index == size) { 21 addToList(arr, list); 22 } else { 23 // when swaping arr[i] with arr[index], we need to make sure the uniqueness of arr[i], 24 // otherwise, we will have duplicates. 25 HashSet<Integer> set = new HashSet<Integer>(); 26 for (int i = index; i < size; i++) { 27 if (set.contains(arr[i]) == false) { 28 set.add(arr[i]); 29 swap(arr, i, index); 30 permutation(arr, index + 1, size, list); 31 swap(arr, i, index); 32 } 33 } 34 } 35 } 36 37 void addToList(int[] arr, List<List<Integer>> list) { 38 ArrayList<Integer> temp = new ArrayList<Integer>(); 39 for (int i : arr) { 40 temp.add(i); 41 } 42 list.add(temp); 43 } 44 }
Note: 当时还考虑到用下面的方法来去重复,但是总是通不过,后来才发现,当swap operation完毕以后,后面部分数组已经不是单调递增的了。但是很欣慰的是,自己还是把问题解决了,而且个人认为,上面所讲的方法应该是最容易理解也是最简单的方法。
1 void permutation(int[] arr, int index, int size, List<List<Integer>> list) { 2 if (index == size) { 3 addToList(arr, list); 4 } else { 5 for (int i = index; i < size; i++) { 6 // arr[i] == arr[index] 不能做,是因为如果和index交换以后,arr[i]有和arr[index]相等,最后一定会重复。 7 // arr[i - 1] == arr[i] 也不能做,是因为前面那个值arr[i-1]已经与index交换过了,如果arr[index]和arr[i]再次交换,最后也会重复。 8 if (i != index && (arr[i] == arr[index] || arr[i - 1] == arr[i])) 9 continue; 10 swap(arr, i, index); 11 permutation(arr, index + 1, size, list); 12 swap(arr, i, index); 13 } 14 } 15 }
参考请注明出处:cnblogs.com/beiyeqingteng
标签:
原文地址:http://www.cnblogs.com/beiyeqingteng/p/5639334.html