递归查找数组中数字的最小路径

Posted

技术标签:

【中文标题】递归查找数组中数字的最小路径【英文标题】:Recursion for finding the smallest path of numbers in an array 【发布时间】:2016-01-20 23:26:21 【问题描述】:

我有数组[0,1,3,4,1]。使用这个数组,我需要编写一个递归函数:

    转到下一个元素,或 跳过下一个元素并转到它后面的元素(最多只能跳过 1 个元素)

条件是它必须是可能的最小数字。这个问题的解决方法如下:

从 0 开始 跳过1并转到3 跳过4并转到1 添加未跳过的元素并将其返回

我已经用它的基本情况启动了这个函数:

private int play(int[] a, int first, int last) 
    int result = 0;

    // base case
    if (first == last)
        return a[first];
    
    else
        //result = play(a,first+1,last);
        //System.out.println(result);
    
    return result;


first = 0last = array_length -1。请注意,数组可以包含任意数量的元素,所以假设我有数组[0 4 23 566 34 45 555 11 34 35 45 65 55 98 344],那么最低的总数将是 591。

请多多包涵,我不熟悉这种递归。提前致谢

【问题讨论】:

所以它假设返回你没有跳过的数字全部加起来? @3kings 是的,这是正确的 所以你可以跳过数字,但不能连续跳过一个以上的数字? @tobias_k 是的,该函数不能跳过多个元素 你在正确的轨道上,你只需要确定递归调用是使用first+1还是first+2(使用你提到的条件)。提示:当心 first+2 超出 last 的情况。 【参考方案1】:

我会做这样的事情,您可以跟踪您当前所在的当前索引以及到目前为止的总和,直到该索引沿着路径的点(因此总和将不包括我们跳过的数字)。

public static int play(int[] a, int index, int sum)
    if (index>=a.length) return Integer.MAX_VALUE;  //Path went over last index. Invalid Path. 
    sum += a[index];  //Add on to the sum of the index you are currently on
    if (index == a.length-1)
        return sum;  //If we are at last element, return sum of the path traveled
    else
        return Math.min(play(a, index+1, sum), play(a, index+2, sum)); //Continue onto path checking both options
    

测试代码:

public static void main(String args[]) 
    int[] a = new int[]0, 4, 23, 566, 34, 45, 555, 11, 34, 35, 45, 65, 55, 98, 344;
    System.out.println(play(a, 0, 0));

输出:591

希望这会有所帮助。

编辑: 好的,删除所有代码并从逻辑上考虑这一点。我喜欢考虑递归(尤其是路径)的方式是,我派出单独的小人物,并且在每次递归之后,我将复制这些小人物以采用不同的路径。在此示例中,我们使用较小的数组 [0,1,3,4,1]

我们从一个小人物开始。他从0 开始。他有2个选择。第一个选项是转到1,第二个选项是转到3。我们需要走这两条路,因为我们不确定未来会发生什么。这个小人复制了自己,将一个人发送到1,另一个发送到3

现在,前往路径 1 的小人还有 2 个选择。他可以去34。前往路径3 的小人还有2 个选择。他可以去41。所以他们复制自己,让小人物通过所有的选择。我希望这一切在这一点上都是有意义的。处理小人复制到不同路径的代码是:play(a, index+1, sum), play(a, index+2, sum))

小人走到路的尽头会做什么?他要告诉原来的小矮人,路还有多远。代码为:if (index == a.length-1)return sum;

不过,最初的小个子并不关心那一条路。他需要将它与走另一条路径的对应物进行比较,看看哪一条更短。这由Math.Min 控制。这只是返回两个小男人的较短距离。因此,距离较短的小人杀死了他的克隆(:p),因为我们不喜欢那条路径。最终所有的小人都会互相残杀,只留下一个距离最短的小人站着。 :)

【讨论】:

这个功能确实有效,但我有一个期中考试要参加。你能逐步解释一下这个功能吗?我真的很想了解递归是如何工作的。 @user3170251 是的,当然。我将添加更多文本。如果您不理解某个特定部分,请告诉我。 @user3170251 让我知道这是否有意义。在文本中教授这一点有点困难。 :p 这个例子很棒。我肯定会把这个解释留给未来可能的项目。 快速提问代码,为什么使用Integer.MAX_VALUE

以上是关于递归查找数组中数字的最小路径的主要内容,如果未能解决你的问题,请参考以下文章

423,动态规划和递归解最小路径和

数字三角形最小路径和—动态规划

算法初级面试题08——递归和动态规划的精髓阶乘汉诺塔子序列和全排列母牛问题逆序栈最小的路径和数组累加成指定整数背包问题

leetcode刷题(126)——1289. 下降路径最小和 II

LeetCode 5129. 下降路径最小和 II Minimum Falling Path Sum II

动态规划专题2:矩阵的最小路径和