https://oj.leetcode.com/problems/unique-paths/
A robot is located at the top-left corner of a m x n grid (marked 'Start' in the diagram below).
The robot can only move either down or right at any point in time. The robot is trying to reach the bottom-right corner of the grid (marked 'Finish' in the diagram below).
How many possible unique paths are there?
public int uniquePaths(int m, int n)
所有求路径数目而不求所有路径的题目基本都有暴力和dp两种解法。而这一题简直就已经成了DP题目的入门范例了,大部分地方都能见到。如果说斐波那契是dp题目的门口,这一题和爬楼梯那题大概就是dp题目开门之后的第一步和第二步了。
先说说暴力解的做法。首先必然都是在可能的时候向右走算是递归一层和向下走另外递归一层。可以top-bottom这样然后以一个叠加器作为参数每次走到终点加一的做法,也可以用bottom-top在终点的时候返回1然后在别的地方同时回收并返回下层和右层递归返回的结果之和...因为最近两次刷都没有写过这种暴力解的代码。。这里就不给出了。
然后说一下dp解的做法,递归式如下
f(0, i) = 1
f(1, 0) = 1
f(i, j) = f(i - 1, j) + f(i , j - 1) ( 1 <= i <= m, 1 <= j <= n)
f(i, j)表示到 格数(i, j)的路径数量。不是很难理解的,就简要说明一下,在x = 0或者y = 0的时候都是华山一条路。所以都是1,然后剩余合理情况都是来自上面一格解集和左边一格解集之和。最后返回f(m,n)即可。可以看出这本质上是一个2维dp,但所有只从前方继承或者只从后方这样单方向继承的二维dp都是可以化解成一维空间的。具体看代码吧:
public int uniquePaths(int m, int n) {
int[] dp = new int[m];
for(int i = 0; i < m; i++)
dp[i] = 1;
for(int i = 1; i < n; i++){
for(int j = 1; j < m; j++){
dp[j] += dp[j - 1];
}
}
return dp[m - 1];
}