首页 > 代码库 > 26、剑指offer--二叉搜索树与双向链表

26、剑指offer--二叉搜索树与双向链表

题目描述
输入一棵二叉搜索树,将该二叉搜索树转换成一个排序的双向链表。要求不能创建任何新的结点,只能调整树中结点指针的指向。
 
解题思路:在二叉搜索树中,左结点<根节点<右节点,因此中序遍历就是排序好的。
在我们遍历转换到根节点时,它的左子树已经排好序的链表,并且处于链表中的最后一个结点为当前值最大结点。我们把该值与根结点连接起来。此时链表中最后一个结点为根结点,接着遍历右子树,并把根结点与右子树中最小的结点链接起来。使用递归进行实现。
 1 /*
 2 struct TreeNode {
 3     int val;
 4     struct TreeNode *left;
 5     struct TreeNode *right;
 6     TreeNode(int x) :
 7             val(x), left(NULL), right(NULL) {
 8     }
 9 };*/
10 class Solution {
11 public:
12     void CovertNode(TreeNode *root,TreeNode **pLastNodeInitList)
13     {
14         if(root == NULL)
15             return;
16         TreeNode *pCurrent = root;
17         if(pCurrent->left)
18         {
19             CovertNode(pCurrent->left,pLastNodeInitList);
20         }
21         pCurrent->left = *pLastNodeInitList;
22         if(*pLastNodeInitList != NULL)
23             (*pLastNodeInitList)->right = pCurrent;
24         *pLastNodeInitList = pCurrent;
25         if(pCurrent->right != NULL)
26         {
27             CovertNode(pCurrent->right,pLastNodeInitList);
28         }
29     }
30     TreeNode* Convert(TreeNode* pRootOfTree)
31     {
32         TreeNode *pLastNodeInitList = NULL;
33         CovertNode(pRootOfTree,&pLastNodeInitList);
34         //pLastNodeInitLast指向链表的最后一个结点
35         TreeNode *pHead = pLastNodeInitList;
36         while(pHead != NULL && pHead->left != NULL)
37         {
38             pHead = pHead->left;
39         }
40         return pHead;
41     }
42 };
递归不是很好理解,一种不用递归实现的易于理解的方法:
1)采用vector来存储中序遍历后各节点
2)将各节点链接起来构成双向链表
3)返回v[0]即链表头
 1 /*
 2 struct TreeNode {
 3     int val;
 4     struct TreeNode *left;
 5     struct TreeNode *right;
 6     TreeNode(int x) :
 7             val(x), left(NULL), right(NULL) {
 8     }
 9 };*/
10 class Solution {
11 public:
12     //非递归中序遍历
13     void midorder2(TreeNode* root,vector<TreeNode *> *v){
14         if(root==NULL)
15             return;
16         stack<TreeNode *> s;
17         while(root||!s.empty())
18         {
19                 while(root)
20                 {
21                     s.push(root);
22                     root=root->left;
23                 }
24                 root=s.top();
25                 s.pop();
26                 (*v).push_back(root);
27                 root=root->right;
28         }
29     }
30     TreeNode* Convert(TreeNode* pRootOfTree)
31     {
32         if(pRootOfTree == NULL)
33             return NULL;
34         vector<TreeNode *> v;
35         midorder2(pRootOfTree,&v);
36          
37         int n = v.size();
38          
39         v[0]->left = NULL;
40         for(int i=1;i<n;i++)
41         {
42             v[i-1]->right = v[i];
43             v[i]->left = v[i-1];
44         }
45         v[n-1]->right = NULL;
46         return v[0];
47     }
48 };

 

26、剑指offer--二叉搜索树与双向链表