【问题标题】:Understanding recursion better in linked lists更好地理解链表中的递归
【发布时间】:2019-11-24 11:45:22
【问题描述】:

我想更深入地理解递归,而不仅仅是直观。我知道这个概念,也知道如何递归求解阶乘或斐波那契数列。但是当递归使用时,我似乎无法很好地想象链表中到底发生了什么。

更具体地说,我正在努力理解以下算法:

(它在链表中查找最大值。它通过从第二个元素开始递归搜索最大值。然后将其与第一个元素进行比较并返回较高的那个。)

 function MaxRec (inRefBegin : tRefList) : tRefList;
  { returns recursively a pointer to the max element in a list }

    var
    rekMax : tRefList; { variable to point to the recursive maximum 
                          starting from second element }
    begin
      if inRefBegin = nil then { Base Case, recursion stops }
        MaxRec := nil
      else
      begin
        rekMax := MaxRec (inRefBegin^.next); 
        if rekMax = nil then
          MaxRec := inRefBegin
        else
          if inRefBegin^.info < rekMax^.info then
            MaxRec := rekMax
          else
            MaxRec := inRefBegin
      end { if }
    end; { MaxRec }


我确实明白理论上应该发生什么。我很难一步一步地想象它。每个堆栈级别会发生什么? 我不明白这一行如何:rekMax := MaxRec (inRefBegin^.next) 可以找到最大值....它只使用指向下一项的指针调用函数,但不比较任何值....函数被调用的时间??

我的思考过程是这样的: 假设我有一个这样的链表:

5 => 7 => 10 => 3 => 2 => nil 
  1. 函数被调用并且不为零((保存到堆栈))
  2. 函数被调用并且不为零((保存到堆栈))
  3. 函数被调用并且不为零((保存到堆栈))
  4. 函数被调用并且不为零((保存到堆栈))
  5. 函数被调用并且不为零((保存到堆栈))
  6. 递归停止

  7. 现在会发生什么?我是否将每个函数与第一个元素进行比较?或者这是我已经拥有递归最大值的地方?可以想象一下吗?

我非常感谢每一个帮助。我知道这个主题在网上有大量资源,相信我已经阅读过它们。但我仍然不清楚每个级别到底发生了什么。

【问题讨论】:

  • 嗯,据我所知,您展示的这个函数根本不是递归的。将ZeigListMax的代码添加到问题中,可能是。
  • 对不起伙计,我的错,我更新了代码。现在应该是

标签: list recursion linked-list pascal


【解决方案1】:

7) 现在会发生什么?我是否将每个函数与第一个元素进行比较?或者这是我已经拥有递归最大值的地方?可以想象一下吗?

在 7) 递归停止,因为您已到达列表的末尾,因此返回 nil。 然后继续上一个调用,此时 MaxRec 的结果现在为零,因此最后一部分的最大值是当前的 inRefBegin 值(同样,因为返回了 nil)。

对于其他级别,退出递归,将当前节点中的值与递归调用返回的值进行比较,并保留最大的节点,直到最后留下最大节点整个列表。

这有帮助吗?

【讨论】:

  • 谢谢我的朋友的解释......我不知道我是否得到它 100%......你说“最后一部分的最大值是当前的 inRefBegin 值”。 .. 当前的 inRefBegin 值是多少?您还说“当前节点中的值与递归调用返回的值进行比较,并保留最大的值”,但哪一行代码确实做到了?
  • 当前的 inRetBegin 值是列表中的每个条目,依次,因为递归遍历列表。至于which line does 的比较,只有一行进行比较,并根据结果选择当前节点值或递归调用返回的值作为新的本地最大值。
  • 好的,再次非常感谢。让我试着用那个列表从 7 开始: 1. 递归停止并返回 nil 2. 这就是 rekMax 现在指向 nil 3. inRefBegin 指向 2 而 rekMax 指向 nil 的原因。这就是返回 2 的原因 4. inRefBegin 指向 3 而 rekMax 指向 2。这就是为什么返回 3 5. inRefBegin 指向 10 而 rekMax 指向 3。这就是为什么返回 10 6. inRefBegin 指向 7 而 rekMax 指向 10 . 这就是为什么返回 10 7。inRefBegin 指向 5,rekMax 指向 10。这就是为什么返回 10。你说的是这个吗?
  • 是的,你明白了 :)
  • 天哪,太棒了!非常感谢你,我的朋友,我花了几天时间试图解决这个问题!
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2010-09-26
  • 2016-04-09
  • 2018-11-04
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多