Convert Sorted List to Binary Search Tree
LC109. Convert Sorted List to Binary Search Tree
将有序链表转化成高度平衡的BST
总体思路:将中间节点作为二叉树的根节点,递归左子树和右子树
方法1:将链表值存入数组
time:$O(n)$
time:$O(n)$
class Solution { public: vector<int> nu; TreeNode* build(int b, int e) { if (b > e) return nullptr; int m = (b + e + 1) / 2; auto node = new TreeNode(nu[m]); node->left = build(b, m - 1); node->right = build(m + 1, e); return node; } TreeNode* sortedListToBST(ListNode* head) { auto p = head; while (p != NULL) { nu.push_back(p->val); p = p->next; } int n = nu.size(); return build(0, n - 1); } };
方法2:不用把链表存入数组,每次用快慢指针找中间元素
time:$O(nlog n)$
time:$O(log n)$
class Solution { public: TreeNode* build(ListNode* head, ListNode* tail) { if (head == tail) { return nullptr; } if (head->next == tail) { return new TreeNode(head->val); } auto mid = head; auto tmp = head; while (tmp != tail && tmp->next != tail) { mid = mid->next; tmp = tmp->next->next; } auto node = new TreeNode(mid->val); node->left = build(head, mid); node->right = build(mid->next, tail); return node; } TreeNode* sortedListToBST(ListNode* head) { return build(head, NULL); } };
方法3:模拟中序遍历。知道链表的长度,就可以根据中序遍历建立BST,二叉树中最左边的点就是链表中的第一个点,这样就不用查找链表的中间节点,
而是按照中序依次建立二叉树中的每个节点,用一个全局变量 ListNode* head 就可以记录下一个要建立的节点
time:$O(n)$
time:$O(log n)$
class Solution { public: ListNode* head; TreeNode* build(int l, int r) { if (l > r) { return NULL; } int mid = l + (r - l) / 2; TreeNode* left = build(l, mid - 1); TreeNode* node = new TreeNode(head->val); node->left = left; head = head->next; node->right = build(mid + 1, r); return node; } TreeNode* sortedListToBST(ListNode* head) { int len = 0; auto p = head; while (p != NULL) { len++; p = p->next; } this->head = head; return build(0, len - 1); } };