Given a collection of distinct integers, return all possible permutations.
Example
Consideration
- clearly, we should user recursion in this problem
- One main point is that arraylist passing by reference. When we add an element to the list, we should remove it after the recursion.
Solution 1
Time Complexity: O(n^n)
class Solution {
List<List<Integer>> res = new ArrayList();
public List<List<Integer>> permute(int[] nums) {
List<Integer> per = new ArrayList();
getPermute(nums, per);
return res;
}
private void getPermute(int[] nums, List<Integer> per) {
if(nums.length == 1) {
per.add(nums[0]);
List<Integer> temp = new ArrayList<Integer>();
for (int num : per) temp.add(num);
res.add(temp);
per.remove(per.size()-1);
} else {
for(int i = 0; i < nums.length; i++) {
per.add(nums[i]);
int[] newNums = new int[nums.length-1];
for(int j = 0; j < nums.length-1; j++) {
if(j < i) {
newNums[j] = nums[j];
} else {
newNums[j] = nums[j+1];
}
}
getPermute(newNums,per);
per.remove(per.size()-1);
}
}
}
}
==Solution 2: dfs ==
Consideration
- to get the permutation, we should swap current number with numbers at other positions
class Solution {
public List<List<Integer>> permute(int[] nums) {
List<List<Integer>> res = new ArrayList();
dfs(res, nums, 0);
return res;
}
private void dfs(List<List<Integer>> res, int[] nums, int cur) {
if(cur == nums.length) {
List<Integer> temp = new ArrayList<Integer>();
for (int num : nums) temp.add(num);
res.add(temp);
} else {
for(int i = cur; i < nums.length; i++) {
swap(nums, cur, i);
dfs(res, nums, cur+1);
swap(nums, cur, i);
}
}
}
private void swap(int[] nums, int i, int j) {
int temp = nums[j];
nums[j] = nums[i];
nums[i] = temp;
}
}
Solution 3: dfs, similar to solution 1, but use a boolean array to store whether the number has been visited
class Solution {
public List<List<Integer>> permute(int[] nums) {
List<List<Integer>> res = new ArrayList();
boolean[] visited = new boolean[nums.length];
dfs(res, new ArrayList(), nums, visited);
return res;
}
private void dfs(List<List<Integer>> res, List<Integer> temp, int[] nums, boolean[] visited) {
if(temp.size() == nums.length) {
// cannot directly add the temp to the res, as it is passed by reference
res.add(new ArrayList(temp));
} else {
for(int i = 0; i < nums.length; i++) {
if(!visited[i]) {
visited[i]= true;
temp.add(nums[i]);
dfs(res, temp, nums, visited);
temp.remove(temp.size()-1);
visited[i]=false;
}
}
}
}
}
Solution 4:
Consideration
- Each permutation is built upon the permutations of the first n-1 numbers. We add the latter number to every possible position of the (n-1) permutations.
class Solution {
public List<List<Integer>> permute(int[] nums) {
List<List<Integer>> res = new ArrayList();
if(nums == null || nums.length == 0)
return res;
List<Integer> first = new ArrayList();
first.add(nums[0]);
res.add(first);
for(int i = 1; i < nums.length; i++) {
List<List<Integer>> newRes = new ArrayList();
for(List<Integer> item: res) {
for(int j = 0; j <= item.size(); j++) {
List<Integer> temp = new ArrayList(item);
temp.add(j, nums[i]);
newRes.add(temp);
}
}
res = newRes;
}
return res;
}
}
Reference