题目:
嗯。。这题呢我大概想了两种方法。第一种是递归时直接更改,第二种是先遍历得到序列,然后再统一修改。两种方法的时间复杂度上面差不了很多。
首先,对于一棵二叉搜索树(排序树),中序遍历可以得到排序序列。因此,我们就很容易可以想到第一种方法。中序遍历一遍,然后使用一个数组存储指向每个节点的指针。然后从头到尾修改left和right指针就可以了。
第二种方法就是在中序遍历递归的时候修改,使用一个指针pre来记录上一个节点,来完成整个链表的融合。最后只需要略微调整首尾节点就可以了。
具体细节看代码吧
包括了建立二叉树的过程:
C++代码附带测试:
#include<iostream>
#include<vector>
#include<algorithm>
using namespace std;
class Node {
public:
int val;
Node* left;
Node* right;
Node() {}
Node(int _val) {
val = _val;
left = nullptr;
right = nullptr;
}
Node(int _val, Node* _left, Node* _right) {
val = _val;
left = _left;
right = _right;
}
};
Node* createTree(vector<int> a,int i){
if(a[i]==-1){
return nullptr;
}
Node* root = new Node(a[i]);
int leftson = i*2+1;
int rightson = i*2+2;
if(leftson>a.size()-1){
root->left = nullptr;
}else{
root->left = createTree(a,leftson);
}
if(rightson>a.size()-1){
root->right = nullptr;
}else{
root->right = createTree(a,rightson);
}
return root;
}
void inorder(Node* root){
if(root==nullptr){
return;
}
inorder(root->left);
cout<<root->val<<" ";
inorder(root->right);
}
class Solution {
public:
// Node* treeToDoublyList(Node* root) {//第一种
// if(root==nullptr){
// return nullptr;
// }
// getArray(root);
// for(int i=1;i<sortPath.size();i++){
// sortPath[i]->left = sortPath[i-1];
// }
// for(int i=sortPath.size()-2;i>=0;i--){
// sortPath[i]->right = sortPath[i+1];
// }
// sortPath[0]->left = sortPath[sortPath.size()-1];
// sortPath[sortPath.size()-1]->right = sortPath[0];
//
// return sortPath[0];
// }
Node *head = nullptr;
Node *pre = nullptr;
Node* treeToDoublyList(Node* root) {
if(root==nullptr){
return nullptr;
}
inorder(root);
head->left = pre;
pre->right = head;
return head;
}
bool haveCircle(Node* head){//双指针判定是否有环
if(head==nullptr){
return false;
}
Node* ptr1 = head;
Node* ptr2 = head->right->right;
while(ptr1!=nullptr&&ptr2!=nullptr){
if(ptr1==ptr2){
return true;
}
ptr1 = ptr1->right;
ptr2 = ptr2->right->right;
}
return false;
}
private:
vector<Node*> sortPath;
void getArray(Node* root){
if(root==nullptr){
return;
}
getArray(root->left);
sortPath.push_back(root);
getArray(root->right);
}
void inorder(Node* root){
if(root==nullptr){
return;
}
inorder(root->left);
if(pre==nullptr){
head = root;
}
else{
pre->right = root;
}
root->left = pre;
pre = root;//这里不能用pre->right
inorder(root->right);
}
};
int main(){
vector<int> a = {4,2,5,1,3};
Node* root = createTree(a,0);
inorder(root);
Solution solution;
Node* head = solution.treeToDoublyList(root);
Node* ptr = head;
cout<<endl;
cout<<solution.haveCircle(head)<<endl;
// while(ptr!=nullptr){//朴素的判别方式
// cout<<ptr->val<<" ";
// ptr = ptr->right;
// }
}