topic link
Niuke.com online oj question - the arrangement of strings
topic description
Input a string of length n, print out all permutations of the characters in the string, you can return this string array in any order.
For example, input the string ABC, then output all the strings ABC, ACB, BAC, BCA, CBA, and CAB that can be arranged by the characters A, B, and C.
Data range: n<10
Requirements: space complexity O(n!), time complexity O(n!)
Input description:
Enter a string, the length does not exceed 10, and the characters only include uppercase and lowercase letters.
Topic example
Example 1
Enter:
"ab"
Return value:
["ab", "ba"]
Explanation:
Returning ["ba", "ab"] is also correct
Example 2
Enter:
"aab"
Return Value:
["aab", "aba", "baa"]
Example 3
Enter:
"abc"
Return value:
["abc", "acb", "bac", "bca", "cab", "cba"]
Example 4
Enter:
""
return value:
[""]
problem solving ideas
This question can use depth-first search and backtracking to list all the cases, and then add the qualified process set to the result set
First define ArrayList<String> result as the result set returned at last.
Defines a Stack<Character> path, as the set of procedures generated during recursion.
Define boolean[] isUsed to determine whether the current location has been used
Implement the depth recursive function PermutationDFS(char[] chars, int depth, Stack< Character> path, boolean[] isUsed, ArrayList result), the parameters are respectively the char array corresponding to str, the recursion depth depth, the process set path, and whether the flag has been traversed The isUsed array, the result set result
The recursion termination condition is: when the recursion depth is equal to the length of chars, construct it as a string, add it to the result set result to
create a loop, from 0 to the length of chars - 1, representing the starting position of the arrangement, if the current position Used (isUsed[i] == true), then continue
to add the current element chars[i] to the process set, mark the position as traversed (isUsed[i] = true), and then continue to recurse, let the recursion depth Add one
When the recursion returns to the current position, it should go back to the state where the recursion has not started, set isUsed[i] = false, and delete the current element of the process set
Finally, create a HashSet and add all the elements in the result to the HashSet to prevent adding duplicate sequences
full code
import java.util.*;
public class Solution {
public ArrayList<String> Permutation(String str) {
ArrayList<String> result = new ArrayList<>();
if(str != null && str.length() > 0){
Stack<Character> path = new Stack<>();
boolean[] isUsed = new boolean[str.length()];
PermutationDFS(str.toCharArray(), 0, path, isUsed, result);
HashSet<String> hashSet = new HashSet<>();
for (int i = 0; i < result.size(); i++){
hashSet.add(result.get(i));
}
ArrayList<String> newResult = new ArrayList<>(hashSet);
Collections.sort(newResult);
return newResult;
}
return result;
}
private void PermutationDFS(char[] chars, int depth, Stack<Character> path, boolean[] isUsed, ArrayList<String> result) {
if(depth == chars.length){
ArrayList<Character> tmp = new ArrayList<>(path);
StringBuilder stringBuilder = new StringBuilder();
for (int i = 0; i < tmp.size(); i++){
stringBuilder.append(tmp.get(i));
}
result.add(stringBuilder.toString());
return;
}
for (int i = 0; i < chars.length; i++){
if(isUsed[i]){
continue;
}
path.add(chars[i]);
isUsed[i] = true;
PermutationDFS(chars, depth + 1, path, isUsed, result);
isUsed[i] = false;
path.pop();
}
}
}