Open In App

JavaScript Program for Longest Common Subsequence

Last Updated : 10 Oct, 2023
Improve
Improve
Like Article
Like
Save
Share
Report

The longest common subsequence (LCS) is defined as the longest subsequence which is common in all given input sequences. In this article, we are given two strings, String1 and String2, the task is to find the longest common subsequence in both of the strings. A subsequence of a string can be achieved by deleting any number of elements from the string.

Example:

Input: 'ABCD' , 'AEBECED'
Output: 'ABCD'
Explanation:  As 'ABCD' is common in both of the string and it is the longest string.

Approach 1: Brute force Method

In this approach, the idea is to generate all the sub-sequences and then to find the longest common subsequence in them. The problem with this approach is having very high time complexity. We need (2 to power n) time complexity to generate all the subsequences of a single string.

Example: This example shows the use of the above-explained approach.

Javascript




function subseqProd(str) {
    const subsequences = [];
  
    function backtrack(subsequence, index) {
        if (index === str.length) {
            subsequences.push(subsequence);
            return;
        }
        backtrack(subsequence + str[index], index + 1);
        backtrack(subsequence, index + 1);
    }
    backtrack('', 0);
    return subsequences;
}
  
function findLCS(str1, str2) {
    const subseq1 = subseqProd(str1);
    const subSeq2 = subseqProd(str2);
    let lcs = '';
  
    for (const sub1 of subseq1) {
        for (const sub2 of subSeq2) {
            if (sub1 === sub2 && sub1.length > lcs.length) {
                lcs = sub1;
            }
        }
    }
  
    return lcs;
}
  
const str1 = "ABCDF";
const str2 = "ACDF";
const lcsSeq = findLCS(str1, str2);
console.log("Longest Common Subsequence: " + lcsSeq);


Output

Longest Common Subsequence: ACDF

Time Complexity: O(2^n*2^m), where n and m are length of string.

Space Complexity: O(2^n)

Approach 2: Using DP array

  • In this approach, We will use this DP array to get the longest common subsequence in both strings.
  • By keeping track of a pointer , We will start to fill the string `str` from the end .
  • We will start by positioning from the rightmost place in the DP array, which is denoted by `(i, j)` with `i = n` & `j = m`. At every cell, we will check whether `S1[i-1]` matches `S2[j-1]` or not. If they matches , it shows that this character can be included to the longest common substring.
  • If we found the previous case we will add the character to end of the `str`. Then, we will move to diagonally top-left cell (↖) by decrementing both of `i` & `j`.
  • However, it is obvious that if the characters do not match, it tells that the character is not the part of the longest common subsequence.
  • In this case, we look whether value in the cell to the left (←) or above (↑) is greater. And move to the cell which has the greater value.
  • We will keep on repeating this process until `i` and `j` are greater than 0. and if they become less than zero, we will exit the loop

Example: This example shows the use of the above-explained approach.

Javascript




function findLCS(s1, s2) {
    const n = s1.length;
    const m = s2.length;
  
    const dp = 
        new Array(n + 1).fill(null).map(() => 
            new Array(m + 1).fill(0));
    for (let i = 0; i <= n; i++) {
        dp[i][0] = 0;
    }
    for (let i = 0; i <= m; i++) {
        dp[0][i] = 0;
    }
  
    for (let ind1 = 1; ind1 <= n; ind1++) {
        for (let ind2 = 1; ind2 <= m; ind2++) {
            if (s1[ind1 - 1] === s2[ind2 - 1]) {
                dp[ind1][ind2] = 1 + dp[ind1 - 1][ind2 - 1];
            } else {
                dp[ind1][ind2] = 
                    Math.max(dp[ind1 - 1][ind2], 
                        dp[ind1][ind2 - 1]);
            }
        }
    }
  
    const len = dp[n][m];
    let i = n;
    let j = m;
    let index = len - 1;
    let str = "";
  
    for (let k = 0; k < len; k++) {
        str += "$"; // Dummy string
    }
  
    while (i > 0 && j > 0) {
        if (s1[i - 1] === s2[j - 1]) {
            str = 
                str.slice(0, index) + s1[i - 1] + 
                    str.slice(index + 1);
            index--;
            i--;
            j--;
        } else if (s1[i - 1] > s2[j - 1]) {
            i--;
        } else {
            j--;
        }
    }
  
    return str;
}
  
const s1 = "abcdek";
const s2 = "bdgek";
console.log(
    "The Longest Common Subsequence is " + findLCS(s1, s2));


Output

The Longest Common Subsequence is bdek

Space Complexity: O(N*M)

Time Complexity: O(N*M)



Like Article
Suggest improvement
Share your thoughts in the comments

Similar Reads