• [leetcode]Convert Sorted List to Binary Search Tree


    这道题有点难。(首先这题是重新创建一个新的BST,所以就不用去想怎么在原有的list里面指针颠来倒去了。)
    1.首先这道题如果O(n*logn)就很简单了。如果可以O(n)空间的话,转化成数组,就可以O(n)时间,但这就没意思了。所以答案是可以O(1)空间,O(n)时间的。
    2.看过答案知道是自底向上考虑。但试了一下,生成的子树的节点个数先是少的,然后变多,然后又少(一开始1个节点的左子树,然后生成3个节点的子树时,又要生成1个节点的右子树),用循环写很不好表示状态,需要用栈来记住很多东西。
    3.那么看到很多相似的步骤,就可以用递归来做,但这是个自底向上的递归,怎么做呢?看一下答案,发现有这么些规律:
    4.在递归中传的都是同一个链表,只是这个链表的节点不停往前走;而真正决定性变化的是区间;
    5.可以看到,每次递归调用开始时,节点指针都指向区间第一个,结束时节点的指针指向区间末尾的后一个。这个可以通过数学归纳法证明,因为一个节点时成立,且k级成立时k+1级也成立。
    6.每次递归调用时,分成左右两部分,左边构造完时,正好指针指向mid,创建一下root,继续构造右部分子树。
    本来想用Java写的,后来发现指针的指针Java不好写,还是C++吧,本来指针啊,树啊,就是C++好。

    class Solution {
    public:
        TreeNode *sortedListToBST(ListNode *head) {
            int len = 0;
            ListNode * node = head;
            while (node != NULL)
            {
                node = node->next;
                len++;
            }
            return buildTree(head, 0, len-1);
        }
        
        TreeNode *buildTree(ListNode *&node, int start, int end)
        {
            if (start > end) return NULL;
            int mid = start + (end - start) / 2;
            TreeNode *left = buildTree(node, start, mid-1);
            TreeNode *root = new TreeNode(node->val);
            root->left = left;
            node = node->next;
            root->right = buildTree(node, mid+1, end);
            return root;
        }
    };
    

      

  • 相关阅读:
    简单的本地注册与登陆的功能
    Android 简单统计文本文件的字符数、单词数、行数、语句数Demo
    个人项目需求与分析——点菜系统App
    强大的健身软件——Keep
    大学生三大痛点
    我推荐的一款实用APP-圣才电子书
    PropertyDescriptor和BeanUtils使用去获得类的get 和 setter访问器
    神奇的 Object.defineProperty
    用cudamat做矩阵运算的GPU加速
    Java并发编程概要
  • 原文地址:https://www.cnblogs.com/lautsie/p/3346581.html
Copyright © 2020-2023  润新知