Given a string s
, return all the palindromic permutations (without duplicates) of it. Return an empty list if no palindromic permutation could be form.
For example:
Given s = "aabb"
, return ["abba", "baab"]
.
Given s = "abc"
, return []
.
思路:
这道题我的思路不是太好。首先我把字符串进行了排序,然后确定奇数字符的个数,如果大于1则返回[],因为无论如何不可能是palindrome。然后我天真的用了一个dfs去遍历,碰到偶数字符则放在两边,奇数字符放在中间。但是这里我有一个问题没有考虑到,就是在遍历的过程中,比如对于aa,b来说
先遍历aa,然后遍历b, 得到aab; 然后清空当前字符串,然后再遍历的时候,会先遍历b,再遍历aa,于是又得道了aab。 所以当有奇数字符的时候会出现重复。这道题我懒得去想一个更优解,于是我直接用unique和erase来去重。。。
代码如下:
class Solution {
public:
vector<string> generatePalindromes(string s) {
//init
vector<string> result;
string solu;
vector<bool> used(s.size(),false);
sort(s.begin(),s.end());
int numofsingle = 0;
int idx = 0;
while (idx < s.size()) {
if (s[idx] == s[idx+1])
idx = idx+2;
else {
numofsingle++;
idx++;
}
}
if (numofsingle > 1) {
return result;
}
//start dfs
dfs(result,solu,used,0,s);
sort(result.begin(),result.end());
result.erase(unique(result.begin(),result.end()),result.end());
return result;
}
private:
void dfs(vector<string> &result,string solu,vector<bool> &used,int len,string s) {
if (len == s.size()) {
result.push_back(solu);
return;
}
for (int i = 0; i < s.size(); i = i+2) {
if (used[i])
continue;
if (i+1 < s.size() && s[i] == s[i+1]) {
used[i] = used[i+1] = true;
solu = s[i]+solu+s[i+1];
dfs(result,solu,used,len+2,s);
solu = solu.substr(1,solu.size()-2);
used[i] = used[i+1] = false;
} else {
used[i] = true;
solu.insert(solu.begin()+len/2,s[i]);
dfs(result,solu,used,len+1,s);
solu.erase(solu.begin()+len/2);
used[i] = false;
i--;
}
}
}
};