Count All Palindromic Subsequence in a given String
Last Updated :
29 Nov, 2023
Find how many palindromic subsequences (need not necessarily be distinct) can be formed in a given string. Note that the empty string is not considered a palindrome.
Examples:
Input : str = "abcd"
Output : 4
Explanation :- palindromic subsequence are : "a" ,"b", "c" ,"d"
Input : str = "aab"
Output : 4
Explanation :- palindromic subsequence are :"a", "a", "b", "aa"
Input : str = "aaaa"
Output : 15
The above problem can be recursively defined.
Initial Values : i= 0, j= n-1;
CountPS(i,j)
// Every single character of a string is a palindrome
// subsequence
if i == j
return 1 // palindrome of length 1
// If first and last characters are same, then we
// consider it as palindrome subsequence and check
// for the rest subsequence (i+1, j), (i, j-1)
Else if (str[i] == str[j])
return countPS(i+1, j) + countPS(i, j-1) + 1;
else
// check for rest sub-sequence and remove common
// palindromic subsequences as they are counted
// twice when we do countPS(i+1, j) + countPS(i,j-1)
return countPS(i+1, j) + countPS(i, j-1) - countPS(i+1, j-1)
Recursive Approach
Here is the recursive code to the above approach
C++
#include <iostream>
#include <string>
using namespace std;
int Solve(string str, int i, int j) {
if (i == j)
return 1;
if (i > j)
return 0;
if (str[i] == str[j]) {
return 1 + Solve(str, i + 1, j) + Solve(str, i, j - 1);
} else {
return Solve(str, i + 1, j) + Solve(str, i, j - 1) - Solve(str, i + 1, j - 1);
}
}
int main() {
string str = "abcb" ;
cout << "Total palindromic subsequence are: " << Solve(str, 0, str.length() - 1) << endl;
return 0;
}
|
Java
public class GFG {
static int solve(String str, int i, int j)
{
if (i == j)
return 1 ;
if (i > j)
return 0 ;
if (str.charAt(i) == str.charAt(j)) {
return 1 + solve(str, i + 1 , j)
+ solve(str, i, j - 1 );
}
else
return solve(str, i + 1 , j)
+ solve(str, i, j - 1 )
- solve(str, i + 1 , j - 1 );
}
public static void main(String args[])
{
String str = "abcb" ;
System.out.println(
"Total palindromic "
+ "subsequence are : "
+ solve(str, 0 , str.length() - 1 ));
}
}
|
Python3
def solve(s, i, j):
if i = = j:
return 1
if i > j:
return 0
if s[i] = = s[j]:
return 1 + solve(s, i + 1 , j) + solve(s, i, j - 1 )
else :
return solve(s, i + 1 , j) + solve(s, i, j - 1 ) - solve(s, i + 1 , j - 1 )
if __name__ = = "__main__" :
s = "abcb"
print ( "Total palindromic subsequences are:" , solve(s, 0 , len (s) - 1 ))
|
C#
using System;
public class GFG
{
static int Solve( string str, int i, int j)
{
if (i == j)
return 1;
if (i > j)
return 0;
if (str[i] == str[j])
{
return 1 + Solve(str, i + 1, j) + Solve(str, i, j - 1);
}
else
{
return Solve(str, i + 1, j) + Solve(str, i, j - 1) - Solve(str, i + 1, j - 1);
}
}
public static void Main( string [] args)
{
string str = "abcb" ;
Console.WriteLine( "Total palindromic subsequence are: " + Solve(str, 0, str.Length - 1));
}
}
|
Javascript
function solve(str, i, j) {
if (i === j)
return 1;
if (i > j)
return 0;
if (str[i] === str[j]) {
return 1 + solve(str, i + 1, j) + solve(str, i, j - 1);
} else {
return solve(str, i + 1, j) + solve(str, i, j - 1) - solve(str, i + 1, j - 1);
}
}
const str = "abcb" ;
console.log( "Total palindromic subsequences are: " + solve(str, 0, str.length - 1));
|
Output
Total palindromic subsequence are : 6
If we draw recursion tree of the above recursive solution, we can observe overlapping Subproblems. Since the problem has overlapping subproblems, we can solve it efficiently using Dynamic Programming. Below is Dynamic Programming based solution.
C++
#include <cstring>
#include <iostream>
using namespace std;
int countPS(string str)
{
int N = str.length();
int cps[N + 1][N + 1];
memset (cps, 0, sizeof (cps));
for ( int i = 0; i < N; i++)
cps[i][i] = 1;
for ( int L = 2; L <= N; L++) {
for ( int i = 0; i <= N-L; i++) {
int k = L + i - 1;
if (str[i] == str[k])
cps[i][k]
= cps[i][k - 1] + cps[i + 1][k] + 1;
else
cps[i][k] = cps[i][k - 1] + cps[i + 1][k]
- cps[i + 1][k - 1];
}
}
return cps[0][N - 1];
}
int main()
{
string str = "abcb" ;
cout << "Total palindromic subsequence are : "
<< countPS(str) << endl;
return 0;
}
|
Java
public class GFG {
static int countPS(String str)
{
int N = str.length();
int [][] cps = new int [N][N];
for ( int i = 0 ; i < N; i++)
cps[i][i] = 1 ;
for ( int L = 2 ; L <= N; L++) {
for ( int i = 0 ; i <= N-L; i++) {
int k = L + i - 1 ;
if (str.charAt(i) == str.charAt(k)) {
cps[i][k] = cps[i][k - 1 ]
+ cps[i + 1 ][k] + 1 ;
} else {
cps[i][k] = cps[i][k - 1 ]
+ cps[i + 1 ][k]
- cps[i + 1 ][k - 1 ];
}
}
}
return cps[ 0 ][N - 1 ];
}
public static void main(String args[])
{
String str = "abcb" ;
System.out.println( "Total palindromic "
+ "subsequence are : "
+ countPS(str));
}
}
|
Python3
def countPS( str ):
N = len ( str )
cps = [[ 0 for i in range (N + 2 )] for j in range (N + 2 )]
for i in range (N):
cps[i][i] = 1
for L in range ( 2 , N + 1 ):
for i in range (N):
k = L + i - 1
if (k < N):
if ( str [i] = = str [k]):
cps[i][k] = (cps[i][k - 1 ] +
cps[i + 1 ][k] + 1 )
else :
cps[i][k] = (cps[i][k - 1 ] +
cps[i + 1 ][k] -
cps[i + 1 ][k - 1 ])
return cps[ 0 ][N - 1 ]
str = "abcb"
print ( "Total palindromic subsequence are : " , countPS( str ))
|
C#
using System;
class GFG {
static int countPS( string str)
{
int N = str.Length;
int [, ] cps = new int [N + 1, N + 1];
for ( int i = 0; i < N; i++)
cps[i, i] = 1;
for ( int L = 2; L <= N; L++) {
for ( int i = 0; i <= N-L; i++) {
int k = L + i - 1;
if (k < N) {
if (str[i] == str[k])
cps[i, k] = cps[i, k - 1]
+ cps[i + 1, k] + 1;
else
cps[i, k] = cps[i, k - 1]
+ cps[i + 1, k]
- cps[i + 1, k - 1];
}
}
}
return cps[0, N - 1];
}
public static void Main()
{
string str = "abcb" ;
Console.Write( "Total palindromic "
+ "subsequence are : "
+ countPS(str));
}
}
|
Javascript
<script>
function countPS(str)
{
let N = str.length;
let cps = new Array(N);
for (let i=0;i<N;i++)
{
cps[i]= new Array(N);
for (let j=0;j<N;j++)
{
cps[i][j]=0;
}
}
for (let i = 0; i < N; i++)
cps[i][i] = 1;
for (let L = 2; L <= N; L++) {
for (let i = 0; i <= N-L; i++) {
let k = L + i - 1;
if (str[i] == str[k]) {
cps[i][k] = cps[i][k - 1]
+ cps[i + 1][k] + 1;
} else {
cps[i][k] = cps[i][k - 1]
+ cps[i + 1][k]
- cps[i + 1][k - 1];
}
}
}
return cps[0][N - 1];
}
let str = "abcb" ;
document.write( "Total palindromic "
+ "subsequence are : "
+ countPS(str));
</script>
|
PHP
<?php
function countPS( $str )
{
$N = strlen ( $str );
$cps = array_fill (0, $N + 1,
array_fill (0, $N + 1, NULL));
for ( $i = 0; $i < $N ; $i ++)
$cps [ $i ][ $i ] = 1;
for ( $L = 2; $L <= $N ; $L ++)
{
for ( $i = 0; $i <= $N - $L ; $i ++)
{
$k = $L + $i - 1;
if ( $str [ $i ] == $str [ $k ])
$cps [ $i ][ $k ] = $cps [ $i ][ $k - 1] +
$cps [ $i + 1][ $k ] + 1;
else
$cps [ $i ][ $k ] = $cps [ $i ][ $k - 1] +
$cps [ $i + 1][ $k ] -
$cps [ $i + 1][ $k - 1];
}
}
return $cps [0][ $N - 1];
}
$str = "abcb" ;
echo "Total palindromic subsequence are : " .
countPS( $str ) . "\n" ;
?>
|
Output
Total palindromic subsequence are : 6
Time Complexity: O(N2)
Auxiliary Space: O(N2)
Another approach: (Using memoization)
C++
#include <bits/stdc++.h>
using namespace std;
int n, dp[1000][1000];
string str = "abcb" ;
int countPS( int i, int j)
{
if (i > j)
return 0;
if (dp[i][j] != -1)
return dp[i][j];
if (i == j)
return dp[i][j] = 1;
else if (str[i] == str[j])
return dp[i][j]
= countPS(i + 1, j) +
countPS(i, j - 1) + 1;
else
return dp[i][j] = countPS(i + 1, j) +
countPS(i, j - 1) -
countPS(i + 1, j - 1);
}
int main()
{
memset (dp, -1, sizeof (dp));
n = str.size();
cout << "Total palindromic subsequence are : "
<< countPS(0, n - 1) << endl;
return 0;
}
|
Java
class GFG {
static int n;
static int [][] dp = new int [ 1000 ][ 1000 ];
static String str = "abcb" ;
static int countPS( int i, int j)
{
if (i > j)
return 0 ;
if (dp[i][j] != - 1 )
return dp[i][j];
if (i == j)
return dp[i][j] = 1 ;
else if (str.charAt(i) == str.charAt(j))
return dp[i][j]
= countPS(i + 1 , j) +
countPS(i, j - 1 ) + 1 ;
else
return dp[i][j] = countPS(i + 1 , j) +
countPS(i, j - 1 ) -
countPS(i + 1 , j - 1 );
}
public static void main(String[] args)
{
for ( int i = 0 ; i < 1000 ; i++)
for ( int j = 0 ; j < 1000 ; j++)
dp[i][j] = - 1 ;
n = str.length();
System.out.println( "Total palindromic subsequence"
+ "are : " + countPS( 0 , n - 1 ));
}
}
|
Python 3
str = "abcb"
def countPS(i, j):
if (i > j):
return 0
if (dp[i][j] ! = - 1 ):
return dp[i][j]
if (i = = j):
dp[i][j] = 1
return dp[i][j]
else if ( str [i] = = str [j]):
dp[i][j] = (countPS(i + 1 , j) +
countPS(i, j - 1 ) + 1 )
return dp[i][j]
else :
dp[i][j] = (countPS(i + 1 , j) +
countPS(i, j - 1 ) -
countPS(i + 1 , j - 1 ))
return dp[i][j]
if __name__ = = "__main__" :
dp = [[ - 1 for x in range ( 1000 )]
for y in range ( 1000 )]
n = len ( str )
print ( "Total palindromic subsequence are :" ,
countPS( 0 , n - 1 ))
|
C#
using System;
class GFG {
static int n;
static int [, ] dp = new int [1000, 1000];
static string str = "abcb" ;
static int countPS( int i, int j)
{
if (i > j)
return 0;
if (dp[i, j] != -1)
return dp[i, j];
if (i == j)
return dp[i, j] = 1;
else if (str[i] == str[j])
return dp[i, j]
= countPS(i + 1, j) +
countPS(i, j - 1) + 1;
else
return dp[i, j] = countPS(i + 1, j)
+ countPS(i, j - 1)
- countPS(i + 1, j - 1);
}
static void Main()
{
for ( int i = 0; i < 1000; i++)
for ( int j = 0; j < 1000; j++)
dp[i, j] = -1;
n = str.Length;
Console.Write( "Total palindromic subsequence"
+ "are : " + countPS(0, n - 1));
}
}
|
Javascript
<script>
let n;
let dp= new Array(1000);
for (let i=0;i<1000;i++)
{
dp[i]= new Array(1000);
for (let j=0;j<1000;j++)
{
dp[i][j]=-1;
}
}
let str = "abcb" ;
function countPS(i,j)
{
if (i > j)
return 0;
if (dp[i][j] != -1)
return dp[i][j];
if (i == j)
return dp[i][j] = 1;
else if (str[i] == str[j])
return dp[i][j]
= countPS(i + 1, j) +
countPS(i, j - 1) + 1;
else
return dp[i][j] = countPS(i + 1, j) +
countPS(i, j - 1) -
countPS(i + 1, j - 1);
}
n = str.length;
document.write( "Total palindromic subsequence"
+ "are : " + countPS(0, n - 1));
</script>
|
PHP
<?php
$dp = array_fill (0, 100,
array_fill (0, 1000, -1));
$str = "abcb" ;
$n = strlen ( $str );
function countPS( $i , $j )
{
global $str , $dp , $n ;
if ( $i > $j )
return 0;
if ( $dp [ $i ][ $j ] != -1)
return $dp [ $i ][ $j ];
if ( $i == $j )
return $dp [ $i ][ $j ] = 1;
else if ( $str [ $i ] == $str [ $j ])
return $dp [ $i ][ $j ] = countPS( $i + 1, $j ) +
countPS( $i , $j - 1) + 1;
else
return $dp [ $i ][ $j ] = countPS( $i + 1, $j ) +
countPS( $i , $j - 1) -
countPS( $i + 1, $j - 1);
}
echo "Total palindromic subsequence are : " .
countPS(0, $n - 1);
?>
|
Output
Total palindromic subsequence are : 6
Time Complexity : O(N2),
Auxiliary Space: O(N2)
This article is contributed by Aarti_Rathi and Nishant_sing.
Share your thoughts in the comments
Please Login to comment...