这就是我如何解决这个问题-
从书中 -
在最后一跳,直到第 nth 步,孩子可能有
完成单步、双步或三步跳。也就是说,最后
move 可能是从步骤 n-1 的单步跳跃,双
从步骤 n-2 跳出一步,或从 n-3 跳出三步。这
因此到达最后一步的方法总数是
到达最后三个步骤中的每个步骤的方式数
你的想法是正确的——
为什么不是这样的答案:添加这些路径的数量然后添加 3 ?
因为如果你在步骤 n-1 或 n-2 或 n-3,有 3 种方法可以得到
第n步?
这种基本情况的问题在于,它仅适用于 n >= 3。如果只有 2 个步骤,您显然不会添加 3。
让我们分解个别案例并了解这里的基本案例到底是什么。
n=0
There are no stairs to climb.
Total number of ways = 0
n=1
Total number of ways = 1StepHop from (n-1)
Number of ways to do 1StepHop from Step 0(n-1) = 1
Total number of ways = 1
n=2
Total number of ways = 2StepHop from (n-2) + 1StepHop from (n-1)
Number of ways to do 2StepHop to reach Step 2 from Step 0(n-2) = 1
Number of ways to do 1StepHop to reach Step 2 from Step 1(n-1) = 1 (Previous answer for n=1)
Total number of ways = 1 + 1 = 2
n=3
Total number of ways = 3StepHop from (n-3) + 2StepHop from (n-2) + 1StepHop from (n-1)
Number of ways to do 3StepHop to reach Step 3 from Step 0(n-3) = 1
Number of ways to do 2StepHop to reach Step 3 from Step 1(n-2) = 2 (From previous answer for n = 2)
Number of ways to do 1StepHop to reach Step 3 from Step 2 = 1 (From previous answer for n=1)
Total number of ways = 1 + 2 + 1 = 4
观察 -
从上面可以看出,我们正确地考虑了每种情况下的最后一步。为 n-1 中的 1StepHop、n-2 中的 2StepHop 和 中的每一个添加一个来自 n-3 的 3StepHop。
现在查看代码,如果 n==0 则返回 1 的情况有点违反直觉,因为我们已经看到答案应该是 n==0,则为强>0。 -
public static int countWaysDP(int n, int[] map) {
if (n < 0)
return 0;
else if (n == 0)
return 1; <------------- this case is counter-intuitive
else if (map[n] > -1)
return map[n];
else {
map[n] = countWaysDP(n - 1, map) + countWaysDP(n - 2, map) + countWaysDP(n - 3, map);
return map[n];
}
从观察中,您可以看到 n==0 这种反直觉的情况实际上是导致最后一步的原因 - 1StepHop from n-1 、2StepHop 来自 n-2 和 3StepHop 来自 n-3。
因此,只有在递归过程中才能达到 n==0 大小写 - 只有当 n 的初始值大于 0 时才会发生这种情况。
这个问题的更完整的解决方案可能有一个驱动方法,它在核心递归算法之外处理这种情况 -
int countWays(int n) {
if (n <= 0 ) return 0;
int[] map = new int[n+1];
for(int i = 0; i<n+1; i++){
map[i] = -1;
}
return countWaysDP(n, map);
}
希望这有帮助。