Longest Increasing Path in a Matrix

Clarify the problem

  • The problem asks us to find the length of the longest increasing path in a given matrix.
  • The matrix can have positive integers or zero.
  • A path is considered increasing if it consists of adjacent cells with strictly increasing values.
  • We need to find the length of the longest increasing path in the matrix.

Analyze the problem

  • Input: A matrix of integers.
  • Output: An integer representing the length of the longest increasing path.
  • Constraints: The matrix can have a maximum size of 200x200.

Design an algorithm

  • We can solve this problem using a depth-first search (DFS) approach.
  • For each cell in the matrix, we will start a DFS to find the longest increasing path that includes that cell.
  • We will store the lengths of the longest increasing paths for each cell in a separate matrix to avoid redundant calculations.
  • We will iterate through each cell in the matrix and perform a DFS to find the longest increasing path from that cell.
  • During the DFS, we will check the neighboring cells and recursively call the DFS on cells with higher values.
  • We will keep track of the maximum path length encountered during the DFS.

Explain your approach

  • We will start by creating a separate matrix to store the lengths of the longest increasing paths for each cell.
  • Then, we will iterate through each cell in the matrix.
  • For each cell, we will perform a DFS starting from that cell to find the longest increasing path.
  • During the DFS, we will check the neighboring cells and recursively call the DFS on cells with higher values.
  • We will keep track of the maximum path length encountered during the DFS.
  • Finally, we will return the maximum path length.

Write clean and readable code

def longestIncreasingPath(matrix):
    if not matrix:
        return 0

    rows, cols = len(matrix), len(matrix[0])
    memo = [[0] * cols for _ in range(rows)]  # Matrix to store path lengths

    def dfs(i, j):
        if memo[i][j] != 0:
            return memo[i][j]  # Return stored path length if already calculated

        directions = [(0, 1), (1, 0), (0, -1), (-1, 0)]
        max_length = 1

        for dx, dy in directions:
            x, y = i + dx, j + dy
            if 0 <= x < rows and 0 <= y < cols and matrix[x][y] > matrix[i][j]:
                path_length = 1 + dfs(x, y)
                max_length = max(max_length, path_length)

        memo[i][j] = max_length  # Store the calculated path length
        return max_length

    max_path_length = 1
    for i in range(rows):
        for j in range(cols):
            max_path_length = max(max_path_length, dfs(i, j))

    return max_path_length


Test your code

  • Let's test the code with a few test cases:
# Test case 1
matrix1 = [
    [9, 9, 4],
    [6, 6, 8],
    [2, 1, 1]
]
print(longestIncreasingPath(matrix1))  # Output: 4

# Test case 2
matrix2 = [
    [3, 4, 5],
    [3, 2, 6],
    [2, 2, 1]
]
print(longestIncreasingPath(matrix2))  # Output: 4


Optimize if necessary

  • The current solution has a time complexity of O(rows * cols), as we visit each cell once.
  • The space complexity is also O(rows * cols) due to the memo matrix.
  • This solution is already quite efficient, so further optimizations may not be necessary.

Handle error cases

  • The code handles the case when the input matrix is empty by returning 0, indicating that there is no increasing path.

Discuss complexity analysis

  • Time complexity: O(rows * cols), where rows is the number of rows in the matrix and cols is the number of columns in the matrix.
  • Space complexity: O(rows * cols) for the memo matrix.
Next Post Previous Post