Close Menu
    Code and Debug
    • Home
    • Our Courses
    • Blog
    • About Us
    • Contact Us
    Facebook X (Twitter) Instagram YouTube WhatsApp
    • Home
    • Our Courses
    • Blog
    • About Us
    • Contact Us
    Facebook Instagram YouTube LinkedIn WhatsApp
    Code and Debug – BlogCode and Debug – Blog
    Code and Debug – BlogCode and Debug – Blog
    Home»Data Structures & Algorithms»Longest Common Substring | Solved using Tabulation
    Data Structures & Algorithms

    Longest Common Substring | Solved using Tabulation

    codeanddebugBy codeanddebug22 August 2025No Comments4 Mins Read
    Share Facebook Twitter Pinterest LinkedIn Tumblr Reddit Telegram Email
    Featured image of a question to solve Longest Common substring
    Share
    Facebook Twitter LinkedIn Pinterest Email

    Given two strings text1 and text2, find the length of the longest common substring between them. A substring is a contiguous block of characters. Unlike subsequence, characters must be adjacent and in the same order in both strings.

    Here’s the [Problem Link] to begin with.

    Example 1

    text1 = "abcjklp"
    text2 = "acjkp"
    Output: 3
    Explanation: One longest common substring is "cjk" with length 3.

    Example 2

    text1 = "zxabcdezy"
    text2 = "yzabcdezx"
    Output: 6
    Explanation: "abcdez" is a common substring of length 6.

    Goal: return only the length of the longest common substring.

    Content:
     [show]
    • Tabulation
      • Intuition and Approach
      • Code Implementation
      • Code explanation
      • Time and Space Complexity
      • Conclusion
    • Tabulation (Space Optimize)
      • Intuition and Approach
      • Code Implementation
      • Code explanation
      • Time and Space Complexity
      • Conclusion
    • Final takeaway

    Tabulation

    Intuition and Approach

    This is a classic dynamic programming problem. Let dp[i][j] be the length of the longest common suffix of the prefixes text1[:i] and text2[:j].
    Transition:

    • If text1[i-1] == text2[j-1], then the common suffix extends by 1, so dp[i][j] = 1 + dp[i-1][j-1].
    • Otherwise the common suffix breaks, so dp[i][j] = 0.

    Track the maximum over all dp[i][j] while filling the table. Initialize the first row and column to 0 because an empty prefix has no common substring.

    Code Implementation

    class Solution:
        def longestCommonSubstr(self, text1, text2):
            n = len(text1)
            m = len(text2)
            maxi = 0
            dp = [[-1 for _ in range(m + 1)] for _ in range(n + 1)]
            for ind2 in range(0, m + 1):
                dp[0][ind2] = 0
            for ind1 in range(0, n + 1):
                dp[ind1][0] = 0
            for ind1 in range(1, n + 1):
                for ind2 in range(1, m + 1):
                    if text1[ind1 - 1] == text2[ind2 - 1]:
                        dp[ind1][ind2] = 1 + dp[ind1 - 1][ind2 - 1]
                        maxi = max(maxi, dp[ind1][ind2])
                    else:
                        dp[ind1][ind2] = 0
            return maxi

    Code explanation

    • dp is a 2D table of size (n+1) x (m+1) where borders are 0.
    • When characters match, extend the previous diagonal value by 1 to continue the current matching substring.
    • When characters differ, reset to 0 because substrings must be contiguous.
    • maxi stores the best length seen so far.

    Time and Space Complexity

    • Precise: filling n*m cells with O(1) work each gives O(n*m) time. The table uses O(n*m) space.
    • Simplified: O(n*m) time and O(n*m) space.

    Conclusion

    Bottom up DP with a full table is straightforward and helps visualize contiguous matches through the diagonal extension rule.


    Tabulation (Space Optimize)

    Intuition and Approach

    dp[i][j] depends only on dp[i-1][j-1]. This allows reducing space to two 1D arrays representing the previous row and the current row.

    Code Implementation

    class Solution:
        def longestCommonSubstr(self, text1, text2):
            n = len(text1)
            m = len(text2)
            maxi = 0
            prev = [0 for _ in range(m + 1)]
            for ind1 in range(1, n + 1):
                curr = [0 for _ in range(m + 1)]
                for ind2 in range(1, m + 1):
                    if text1[ind1 - 1] == text2[ind2 - 1]:
                        curr[ind2] = 1 + prev[ind2 - 1]
                        maxi = max(maxi, curr[ind2])
                    else:
                        curr[ind2] = 0
                prev = curr
            return maxi

    Code explanation

    • prev[j] stores values for row ind1 - 1, and curr[j] for row ind1.
    • On match, take 1 + prev[ind2 - 1] to continue the substring.
    • On mismatch, reset curr[ind2] to 0 since contiguity is broken.
    • Track the maximum along the way, then return it.

    Time and Space Complexity

    • Precise: still processes n*m cells, so O(n*m) time. Uses two arrays of length m+1, so O(m) extra space.
    • Simplified: O(n*m) time and O(min(n, m)) space if you iterate along the shorter string as columns.

    Conclusion

    Space optimization preserves the same transitions and runtime while cutting memory to linear in one dimension. Use this when inputs are large and only the length is required.


    Final takeaway

    • Longest common substring requires contiguity, so mismatches reset the DP cell to 0.
    • Tabulation gives a clear and reliable O(n*m) solution.
    • Space optimized tabulation reduces memory to O(min(n, m)) while keeping the time optimal.
    Join our Advance DSA COURSE

    For any changes to the article, kindly email at code@codeanddebug.in or contact us at +91-9712928220.

    Dynamic Programming on Strings Medium
    Share. Facebook Twitter Pinterest LinkedIn Tumblr Email
    Previous ArticlePrint the Longest Common Subsequence | Build Table, Then Reconstruct
    codeanddebug
    • Website

    Related Posts

    Data Structures & Algorithms

    Print the Longest Common Subsequence | Build Table, Then Reconstruct

    22 August 2025
    Data Structures & Algorithms

    Longest Common Subsequence | Leetcode 1143 | All DP Approach

    22 August 2025
    Data Structures & Algorithms

    Insert Interval | Leetcode 57 | Greedy Solution

    22 August 2025
    Add A Comment
    Leave A Reply Cancel Reply

    Categories
    • Data Structures & Algorithms (210)
      • Beginner (71)
      • Expert (47)
      • Intermediate (92)
    • Uncategorised (1)
    Recent Posts

    Longest Common Substring | Solved using Tabulation

    22 August 2025

    Print the Longest Common Subsequence | Build Table, Then Reconstruct

    22 August 2025

    Longest Common Subsequence | Leetcode 1143 | All DP Approach

    22 August 2025

    Insert Interval | Leetcode 57 | Greedy Solution

    22 August 2025

    Shortest Job first (SJF) | Greedy Algorithm

    22 August 2025
    Facebook Instagram YouTube LinkedIn WhatsApp
    © 2025 Code and Debug. All rights reserved.

    Type above and press Enter to search. Press Esc to cancel.