2014.2.26 22:36
Given a string s, partition s such that every substring of the partition is a palindrome.
Return all possible palindrome partitioning of s.
For example, given s = "aab"
,
Return
[ ["aa","b"], ["a","a","b"] ]
Solution:
This problem can be solved with DFS, where in each recursion you find a palindromic segment.
I first tried to judge if the segent is palindrome in the recursive function, but it proved to be inefficient enough. Later I realized it would only require O(n^2) time to check every palindrome segments in the string. If you store the result with a 2d array, you can find out if a segment is palindromic in O(1) time. This will reduce a lot of time in recursion.
Luckily the input string wouldn't be quite long, as the algorithm is almost factorial in time.
Total time complexity is O(n!). Space complexity is O(n^2).
Accepted code:
1 // 1CE, 2RE, 1AC, beware of subscript overflow. 2 #include <string> 3 #include <vector> 4 using namespace std; 5 6 class Solution { 7 public: 8 vector<vector<string> > partition(string s) { 9 int i; 10 11 len = (int)s.length(); 12 for (i = 0; i < (int)result.size(); ++i) { 13 result[i].clear(); 14 } 15 result.clear(); 16 17 for (i = 0; i < 256; ++i) { 18 pos.push_back(vector<int>()); 19 } 20 // record the position of each characters 21 for (i = 0; i < len; ++i) { 22 pos[s[i]].push_back(i); 23 } 24 dfs(s, 0); 25 26 // clean up 27 vl.clear(); 28 vr.clear(); 29 for (i = 0; i < 256; ++i) { 30 pos[i].clear(); 31 } 32 pos.clear(); 33 34 return result; 35 } 36 private: 37 vector<int> vl, vr; 38 int len; 39 vector<vector<string> > result; 40 vector<string> single_result; 41 vector<vector<int> > pos; 42 43 void dfs(const string &s, int idx) { 44 int i, j; 45 if (idx == len) { 46 for (i = 0; i < (int)vl.size(); ++i) { 47 single_result.push_back(s.substr(vl[i], vr[i] - vl[i] + 1)); 48 } 49 result.push_back(vector<string>(single_result)); 50 single_result.clear(); 51 return; 52 } 53 54 int ll, rr; 55 ll = idx; 56 for (i = (int)pos[s[idx]].size() - 1; i >= 0 && pos[s[idx]][i] >= idx; --i) { 57 rr = pos[s[idx]][i]; 58 for (j = ll; j < ll + rr - j; ++j) { 59 if (s[j] != s[ll + rr - j]) { 60 break; 61 } 62 } 63 if (j >= ll + rr - j) { 64 // a palindromic substring is found 65 vl.push_back(ll); 66 vr.push_back(rr); 67 dfs(s, rr + 1); 68 vl.pop_back(); 69 vr.pop_back(); 70 } 71 } 72 } 73 };