// Source : https://oj.leetcode.com/problems/longest-palindromic-substring/ // Author : Hao Chen // Date : 2014-07-17 /********************************************************************************** * * Given a string S, find the longest palindromic substring in S. * You may assume that the maximum length of S is 1000, * and there exists one unique longest palindromic substring. * **********************************************************************************/ #include #include #include #include using namespace std; string findPalindrome(string s, int left, int right) { int n = s.size(); int l = left; int r = right; while (left>=0 && right<=n-1 && s[left] == s[right]) { left--; right++; } return s.substr(left+1, right-left-1); } // This is the common solution. // Actuatlly it's faster than DP solution under Leetcode's test // the below optimized DP solution need 700ms+, this needs around 250ms. string longestPalindrome_recursive_way(string s) { int n = s.size(); if (n<=1) return s; string longest; string str; for (int i=0; i longest.size()){ longest = str; } str = findPalindrome(s, i, i+1); if (str.size() > longest.size()){ longest = str; } } return longest; } //================================================================================ void findPalindrome(string s, int left, int right, int& start, int& len) { int n = s.size(); int l = left; int r = right; while (left>=0 && right<=n-1 && s[left] == s[right]) { left--; right++; } if (right-left-1 > len){ len = right-left-1; start = left+1; } } //The following solution is better than previous solution. //Because it remove the sub-string return in findPalindrome(). string longestPalindrome_recursive_way2(string s) { int n = s.size(); if (n<=1) return s; int start=0, len=0; string longest; string str; for (int i=0; i s[j] is Palindrome or not. //using char or int could cause the `Memory Limit Error` //vector< vector > matrix (n, vector(n)); //using bool type could cause the `Time Limit Error` vector< vector > matrix (n, vector(n)); // Dynamic Programming // 1) if i == j, then matrix[i][j] = true; // 2) if i != j, then matrix[i][j] = (s[i]==s[j] && matrix[i+1][j-1]) for (int i=n-1; i>=0; i--){ for (int j=i; j 3, then, check s[i]==s[j] && matrix[i+1][j-1] if ( i==j || (s[i]==s[j] && (j-i<2 || matrix[i+1][j-1]) ) ) { matrix[i][j] = true; if (longest.size() < j-i+1){ longest = s.substr(i, j-i+1); } } } } return longest; } // Optimized DP soltuion can be accepted by LeetCode. string longestPalindrome_dp_opt_way(string s) { int n = s.size(); if (n<=1) return s; //Construct a matrix, and consdier matrix[j][i] as s[i] -> s[j] is Palindrome or not. // ------^^^^^^ // NOTE: it's [j][i] not [i][j] //Using vector could cause the `Time Limit Error` //So, use the native array bool **matrix = (bool**)malloc(n*sizeof(bool*)); int start=0, len=0; // Dynamic Programming // 1) if i == j, then matrix[i][j] = true; // 2) if i != j, then matrix[i][j] = (s[i]==s[j] && matrix[i-1][j+1]) for (int i=0; i 3, then, check s[i]==s[j] && matrix[i-1][j+1] if ( i==j || (s[j]==s[i] && (i-j<2 || matrix[i-1][j+1]) ) ) { matrix[i][j] = true; if (len < i-j+1){ start = j; len = i-j+1; } } } } for (int i=0; i 1){ s = argv[1]; } cout << s << " : " << longestPalindrome(s) << endl; s = "321012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210012321001232100123210123210012321001232100123210123"; cout << s << " : " << longestPalindrome(s) << endl; //"illi" s = "iptmykvjanwiihepqhzupneckpzomgvzmyoybzfynybpfybngttozprjbupciuinpzryritfmyxyppxigitnemanreexcpwscvcwddnfjswgprabdggbgcillisyoskdodzlpbltefiz"; cout << s << " : " << longestPalindrome(s) << endl; return 0; }