LeetCode: Convert Sorted List to Binary Search Tree 解题报告

Convert Sorted List to Binary Search Tree 

Given a singly linked list where elements are sorted in ascending order, convert it to a height balanced BST.

 

Show Tags

SOLUTION 1:

这个方法比较暴力,每次遍历当前list,找到中间的节点,建立 root,分别使用递归建立左树以及右树,并将左右树挂在root之下。但这个算法会复杂度很高。
建立root次数为N,每次遍历最多N次,最坏为N平方(实际不会这么多)
 1 public TreeNode sortedListToBST1(ListNode head) {
 2         ListNode fast = head;
 3         ListNode slow = head;
 4         
 5         ListNode pre = head;
 6         
 7         if (head == null) {
 8             return null;
 9         }
10         
11         TreeNode root = null;
12         if (head.next == null) {
13             root = new TreeNode(head.val);
14             root.left = null;
15             root.right = null;
16             return root;
17         }
18         
19         // get the middle node.
20         while (fast != null && fast.next != null) {
21             fast = fast.next.next;
22             
23             // record the node before the SLOW.
24             pre = slow;
25             slow = slow.next;
26         }
27         
28         // cut the list to two parts.
29         pre.next = null;
30         TreeNode left = sortedListToBST1(head);
31         TreeNode right = sortedListToBST1(slow.next);
32         
33         root = new TreeNode(slow.val);
34         root.left = left;
35         root.right = right;
36         
37         return root;
38     }
View Code

 

SOLUTION 2:

 这个解法使用一个参数来记录当前正在操作的List Node. DFS本身的效果是,从head直到尾部建树,并且将currNode移动到size+1处。
这样可以在1次iterator 我们的List后直接建立树。
这是一种Bottom-up的建树方法。如果我们使用C++,则可以将List Node的指针直接做为入参。我们这里使用了类似的方法,不过,
Java不能使用指针,所以我们自建一个自定义的类,里面只有一个ListNode,这样我们就能方便地修改入参了(好纠结啊,这时主页君就开始怀念起C的指针了),
:)
C++版本可以参见张磊哥哥的解答喔:)
 1 public TreeNode sortedListToBST(ListNode head) {
 2         if (head == null) {
 3             return null;
 4         }
 5         
 6         int size = 0;
 7         ListNode cur = head;
 8         while (cur != null) {
 9             size++;
10             cur = cur.next;
11         }
12          
13         CurrNode curNode = new CurrNode(head); 
14         return sortedListToBSTHelp(curNode, size);
15     }
16     
17     public class CurrNode {
18         ListNode node;
19         
20         CurrNode(ListNode node) {
21             this.node = node;
22         }
23     }
24     
25     // when the recursion is done, the curr node should point to the node
26     // which is the next of the block.
27     public TreeNode sortedListToBSTHelp(CurrNode curr, int size) {
28         if (size <= 0) {
29             return null;
30         }
31         
32         TreeNode left = sortedListToBSTHelp(curr, size/2);
33         
34         // because we want to deal with the right block.
35         TreeNode root = new TreeNode(curr.node.val);
36         curr.node = curr.node.next;
37         
38         TreeNode right = sortedListToBSTHelp(curr, size - 1 - size/2);
39         
40         root.left = left;
41         root.right = right;
42         
43         return root;
44     }
View Code

 

SOLUTION 3:

这个解法使用一个instance variable 来记录当前正在操作的List Node. DFS本身的效果是,从head直到尾部建树,并且将currNode移动到size+1处。
这样可以在1次iterator 我们的List后直接建立树。
这是一种Bottom-up的建树方法。如果我们使用C++,则可以将List Node直接做为入参来改变之而不需要使用实例变量。
问题是:我们如果可以的话,尽量不要使用实例变量,因为它是各个Method 共享的,所以这个方法存在风险。因为变量有可能被别的方法修改。
 
这个dfs的意思就是 对一个以head 起始的list, size为大小的list建一个树,一个bfs树
并且这个dfs有一个作用 会把指针移动到这个要建的树的下一个位置
 
这样 我们先建立左树,        TreeNode left = dfs(head, size / 2);
经过这一行 cur就移动到了中间
我们建立 一个根         TreeNode root = new TreeNode(curNode.val);

把cur移动到下一个     curNode = curNode.next;
再用递归建立右树      
 
构造我们想要的树 返回根结果
root.left = left;
root.right = right;
return root;
 1 /**
 2  * Definition for singly-linked list.
 3  * public class ListNode {
 4  *     int val;
 5  *     ListNode next;
 6  *     ListNode(int x) { val = x; next = null; }
 7  * }
 8  */
 9 /**
10  * Definition for binary tree
11  * public class TreeNode {
12  *     int val;
13  *     TreeNode left;
14  *     TreeNode right;
15  *     TreeNode(int x) { val = x; }
16  * }
17  */
18 public class Solution {
19     ListNode curNode = null;
20     
21     public TreeNode sortedListToBST(ListNode head) {
22         if (head == null) {
23             return null;
24         }
25         
26         int size = 0;
27         ListNode cur = head;
28         while (cur != null) {
29             size++;
30             cur = cur.next;
31         }
32         
33         curNode = head;
34         return dfs(head, size);
35     }
36     
37     // Use the size to control.
38     public TreeNode dfs(ListNode head, int size) {
39         if (size <= 0) {
40             return null;
41         }
42         
43         TreeNode left = dfs(head, size / 2);
44         TreeNode root = new TreeNode(curNode.val);
45         
46         // move the current node to the next place.
47         curNode = curNode.next;
48         TreeNode right = dfs(curNode, size - size / 2 - 1);
49         
50         root.left = left;
51         root.right = right;
52         
53         return root;
54     }
55 }
View Code

 

posted on 2015-04-04 13:48  Yu's Garden  阅读(1595)  评论(0编辑  收藏

导航