题目:把二元查找树转变成排序的双向链表
输入一棵二元查找树,将该二元查找树转换成一个排序的双向链表。
要求不能创建任何新的结点,只调整指针的指向。
10
/ \
6 14
/ \ / \
4 8 12 16 转换成双向链表 4=6=8=10=12=14=16。
方案一:
BSTreeNode * treeToLinkedList(BSTreeNode * root) { BSTreeNode * head, * tail; helper(head, tail, root); return head; } //基本思想:函数helper将root子树在中序下的头赋值给head,把尾赋值给tail。函数负责把root和左子树的tail及右子树的head连接。 void helper(BSTreeNode *& head, BSTreeNode *& tail, BSTreeNode *root) { BSTreeNode *lt, *rh; if (root == NULL) //也可使用(root->m_pLeft == NULL && root->m_pRight==NULL){head = root;tail=root;return;} { head = NULL, tail = NULL; return; } helper(head, lt, root->m_pLeft); helper(rh, tail, root->m_pRight); if (lt!=NULL) { lt->m_pRight = root; root->m_pLeft = lt; } else { head = root; } if (rh!=NULL) { root->m_pRight=rh; rh->m_pLeft = root; } else { tail = root; } }方案二:
基本思想:设置一个全局变量last表示当前已处理的部分子树的最后一个节点。每次递归调用左子树,直到遇到最左的节点后才开始更新last,而后递归调用右子树。
其实也可以把last做成一个指针参数传给convert函数,它的类型是Node* &last或者Node **last。
Node* head; Node* last; void convert(Node* p){ if(p==null)return; convert(p->left); addToList(p); convert(p->right); } void addToList(Node* p){ if(last !=null){ p->left = last; last->right = p; } else{ head = p; } last = p; }