We begin by directly modeling the problem’s recursive nature, where each position can be reached by moving right or down.
i
,j
), you must come from either (i-1
,j
) (moving down) or (i
,j-1
) (moving right). The number of paths to (i
,j
) is the sum of paths to these two positions. The base case is the starting point (0,0), which has exactly one path (staying there), and any position outside the grid has zero paths.paths(i, j)
to compute the number of paths to position (i
,j
).i == j == 0
, return 1.i < 0
, j < 0
, i == m
, or j == n
), return 0.paths(i-1, j)
and paths(i, j-1)
.paths(m-1, n-1)
to get the number of paths to the bottom-right corner.m+n
, leading to approximately 2^(m*n) operations in the worst case.m+n
along the longest path in the grid.
We optimize the recursive solution by storing computed results to eliminate redundant calculations.
i
,j
) in a dictionary, we can retrieve results in O(1) time, reducing the number of computations.memo
with the base case {(0,0): 1} (one path to the starting point).paths(i, j)
that checks if (i
,j
) is in memo
. If so, return the cached value.i < 0
, j < 0
, i == m
, or j == n
), return 0.paths(i, j-1) + paths(i-1, j)
, store the result in memo[(i,j)]
, and return it.paths(m-1, n-1)
to get the result.i
,j
) is computed once, with O(1) lookups and operations per call. There are m*n
positions in the grid.memo
dictionary stores up to m*n
entries, and the recursion stack uses O(m+n) space.
We shift to an iterative approach using a dynamic programming grid to compute paths bottom-up.
dp[i][j]
stores the number of paths to position (i
,j
), computed as the sum of paths from above and left.dp
of size m x n
, initialized with zeros.dp[0][0] = 1
(base case: one path to the starting point).i
,j
) in the grid from 0 to m-1
and 0 to n-1
.dp[i][j] = dp[i-1][j] + dp[i][j-1]
(adding paths from above and left, if valid).dp[m-1][n-1]
, the number of paths to the bottom-right corner.m*n
positions, with O(1) operations per position.dp
array stores m*n
values.
The Unique Paths problem is a classic dynamic programming challenge that appears in many algorithm interviews. You are given an m x n
grid, and your task is to determine how many distinct paths exist to move from the top-left corner to the bottom-right corner by only moving right or down. This is a foundational problem that tests understanding of combinatorics and dynamic programming strategies.
A naive solution uses recursion to explore all possible paths from the starting cell to the goal. At each cell (i, j)
, you have two choices: move right or move down. The recursive function sums the number of valid paths from these two options.
While conceptually straightforward, this brute-force approach is highly inefficient for larger grids due to repeated recomputation of the same subproblems. For example, the number of recursive calls grows exponentially as O(2m+n), making this solution infeasible beyond small grid sizes.
The optimal solution to the Unique Paths problem uses bottom-up dynamic programming to compute the number of ways to reach each cell by building up from the base case. Instead of recalculating overlapping subproblems, we store the result of each computation in a 2D table.
You initialize a 2D array dp
of size m x n
, where dp[i][j]
represents the number of ways to reach cell (i, j)
. The first row and first column are filled with 1s because there is only one way to move strictly right or strictly down. Each remaining cell is computed as the sum of the paths from the cell above and the cell to the left.
The final result is stored in dp[m-1][n-1]
, which represents the total number of unique paths from the top-left to the bottom-right.
The Unique Paths problem is a powerful introduction to dynamic programming concepts and optimization techniques. By transitioning from brute-force recursion to a tabulation-based approach, you dramatically improve efficiency and scalability. Mastering this pattern helps tackle a wide range of grid traversal and DP problems, including obstacles, cost minimization, and more complex movement constraints.