1. 程式人生 > >劍指offer——27.字串的排列

劍指offer——27.字串的排列

題目描述:

輸入一個字串,按字典序打印出該字串中字元的所有排列。例如輸入字串abc,則打印出由字元a,b,c所能排列出來的所有字串abc,acb,bac,bca,cab和cba。

輸入描述:輸入一個字串,長度不超過9(可能有字元重複),字元只包括大小寫字母。

解題思路:

每次確定第一位的字母,將剩餘字母繼續組成一個字串,再確定剩餘字串首字母,迴圈往復,便是遞迴。

參考原始碼1:

class Solution {
public:
        vector<string> res;
    vector<string> Permutation(string str)
    {  
        if(str.length() == 0) return res;
        sort(str.begin(),str.end());
        string tmp = "";
        Helper(str,tmp);
        return res;
    }  
    void Helper(string str,string str1)
    {  
            if(str.length() == 0)
            {
                    res.push_back(str1);
                    return;
            }
            for(int i = 0;i < str.length();i++)
            {
                if(i == 0)
                {
                    string tmp = str;
                    tmp.erase(tmp.begin());
                    Helper(tmp,str1+str[0]);
                    continue;
                }
                if(str[i] == str[i-1]) continue;
                string tmp = str;
                tmp.erase(tmp.begin()+i);
                Helper(tmp,str1+str[i]);
            }
    }  
};

參考原始碼2:

第一種方法是在原字串中去掉某個字母,本方法是將首字母跟後方字母進行調換,以使每次首字母都不同,同樣是使用遞迴。

class Solution {
public:
    vector<string> res;
    vector<string> Permutation(string str) {
        if(str.length() == 0) return res;
        helper(str,0);
        sort(res.begin(),res.end());
        return res;
    }
    void helper(string str,int pos)
    {
        if(pos == str.length()-1)
        {
            res.push_back(str);
            return;
        }
        for(int i = pos;i < str.length();i++)
        {
            if(i != pos && str[i] == str[pos]) continue;
            char tmp = str[pos];
            str[pos] = str[i];
            str[i] = tmp;
            helper(str,pos+1);
            str[i] = str[pos];
            str[pos] = tmp;
        }
    }
};