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] ]
----------------------------------------------------------------------------------------------------
在这里,将介绍2种排列方法。
第一种方法非常容易理解:基于回溯的思想。
额外设置一个isUsed数组,来标记这个index下的数有没有被使用。
每次,我们都挑选一个没有被使用的数,加到我的list中去,继续递归
当我的list满了,则将这个list加到最终的result中去。
1. 比如,一开始1, 2, 3都没有被使用,假设我们挑了2, (此时有1, 2, 3 这3种选择)
2. 在挑了2后,我们选择3 (此时有1, 3 这2种选择)
3. 最后,只有1没有被使用了,挑选1.
这只是其中的一种情况,我们继续回上去,看有没有别的可能。
用递归的时候要注意:恢复现场
比如设置了isUsed[ i ] = true ; 往list加过东西。
在递归完了后,要变回原样(isUsed[ i ] = false, list中添加的东西删掉)
运行时间:
代码:
public List<List<Integer>> permute(int[] nums) {
List<List<Integer>> result = new ArrayList<>();
List<Integer> store = new ArrayList<>();
boolean[] isUsed = new boolean[nums.length];
doPermute(nums, isUsed, store, result);
return result;
}
private void doPermute(int[] nums, boolean[] isUsed, List<Integer> store, List<List<Integer>> result) {
if (store.size() == nums.length) {
result.add(new ArrayList<>(store));
return;
}
for (int i = 0; i < nums.length; i++) {
if (!isUsed[i]) {
store.add(nums[i]);
isUsed[i] = true;
doPermute(nums, isUsed, store, result);
store.remove(store.size() - 1);
isUsed[i] = false;
}
}
}
第二种方法:
第二种方法的思想是这样的:
假设我们的输入时{1,2, 3}
1. 我们先将1 加入,得到 { 1 }
2. 接着,2可以加到1的前面或者后面, 得到 { 1, 2 }, { 2, 1 }
3. 接着是3了, 3 可以选择{ 1, 2 } 选择加入index = 0, 1, 2中的位置。
对于{1, 2 } 可以得到 {3, 1, 2 }, {1, 3, 2 } ,{ 2, 1, 3 }
对于{2, 1} 可以得到{3, 2, 1 }, {2, 3, 1}, {2, 1,3}
运行时间:(跟第一种方法一样)
代码:
public List<List<Integer>> permute2(int[] nums) {
List<List<Integer>> result = new ArrayList<>();
if (nums.length == 0) {
return result;
}
List<Integer> curList = new ArrayList<>();
curList.add(nums[0]);
result.add(curList);
int index = 1;
while (index < nums.length) {
List<List<Integer>> newResult = new ArrayList<>();
for (List<Integer> list : result) {
for (int j = 0; j <= index; j++) {
List<Integer> newList = new ArrayList<>(list);
newList.add(j,nums[index]);
newResult.add(newList);
}
}
result = newResult;
index++;
}
return result;
}