# Find the longest subsequence of a string that is a substring of another string

• Difficulty Level : Hard
• Last Updated : 06 Jul, 2021

Given two strings X and Y consisting of N and M characters, the task is to find the longest subsequence of a string X which is a substring of the string Y.

Examples:

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.  To complete your preparation from learning a language to DS Algo and many more,  please refer Complete Interview Preparation Course.

In case you wish to attend live classes with experts, please refer DSA Live Classes for Working Professionals and Competitive Programming Live for Students.

Input: X = “ABCD”, Y = “ACDBDCD”
Output: ACD
Explanation:
“ACD” is longest subsequence of X which is substring of Y.

Input: X = A, Y = A
Output: A

Naive Approach: The simplest approach to solve the given problem is to find all the subsequences of the given string X and print that subsequence among all the generated subsequences which is of maximum length and is a substring of Y.

Time Complexity: O(N*M*2N)
Auxiliary Space: O(N)

Efficient Approach: The above approach can also be optimized by using Dynamic Programming. The idea is to create a 2D array, dp[][] of dimensions (N + 1)*(M + 1) and the state dp[i][j] is maximum length of subsequence of X[0, i] which is substring of Y[0, j]. Follow the steps below to solve the problem:

• Create a 2D array, dp[][] of size N+1 rows and M+1 columns.
• Initialize the first row and the first column of the matrix with 0.
• Fill all the remaining rows as follows:
• If the value of X[i – 1] is equal to the value of Y[j – 1], then update the value of dp[i][j] to (1 + dp[i – 1][j – 1]).
• Otherwise, update the value of dp[i][j] to dp[i – 1][j].
• Store the maximum length of the required sequence in a variable len by iterating the last row in the matrix and store the row and column index of the maximum cell value in variables i and j respectively.
• Create a variable, say res to store the resultant string and backtrack from the maximum cell value.
• Iterate until the value of len is greater than 0, and perform the following steps:
• If the value of X[i – 1] is equal to the value of Y[j – 1], then append X[i – 1] to res and decrement the value of len, i and j by 1.
• Otherwise, decrement the value of i by 1.
• After completing the above steps, print the string res as the result.

Below is the implementation of the above approach:

## C++

 `// C++ program for the above approach``#include ``using` `namespace` `std;` `// Function to find the longest``// subsequence that matches with``// the substring of other string``string longestSubsequence(string X, string Y)``{``    ` `    ``// Stores the lengths of strings``    ``// X and Y``    ``int` `n = X.size();``    ``int` `m = Y.size();` `    ``// Create a matrix``    ``vector> mat(n + 1, vector<``int``>(m + 1));``    ` `    ``// Initialize the matrix``    ``for``(``int` `i = 0; i < n + 1; i++)``    ``{``        ``for``(``int` `j = 0; j < m + 1; j++)``        ``{``            ``if` `(i == 0 || j == 0)``                ``mat[i][j] = 0;``        ``}``    ``}` `    ``// Fill all the remaining rows``    ``for``(``int` `i = 1; i < n + 1; i++)``    ``{``        ``for``(``int` `j = 1; j < m + 1; j++)``        ``{``            ` `            ``// If the characters are equal``            ``if` `(X[i - 1] == Y[j - 1])``            ``{``                ``mat[i][j] = 1 + mat[i - 1][j - 1];``            ``}` `            ``// If not equal, then``            ``// just move to next``            ``// in subsequence string``            ``else``            ``{``                ``mat[i][j] = mat[i - 1][j];``            ``}``        ``}``    ``}` `    ``// Find maximum length of the``    ``// longest subsequence matching``    ``// substring of other string``    ``int` `len = 0, col = 0;` `    ``// Iterate through the last``    ``// row of matrix``    ``for``(``int` `i = 0; i < m + 1; i++)``    ``{``        ``if` `(mat[n][i] > len)``        ``{``            ``len = mat[n][i];``            ``col = i;``        ``}``    ``}` `    ``// Store the required string``    ``string res = ``""``;``    ``int` `i = n;``    ``int` `j = col;` `    ``// Backtrack from the cell``    ``while` `(len > 0)``    ``{``        ` `        ``// If equal, then add the``        ``// character to res string``        ``if` `(X[i - 1] == Y[j - 1])``        ``{``            ``res = X[i - 1] + res;``            ``i--;``            ``j--;``            ``len--;``        ``}``        ``else``        ``{``            ``i--;``        ``}``    ``}` `    ``// Return the required string``    ``return` `res;``}` `// Driver code``int` `main()``{``    ``string X = ``"ABCD"``;``    ``string Y = ``"ACDBDCD"``;``    ` `    ``cout << (longestSubsequence(X, Y));``    ` `    ``return` `0;``}` `// This code is contributed by mohit kumar 29`

## Java

 `// Java program for the above approach` `class` `GFG {` `    ``// Function to find the longest``    ``// subsequence that matches with``    ``// the substring of other string``    ``public` `static` `String longestSubsequence(``        ``String X, String Y)``    ``{` `        ``// Stores the lengths of strings``        ``// X and Y``        ``int` `n = X.length();``        ``int` `m = Y.length();` `        ``// Create a matrix``        ``int``[][] mat = ``new` `int``[n + ``1``][m + ``1``];` `        ``// Initialize the matrix``        ``for` `(``int` `i = ``0``; i < n + ``1``; i++) {``            ``for` `(``int` `j = ``0``; j < m + ``1``; j++) {``                ``if` `(i == ``0` `|| j == ``0``)``                    ``mat[i][j] = ``0``;``            ``}``        ``}` `        ``// Fill all the remaining rows``        ``for` `(``int` `i = ``1``;``             ``i < n + ``1``; i++) {` `            ``for` `(``int` `j = ``1``;``                 ``j < m + ``1``; j++) {` `                ``// If the characters are equal``                ``if` `(X.charAt(i - ``1``)``                    ``== Y.charAt(j - ``1``)) {``                    ``mat[i][j] = ``1``                                ``+ mat[i - ``1``][j - ``1``];``                ``}` `                ``// If not equal, then``                ``// just move to next``                ``// in subsequence string``                ``else` `{``                    ``mat[i][j] = mat[i - ``1``][j];``                ``}``            ``}``        ``}` `        ``// Find maximum length of the``        ``// longest subsequence matching``        ``// substring of other string``        ``int` `len = ``0``, col = ``0``;` `        ``// Iterate through the last``        ``// row of matrix``        ``for` `(``int` `i = ``0``; i < m + ``1``; i++) {` `            ``if` `(mat[n][i] > len) {``                ``len = mat[n][i];``                ``col = i;``            ``}``        ``}` `        ``// Store the required string``        ``String res = ``""``;``        ``int` `i = n;``        ``int` `j = col;` `        ``// Backtrack from the cell``        ``while` `(len > ``0``) {` `            ``// If equal, then add the``            ``// character to res string``            ``if` `(X.charAt(i - ``1``)``                ``== Y.charAt(j - ``1``)) {` `                ``res = X.charAt(i - ``1``) + res;``                ``i--;``                ``j--;``                ``len--;``            ``}``            ``else` `{``                ``i--;``            ``}``        ``}` `        ``// Return the required string``        ``return` `res;``    ``}` `    ``// Driver Code``    ``public` `static` `void` `main(String args[])``    ``{``        ``String X = ``"ABCD"``;``        ``String Y = ``"ACDBDCD"``;``        ``System.out.println(``            ``longestSubsequence(X, Y));``    ``}``}`

## Python3

 `# Python3 program for the above approach` `# Function to find the longest``# subsequence that matches with``# the substring of other string``def` `longestSubsequence(X, Y):``    ` `    ``# Stores the lengths of strings``    ``# X and Y``    ``n ``=` `len``(X)``    ``m ``=` `len``(Y)` `    ``# Create a matrix``    ``mat ``=` `[[``0` `for` `i ``in` `range``(m ``+` `1``)]``              ``for` `j ``in` `range``(n ``+` `1``)]``              ` `    ``# Initialize the matrix``    ``for` `i ``in` `range``(``0``, n ``+` `1``):``        ``for` `j ``in` `range``(``0``, m ``+` `1``):``            ``if` `(i ``=``=` `0` `or` `j ``=``=` `0``):``                ``mat[i][j] ``=` `0` `    ``# Fill all the remaining rows``    ``for` `i ``in` `range``(``1``, n ``+` `1``):``        ``for` `j ``in` `range``(``1``, m ``+` `1``):``            ` `            ``# If the characters are equal``            ``if` `(X[i ``-` `1``] ``=``=` `Y[j ``-` `1``]):``                ``mat[i][j] ``=` `1` `+` `mat[i ``-` `1``][j ``-` `1``]``                ` `            ``# If not equal, then``            ``# just move to next``            ``# in subsequence string``            ``else``:``                ``mat[i][j] ``=` `mat[i ``-` `1``][j]` `    ``# Find maximum length of the``    ``# longest subsequence matching``    ``# substring of other string``    ``len1 ``=` `0``    ``col ``=` `0``    ` `    ``# Iterate through the last``    ``# row of matrix``    ``for` `i ``in` `range``(``0``, m ``+` `1``):``        ``if` `(mat[n][i] > len1):``            ``len1 ``=` `mat[n][i]``            ``col ``=` `i` `    ``# Store the required string``    ``res ``=` `""``    ``i ``=` `n``    ``j ``=` `col``    ` `    ``# Backtrack from the cell``    ``while` `(len1 > ``0``):` `        ``# If equal, then add the``        ``# character to res string``        ``if` `(X[i ``-` `1``] ``=``=` `Y[j ``-` `1``]):``            ``res ``=` `X[i ``-` `1``] ``+` `res``            ``i ``-``=` `1``            ``j ``-``=` `1``            ``len1 ``-``=` `1``        ``else``:``            ``i ``-``=` `1` `    ``# Return the required string``    ``return` `res` `# Driver code``X ``=` `"ABCD"``Y ``=` `"ACDBDCD"` `print``(longestSubsequence(X, Y))` `# This code is contributed by amreshkumar3`

## C#

 `// C# program for the above approach``using` `System;``using` `System.Collections.Generic;` `class` `GFG{` `// Function to find the longest``// subsequence that matches with``// the substring of other string``static` `string` `longestSubsequence(``string` `X, ``string` `Y)``{``    ``int` `i, j;``    ` `    ``// Stores the lengths of strings``    ``// X and Y``    ``int` `n = X.Length;``    ``int` `m = Y.Length;` `    ``// Create a matrix``    ``int` `[,]mat = ``new` `int``[n + 1, m + 1];` `    ``// Initialize the matrix``    ``for``(i = 0; i < n + 1; i++)``    ``{``        ``for``(j = 0; j < m + 1; j++)``        ``{``            ``if` `(i == 0 || j == 0)``                ``mat[i,j] = 0;``        ``}``    ``}` `    ``// Fill all the remaining rows``    ``for``(i = 1; i < n + 1; i++)``    ``{``        ``for``(j = 1; j < m + 1; j++)``        ``{``            ` `            ``// If the characters are equal``            ``if` `(X[i - 1] == Y[j - 1])``            ``{``                ``mat[i, j] = 1 + mat[i - 1, j - 1];``            ``}` `            ``// If not equal, then``            ``// just move to next``            ``// in subsequence string``            ``else``            ``{``                ``mat[i, j] = mat[i - 1, j];``            ``}``        ``}``    ``}` `    ``// Find maximum length of the``    ``// longest subsequence matching``    ``// substring of other string``    ``int` `len = 0, col = 0;` `    ``// Iterate through the last``    ``// row of matrix``    ``for``(i = 0; i < m + 1; i++)``    ``{``        ``if` `(mat[n,i] > len)``        ``{``            ``len = mat[n,i];``            ``col = i;``        ``}``    ``}` `    ``// Store the required string``    ``string` `res = ``""``;``    ``i = n;``    ``j = col;` `    ``// Backtrack from the cell``    ``while` `(len > 0)``    ``{``        ` `        ``// If equal, then add the``        ``// character to res string``        ``if` `(X[i - 1] == Y[j - 1])``        ``{``            ``res = X[i - 1] + res;``            ``i--;``            ``j--;``            ``len--;``        ``}``        ``else``        ``{``            ``i--;``        ``}``    ``}` `    ``// Return the required string``    ``return` `res;``}` `// Driver Code``public` `static` `void` `Main()``{``    ``string` `X = ``"ABCD"``;``    ``string` `Y = ``"ACDBDCD"``;``    ` `    ``Console.Write(longestSubsequence(X, Y));``}``}` `// This code is contributed by bgangwar59`

## Javascript

 ``
Output:
`ACD`

Time Complexity: O(N*M)
Auxiliary Space: O(N*M)

My Personal Notes arrow_drop_up