第二十六题:字符串的全排列
题目描述
输入一个字符串,按字典序打印出该字符串中字符的所有排列。例如输入字符串abc,则打印出由字符a,b,c所能排列出来的所有字符串abc,acb,bac,bca,cab和cba。
输入描述:
输入一个字符串,长度不超过9(可能有字符重复),字符只包括大小写字母。
思路:
递归+回溯思想
①递归:也就是穷举,把所有情况都列举出来
②回溯:在递归的过程中,回退的步骤
具体实现如下图所示(改图引用高人的:手动狗头):
具体实现代码如下:
public class Solution {
public ArrayList<String> Permutation(String str) {
ArrayList list = new ArrayList();
if (str != null && str.length() > 0) {
PermutationHelper(str.toCharArray(), 0, list);
//上图所示,左右在以C开头的字符串,结果并不是已经排好序的,所以进行sort
Collections.sort(list);
}
return list;
}
//递归method
public static void PermutationHelper(char[] cs,int i, ArrayList list) {
//当进行两次交换即:A swap A , B swap B
if(i == cs.length - 1) {
//结果之一
String val = String.valueOf(cs);
//这里做了去重判断,原因是因为当有重复的元素时会出现相同的字符串,例:aabc
if (!list.contains(val)){
list.add(val);
}
}else {
for(int j = i; j < cs.length; ++j) {
swap(cs, i, j);
PermutationHelper(cs, i + 1, list);
//回溯
swap(cs, i, j);
}
}
}
//swap交换操作
public static void swap(char[] s,int i,int j) {
char tmp = s[i];
s[i] = s[j];
s[j] = tmp;
}
}
这里有个大佬写的一种复杂度更低的做法,可以参照看一看
http://www.cnblogs.com/pmars/p/3458289.html