查看: 2281| 回复: 14
跳转到指定楼层
上一主题 下一主题
收起左侧

[Leetcode] 求救897. Increasing Order Search Tree,想了一晚上也没看懂的答案

全局:

注册一亩三分地论坛,查看更多干货!

您需要 登录 才可以下载或查看附件。没有帐号?注册账号

x
就是最高vote的答案,具体如下:
public TreeNode increasingBST(TreeNode root) {
        return increasingBST(root, null);
    }

    public TreeNode increasingBST(TreeNode root, TreeNode tail) {
        if (root == null) return tail;
        TreeNode res = increasingBST(root.left, root);
        root.left = null;
        root.right = increasingBST(root.right, tail);
        return res;
    }

真的看不懂这几个递归的关系,有返回值感觉应该是divide&conquer, 但也不像一般的divide&conquer返回值对称的情况,这个函数的意义是每个子树的最左点(即head吗)?又像是用了tail节点来traverse记录需要连接的点,但是代码里也并没有.right=tail这样的代码, 请问是如何链接上的?
求大神解答以及提供这个代码的运行流程图或思考方法,不胜感激。

上一篇:Leetcode 120. Triangle 请问我的DP代码到底错在哪里啊?
下一篇:50. Pow(x, n) - x * x 和 x **2 的区别
推荐
zjck1995 2019-6-6 05:16:59 | 只看该作者
全局:
FightingBBY 发表于 2019-6-6 04:46
原谅小白,前面那个指针啊? 通过那个语句连起来的?

就是 root.right = increasingBST(root.right, tail);
然后终止状态是  if (root == null) return tail;
这块可能挺难理解的(实际面试不太推荐写这么tricky的解法, 这是我之前写的代码 https://paste.ubuntu.com/p/7MpZVrQZcQ/ , 虽然长了点,但很好理解)
回复

使用道具 举报

推荐
zjck1995 2019-6-6 03:11:47 | 只看该作者
全局:
这个答案挺有意思的,首先得明确知道increasingBST(TreeNode root, TreeNode tail) 干了什么,参数里面 root 是一个tree, tail是已完成的链,这个函数实现了把root转成一条链,然后再把tail这条链接上去,形成新的链并返回,具体操作如下:
1. 把root左儿子转成一个链,并把root接到这条链的后面
       TreeNode res = increasingBST(root.left, root); (不过此时第二个参数root并不是链,但你可以假设它是,因为在第二步会做, lazy update?)
2. 将 root左儿子清除,并将root右儿子转成链
       root.left = null;
       root.right = increasingBST(root.right, tail);
      
非常tricky的一个解法,不过代码挺短的~
回复

使用道具 举报

推荐
 楼主| FightingBBY 2019-6-8 01:29:32 | 只看该作者
全局:
337845818 发表于 2019-6-7 21:26
你想怎么定义都可以, 树是一种特殊的dag图, 解法就那么几种.
这题你不能理解的话, 大概你试试preorder t ...

醉了,这不是inorder traverse吗(左根右)? 返回的就是最左节点(也是root右边该链接的那个点),只是当运行到root==null的时候分情况return应该链接的下一个点。前面大神解释清楚了。不知道怎么又来了preorder traverse...恐怕回复错了题目吧
回复

使用道具 举报

🔗
 楼主| FightingBBY 2019-6-6 03:57:57 | 只看该作者
全局:
zjck1995 发表于 2019-6-6 03:11
这个答案挺有意思的,首先得明确知道increasingBST(TreeNode root, TreeNode tail) 干了什么,参数里面 roo ...

谢谢大神,赶紧抓住再问问!!!
大概精神我也能领会一二,就像你说的一样,但是就是纠结在他是怎么把这个链串接上的,代码里并没有对tail做任何操作,比如tail.right或者tail.left啊
回复

使用道具 举报

🔗
zjck1995 2019-6-6 04:34:23 | 只看该作者
全局:
FightingBBY 发表于 2019-6-6 03:57
谢谢大神,赶紧抓住再问问!!!
大概精神我也能领会一二,就像你说的一样,但是就是纠结在他是怎么把这 ...

不需要对tail进行操作,tail这个参数表示指向一条链的头部,是已经处理好的,只需要把前面的指针指向这个tail就好了
回复

使用道具 举报

🔗
 楼主| FightingBBY 2019-6-6 04:46:01 | 只看该作者
全局:
zjck1995 发表于 2019-6-6 04:34
不需要对tail进行操作,tail这个参数表示指向一条链的头部,是已经处理好的,只需要把前面的指针指向这个 ...

原谅小白,前面那个指针啊? 通过那个语句连起来的?
回复

使用道具 举报

🔗
 楼主| FightingBBY 2019-6-6 07:02:39 | 只看该作者
全局:
FightingBBY 发表于 2019-6-6 04:46
原谅小白,前面那个指针啊? 通过那个语句连起来的?

嗯嗯我自己也按自己想法解答了,只是看到这个答案这么多vote就很好奇。其实可以不可以理解root.right = increasingBST(root.right, tail); 就是将根和右子树最左的节点连在一起。如果是叶子节点,则分为:
做叶子就返回自己的parent,右叶子返回自己parent 的parent?
回复

使用道具 举报

🔗
zjck1995 2019-6-6 15:02:48 | 只看该作者
全局:
FightingBBY 发表于 2019-6-6 07:02
嗯嗯我自己也按自己想法解答了,只是看到这个答案这么多vote就很好奇。其实可以不可以理解root.right = i ...

我其实没太看懂你的意思,不过vote高并不一定是最好的,这道题其实很简单,无非十几行的代码就可以表述得非常清楚,没必要为了极致优化代码行数而写成这样,也不需要纠结这个
回复

使用道具 举报

🔗
337845818 2019-6-6 22:14:47 | 只看该作者
全局:
本质上是in order visit, 递归, 不是d&c.
你不懂递归的话自然很难理解.
如果你不懂dfs bfs的话, 还是先看图题再考虑树题.
回复

使用道具 举报

🔗
 楼主| FightingBBY 2019-6-7 01:33:55 | 只看该作者
全局:
zjck1995 发表于 2019-6-6 15:02
我其实没太看懂你的意思,不过vote高并不一定是最好的,这道题其实很简单,无非十几行的代码就可以表述得 ...

好吧,我就是觉得如果我理解不了,肯定还是递归没有掌握到位
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 注册账号
隐私提醒:
  • ☑ 禁止发布广告,拉群,贴个人联系方式:找人请去🔗同学同事飞友,拉群请去🔗拉群结伴,广告请去🔗跳蚤市场,和 🔗租房广告|找室友
  • ☑ 论坛内容在发帖 30 分钟内可以编辑,过后则不能删帖。为防止被骚扰甚至人肉,不要公开留微信等联系方式,如有需求请以论坛私信方式发送。
  • ☑ 干货版块可免费使用 🔗超级匿名:面经(美国面经、中国面经、数科面经、PM面经),抖包袱(美国、中国)和录取汇报、定位选校版
  • ☑ 查阅全站 🔗各种匿名方法

本版积分规则

>
快速回复 返回顶部 返回列表