Minimum number of Appends needed to make a string palindrome
Last Updated :
16 Nov, 2024
Given a string s, the task is to find the minimum characters to be appended (insertion at the end) to make a string palindrome.
Examples:
Input: s = "abede"
Output : 2
Explanation: We can make string palindrome as "abedeba" by adding ba at the end of the string.
Input: s = "aabb"
Output : 2
Explanation: We can make string palindrome as"aabbaa" by adding aa at the end of the string.
Check palindrome every time - O(n^2) Time and O(n) Space
The solution involves progressively removing characters from the beginning of the string, one by one, until the string becomes a palindrome. The answer will be total number of character removed.
For example, consider the string s = "abede". We first check if the entire string is a palindrome, which it isn't. Next, we remove the first character, resulting in the string "bede". We check again, but it's still not a palindrome. We then remove another character from the start, leaving "ede". This time, the string is a palindrome. Therefore, the output is 2, representing the number of characters removed from the beginning to achieve a palindrome.
C++
// C++ code to find minimum number
// of appends to make string Palindrome
#include <iostream>
using namespace std;
// Function to check if a given string is a palindrome
bool isPalindrome(string s) {
int left = 0, right = s.length() - 1;
while (left < right) {
if (s[left] != s[right]) return false;
left++;
right--;
}
return true;
}
// Function to find the minimum number of
// characters to remove from the beginning
int noOfAppends(string& s) {
int n = s.length();
// Remove characters from the start until
// the string becomes a palindrome
for (int i = 0; i < n; i++) {
if (isPalindrome(s.substr(i))) {
// Return the number of characters removed
return i;
}
}
// If no palindrome is found, remove
// all but one character
return n - 1;
}
int main() {
string s = "abede";
int result = noOfAppends(s);
cout << result << endl;
return 0;
}
Java
// Java code to find minimum number
// of appends to make string Palindrome
import java.util.*;
class GfG {
// Function to check if a given string is a palindrome
static boolean isPalindrome(String s) {
int left = 0, right = s.length() - 1;
while (left < right) {
if (s.charAt(left) != s.charAt(right)) return false;
left++;
right--;
}
return true;
}
// Function to find the minimum number of
// characters to remove from the beginning
static int noOfAppends(String s) {
int n = s.length();
// Remove characters from the start until
// the string becomes a palindrome
for (int i = 0; i < n; i++) {
if (isPalindrome(s.substring(i))) {
// Return the number of characters removed
return i;
}
}
// If no palindrome is found, remove
// all but one character
return n - 1;
}
public static void main(String[] args) {
String s = "abede";
int result = noOfAppends(s);
System.out.println(result);
}
}
Python
# Python code to find minimum number
# of appends to make string Palindrome
# Function to check if a given string is a palindrome
def is_palindrome(s):
left, right = 0, len(s) - 1
while left < right:
if s[left] != s[right]:
return False
left += 1
right -= 1
return True
# Function to find the minimum number of
# characters to remove from the beginning
def no_of_appends(s):
n = len(s)
# Remove characters from the start until
# the string becomes a palindrome
for i in range(n):
if is_palindrome(s[i:]):
# Return the number of characters
# removed
return i
# If no palindrome is found, remove
# all but one character
return n - 1
if __name__ == "__main__":
s = "abede"
result = no_of_appends(s)
print(result)
C#
// C# code to find minimum number
// of appends to make string Palindrome
using System;
class GfG {
// Function to check if a given string
// is a palindrome
static bool IsPalindrome(string s) {
int left = 0, right = s.Length - 1;
while (left < right) {
if (s[left] != s[right]) return false;
left++;
right--;
}
return true;
}
// Function to find the minimum number of
// characters to remove from the beginning
static int NoOfAppends(string s) {
int n = s.Length;
// Remove characters from the start until
// the string becomes a palindrome
for (int i = 0; i < n; i++) {
if (IsPalindrome(s.Substring(i))) {
// Return the number of characters
// removed
return i;
}
}
// If no palindrome is found, remove all but
// one character
return n - 1;
}
static void Main(string[] args) {
string s = "abede";
int result = NoOfAppends(s);
Console.WriteLine(result);
}
}
JavaScript
// JavaScript code to find minimum number
// of appends to make string Palindrome
// Function to check if a given string is a palindrome
function isPalindrome(s) {
let left = 0, right = s.length - 1;
while (left < right) {
if (s[left] !== s[right]) return false;
left++;
right--;
}
return true;
}
// Function to find the minimum number of
// characters to remove from the beginning
function noOfAppends(s) {
let n = s.length;
// Remove characters from the start until
// the string becomes a palindrome
for (let i = 0; i < n; i++) {
if (isPalindrome(s.substring(i))) {
// Return the number of
// characters removed
return i;
}
}
// If no palindrome is found, remove
// all but one character
return n - 1;
}
const s = "abede";
const result = noOfAppends(s);
console.log(result);
Using Knuth Morris Pratt Algorithm - O(n) Time and O(n) Space
The basic idea behind the approach is that we calculate the largest substring from the end and the length of the string minus this value is the minimum number of appends. The logic is intuitive, we need not append the palindrome and only those which do not form the palindrome. To find this largest palindrome from the end, we reverse the string, calculate the DFA.
The DFA (Deterministic Finite Automaton) mentioned in the context of the Knuth Morris Pratt Algorithm is a concept used to help find the longest prefix of a string that is also a suffix and reverse the string again(thus gaining back the original string) and find the final state, which represents the number of matches of the string with the revered string and hence we get the largest substring that is a palindrome from the end.
C++
// CPP program for the given approach
// using 2D vector for DFA
#include <bits/stdc++.h>
using namespace std;
// Function to build the DFA and precompute the state
vector<vector<int>> buildDFA(string& s) {
int n = s.length();
// Number of possible characters (ASCII range)
int c = 256;
// Initialize 2D vector with zeros
vector<vector<int>> dfa(n, vector<int>(c, 0));
int x = 0;
dfa[0][s[0]] = 1;
// Build the DFA for the given string
for (int i = 1; i < n; i++) {
for (int j = 0; j < c; j++) {
dfa[i][j] = dfa[x][j];
}
dfa[i][s[i]] = i + 1;
x = dfa[x][s[i]];
}
return dfa;
}
// Function to find the longest overlap
// between the string and its reverse
int longestOverlap(vector<vector<int>>& dfa, string& query) {
int ql = query.length();
int state = 0;
// Traverse through the query to
// find the longest overlap
for (int i = 0; i < ql; i++) {
state = dfa[state][query[i]];
}
return state;
}
// Function to find the minimum
// number of characters to append
int minAppends(string s) {
// Reverse the string
string reversedS = s;
reverse(reversedS.begin(), reversedS.end());
// Build the DFA for the reversed string
vector<vector<int>> dfa = buildDFA(reversedS);
// Get the longest overlap with the original string
int longestOverlapLength = longestOverlap(dfa, s);
// Minimum characters to append
// to make the string a palindrome
return s.length() - longestOverlapLength;
}
int main() {
string s = "abede";
cout << minAppends(s) << endl;
return 0;
}
Java
// Java program for the given approach
// using 2D array for DFA
import java.util.*;
class GfG {
// Function to build the DFA and precompute the state
static int[][] buildDFA(String s) {
int n = s.length();
// Number of possible characters (ASCII range)
int c = 256;
// Initialize 2D array with zeros
int[][] dfa = new int[n][c];
int x = 0;
dfa[0][s.charAt(0)] = 1;
// Build the DFA for the given string
for (int i = 1; i < n; i++) {
for (int j = 0; j < c; j++) {
dfa[i][j] = dfa[x][j];
}
dfa[i][s.charAt(i)] = i + 1;
x = dfa[x][s.charAt(i)];
}
return dfa;
}
// Function to find the longest overlap
// between the string and its reverse
static int longestOverlap(int[][] dfa, String query) {
int ql = query.length();
int state = 0;
// Traverse through the query to
// find the longest overlap
for (int i = 0; i < ql; i++) {
state = dfa[state][query.charAt(i)];
}
return state;
}
// Function to find the minimum
// number of characters to append
static int minAppends(String s) {
// Reverse the string
String reversedS = new StringBuilder(s).reverse().toString();
// Build the DFA for the reversed string
int[][] dfa = buildDFA(reversedS);
// Get the longest overlap with the original string
int longestOverlapLength = longestOverlap(dfa, s);
// Minimum characters to append
// to make the string a palindrome
return s.length() - longestOverlapLength;
}
public static void main(String[] args) {
String s = "abede";
System.out.println(minAppends(s));
}
}
Python
# Python program for the given approach
# using 2D list for DFA
# Function to build the DFA and precompute the state
def buildDFA(s):
n = len(s)
# Number of possible characters (ASCII range)
c = 256
# Initialize 2D list with zeros
dfa = [[0] * c for _ in range(n)]
x = 0
dfa[0][ord(s[0])] = 1
# Build the DFA for the given string
for i in range(1, n):
for j in range(c):
dfa[i][j] = dfa[x][j]
dfa[i][ord(s[i])] = i + 1
x = dfa[x][ord(s[i])]
return dfa
# Function to find the longest overlap
# between the string and its reverse
def longestOverlap(dfa, query):
ql = len(query)
state = 0
# Traverse through the query to
# find the longest overlap
for i in range(ql):
state = dfa[state][ord(query[i])]
return state
# Function to find the minimum
# number of characters to append
def minAppends(s):
# Reverse the string
reversedS = s[::-1]
# Build the DFA for the reversed string
dfa = buildDFA(reversedS)
# Get the longest overlap with the
# original string
longestOverlapLength = longestOverlap(dfa, s)
# Minimum characters to append
# to make the string a palindrome
return len(s) - longestOverlapLength
if __name__ == "__main__":
s = "abede"
print(minAppends(s))
C#
// C# program for the given approach
// using 2D array for DFA
using System;
class GfG {
// Function to build the DFA and precompute the state
static int[,] buildDFA(string s) {
int n = s.Length;
// Number of possible characters
// (ASCII range)
int c = 256;
// Initialize 2D array with zeros
int[,] dfa = new int[n, c];
int x = 0;
dfa[0, s[0]] = 1;
// Build the DFA for the given string
for (int i = 1; i < n; i++) {
for (int j = 0; j < c; j++) {
dfa[i, j] = dfa[x, j];
}
dfa[i, s[i]] = i + 1;
x = dfa[x, s[i]];
}
return dfa;
}
// Function to find the longest overlap
// between the string and its reverse
static int longestOverlap(int[,] dfa, string query) {
int ql = query.Length;
int state = 0;
// Traverse through the query to
// find the longest overlap
for (int i = 0; i < ql; i++) {
state = dfa[state, query[i]];
}
return state;
}
// Function to find the minimum
// number of characters to append
static int minAppends(string s) {
// Reverse the string using char array
char[] reversedArray = s.ToCharArray();
Array.Reverse(reversedArray);
string reversedS = new string(reversedArray);
// Build the DFA for the reversed string
int[,] dfa = buildDFA(reversedS);
// Get the longest overlap with the original string
int longestOverlapLength = longestOverlap(dfa, s);
// Minimum characters to append
// to make the string a palindrome
return s.Length - longestOverlapLength;
}
static void Main() {
string s = "abede";
Console.WriteLine(minAppends(s));
}
}
JavaScript
// JavaScript program for the given approach
// using 2D array for DFA
// Function to build the DFA and precompute the state
function buildDFA(s) {
let n = s.length;
// Number of possible characters
// (ASCII range)
let c = 256;
// Initialize 2D array with zeros
let dfa = Array.from({ length: n }, () => Array(c).fill(0));
let x = 0;
dfa[0][s.charCodeAt(0)] = 1;
// Build the DFA for the given string
for (let i = 1; i < n; i++) {
for (let j = 0; j < c; j++) {
dfa[i][j] = dfa[x][j];
}
dfa[i][s.charCodeAt(i)] = i + 1;
x = dfa[x][s.charCodeAt(i)];
}
return dfa;
}
// Function to find the longest overlap
// between the string and its reverse
function longestOverlap(dfa, query) {
let ql = query.length;
let state = 0;
// Traverse through the query to
// find the longest overlap
for (let i = 0; i < ql; i++) {
state = dfa[state][query.charCodeAt(i)];
}
return state;
}
// Function to find the minimum
// number of characters to append
function minAppends(s) {
// Reverse the string
let reversedS = s.split('').reverse().join('');
// Build the DFA for the reversed string
let dfa = buildDFA(reversedS);
// Get the longest overlap with the original string
let longestOverlapLength = longestOverlap(dfa, s);
// Minimum characters to append
// to make the string a palindrome
return s.length - longestOverlapLength;
}
let s = "abede";
console.log(minAppends(s));
Related Article :
Similar Reads
Minimum number of deletions to make a string palindrome | Set 2 Given a string A, compute the minimum number of characters you need to delete to make resulting string a palindrome. Examples: Input : baca Output : 1 Input : geek Output : 2 We have discussed one approach in below post. Minimum number of deletions to make a string palindrome Below approach will use
9 min read
Minimum Deletions to Make a String Palindrome Given a string s of length n, the task is to remove or delete the minimum number of characters from the string so that the resultant string is a palindrome. Note: The order of characters should be maintained. Examples : Input : s = "aebcbda"Output : 2Explanation: Remove characters 'e' and 'd'. Resul
15+ min read
Minimum number of characters to be replaced to make a given string Palindrome Given string str, the task is to find the minimum number of characters to be replaced to make a given string palindrome. Replacing a character means replacing it with any single character in the same position. We are not allowed to remove or add any characters. If there are multiple answers, print t
5 min read
Form minimum number of Palindromic Strings from a given string Given a string S, the task is to divide the characters of S to form minimum number of palindromic strings. Note: There can be multiple correct answers. Examples: Input: S = "geeksforgeeks"Output: {eegksrskgee, o, f} Explanation: There should be at least 3 strings "eegksrskgee", "o", "f". All 3 forme
12 min read
Minimum number of palindromes required to express N as a sum | Set 2 Given a number N, we have to find the minimum number of palindromes required to express N as a sum of them. Examples: Input : N = 11 Output : 1 Explanation: 11 is itself a palindrome.Input : N = 65 Output : 3 Explanation: 65 can be expressed as a sum of three palindromes (55, 9, 1).In the previous p
11 min read