Transform string A into B by deleting characters from ends and reinserting at any position


Anagram of a string means a string contains exact same characters as another string with the order of characters may vary from the original string, so we called that both strings are anagram of each other. Here we have given the two strings first and second which are anagrams of each other. And our task is to minimize the count of operations to make the first string as second string.

An operation is that we can delete an character from the begin or end of an first string and reinserting at any position.

Sample Example

Input 

First: "hello",
Second: "ohlle"

Output 

3

Explanation

Here we perform minimum operations to make first string as second string −

  • Remove last character from the first string and put in the index 0, "ohell"

  • Again, remove last character from updated first string and put at the index 2, "ohlel"

  • Again, remove last character from updated first string and put at the index 3, "ohlle"

Input 

First: "world",
Second: "world"

Output 

0

Explanation

As here both first and second string are equal to each other.

Dynamic Approach Using concept of LCS

We are going to solve this problem using the concept of Longest Common subsequence (LCS), a very popular problem of the dynamic programming.

Example

Let's see the code below for better understanding of above approach.

#include <bits/stdc++.h>
using namespace std;
 
// Create a function to minimize the count of operations
int minimizeCountOfOperations(string First, string Second){
   // Create an 2d matrix to maintain the longest continous length of first string that is part of the string second subsequence
   int t[1001][1001];
   // Variable maxlen store the maximum value of 2d matrix d 
   int maxlen = 0;
   for (int i = 0; i <= First.size(); i++) {
      for (int j = 0; j <= Second.size(); j++) {
         t[i][j] = 0;
         if (i && j) {             
            // if the sufix of first string is part of both second string upto j and also j-1 
            t[i][j] = t[i][j - 1];                
            // last charcter of both the string equal, then suffix of first string upto i-1 is part of second string upto j-1
            if (First[i - 1] == Second[j - 1]) {
               t[i][j] = max(t[i][j],1 + t[i - 1][j - 1]);
               maxlen = max(maxlen, t[i][j]);
            }
         }
      }
   } 
   return First.size() - maxlen;
}
int main(){
   string First = "hello";
   string Second = "ohlle";    
   int minCount = minimizeCountOfOperations(First, Second);
   cout << "Count of Minimum Operation needed to transform first string into second string is: " << minCount;
   return 0;
}

Output

Count of Minimum Operation needed to transform first string into second string is: 3

Time and Space Complexity

The time complexity of the above code is O(N^2).

The space complexity of the above code is O(N^2), as we are using a 2D matrix to store the results.

Here N is the size of the given string.

Efficient Version of the above approach by using Array instead of 2d matrix

This is the same approach as above here the only difference is that we are using a linear array instead of 2D matrix which will provide us better space complexity. This will reduce the space complexity as we are going to prune the results which were not required and replace it with the new calculated values.

Example

Let's see the code below for a better understanding of the above approach.

#include <bits/stdc++.h>
using namespace std;
 
// Create a function to minimize the count of operations
int minimizeCountOfOperations(string First, string Second){
   // Create an array to maintain the longest continous length of first string that is part of the string second subsequence and assign it 0
   int t[1001] = {0}; 
   // Variable maxlen store the maximum value of 2d matrix d
   int maxlen = 0; 
   for (int i = 1; i <= First.size(); i++) {
      int previousVal = 0;
      for (int j = 1; j <= Second.size(); j++) {            
         int store = t[j];
         t[j] =t[j-1];            
         if(First[i - 1] == Second[j - 1])
            t[j] = max(t[j], previousVal+1);
         else 
            t[j] = max(t[j], 0);               
            previousVal = store;
         maxlen = max(maxlen, t[j]);
      }
   }    
   return First.size() - maxlen;
}
int main(){
   string First = "hello";
   string Second = "ohlle";
   int minCount = minimizeCountOfOperations(First, Second);
   cout << "Count of Minimum Operation needed to transform first string into second string is: " << minCount;
   return 0;
}

Output

Count of Minimum Operation needed to transform first string into second string is: 3

Time and Space Complexity

The time complexity of the above code is O(N^2).

The space complexity of the above code is O(N), as we are using the array.

Here N is the size of the given string.

Conclusion

In this tutorial, we have implemented a C++ program to Transform string A into B by deleting characters from ends and reinserting them at any position. We have implemented two approaches to solve this problem. Approaches are Dynamic Approach with a 2d matrix using the concept of LCS and the second approach is an efficient version of the first approach using an array instead of a 2d matrix.

Updated on: 24-Aug-2023

42 Views

Kickstart Your Career

Get certified by completing the course

Get Started
Advertisements