Count of unique palindromic strings of length X from given string

Given a string s and an integer X, our task is to find the number of distinct palindromic strings of length X from the given string.

Examples:

Input: s = “aaa”, X = 2
Output: 1
Explanation:
Here all the characters of the string is the same so we can only make a one different string {aa} of length 2.

Input: s = “aabaabbc”, X = 3
Output: 6
Explanation:
To make a palindromic string of length 3 we have 6 possible strings aaa, aba, aca, bab, bcb, bbb.

Naive Approach: The naive method is to generate all the possible subsequence of length X, then check if that subsequence forms a palindrome or not.



Time Complexity: O(2N)
Auxiliary Space: O(X)

Efficient Approach: The idea is to find the frequency of all the characters of the string. Count the different numbers of the characters we can put at the particular position and decrease the number of count by 2 because for palindromic string the position (i) and (X – i) will be the same. If the length of X is odd then we have to put the only single char at that position X/2.

Below is the implementation of the above approach:

CPP

filter_none

edit
close

play_arrow

link
brightness_4
code

// C++ implementation to count different
// palindromic string of length X
// from the given string S
  
#include <bits/stdc++.h>
using namespace std;
  
// Function to count different
// palindromic string of length X
// from the given string S
long long findways(string s, int x)
{
    // Base case
    if (x > (int)s.length())
        return 0;
  
    long long int n = (int)s.length();
  
    // Create the frequency array
    int freq[26];
  
    // Intitalise frequency array with 0
    memset(freq, 0, sizeof freq);
  
    // Count the frequency in the string
    for (int i = 0; i < n; ++i)
        freq[s[i] - 'a']++;
  
    multiset<int> se;
  
    for (int i = 0; i < 26; ++i)
        if (freq[i] > 0)
            // Store frequency of the char
            se.insert(freq[i]);
  
    long long ans = 1;
  
    for (int i = 0; i < x / 2; ++i) {
        long long int count = 0;
        for (auto u : se) {
            // check the frequency which
            // is greater than zero
            if (u >= 2)
  
                // No. of different char we can
                // put at the position of
                // the i and x - i
                count++;
        }
  
        if (count == 0)
            return 0;
  
        else
            ans = ans * count;
  
        // Iterator pointing to the
        // last element of the set
        auto p = se.end();
        p--;
        int val = *p;
        se.erase(p);
        if (val > 2)
            // decrease the value of the char
            // we put on the position i and n - i
            se.insert(val - 2);
    }
  
    if (x % 2 != 0) {
        long long int count = 0;
        for (auto u : se)
            // different no of char we can
            // put at the position x/2
            if (u > 0)
                count++;
  
        ans = ans * count;
    }
  
    // Return total no of
    // different string
    return ans;
}
  
// Driver code
int main()
{
    string s = "aaa";
    int x = 2;
    cout << findways(s, x);
  
    return 0;
}

chevron_right


Output:

1

Time Complexity: O(N + 26 * X)

Attention reader! Don’t stop learning now. Get hold of all the important DSA concepts with the DSA Self Paced Course at a student-friendly price and become industry ready.




My Personal Notes arrow_drop_up

Check out this Author's contributed articles.

If you like GeeksforGeeks and would like to contribute, you can also write an article using contribute.geeksforgeeks.org or mail your article to contribute@geeksforgeeks.org. See your article appearing on the GeeksforGeeks main page and help other Geeks.

Please Improve this article if you find anything incorrect by clicking on the "Improve Article" button below.