二叉搜索树
二叉搜索树又称二叉排序树,它或者是一棵空树,或者是具有以下性质的二叉树:
若它的左子树不为空,则左子树上所有节点的值都小于根节点的值
若它的右子树不为空,则右子树上所有节点的值都大于根节点的值
它的左右子树也分别为二叉搜索树
初步搭建二叉搜索树
二叉搜索树节点
cpp
template<class K>
struct BSTreeNode
{
BSTreeNode(const K& key)
:_left(nullptr)
, _right(nullptr)
, _key(key)
{}
BSTreeNode<K>* _left;
BSTreeNode<K>* _right;
K _key;
};
二叉树遍历/插入/查找
cpp
template<class K>
class BSTree
{
typedef BSTreeNode<K> Node;
public:
bool Insert(const K& key)
{
if (_root == nullptr)
{
_root = new Node(key);
return true;
}
Node* cur = _root;
Node* parent = nullptr;
while (cur)
{
if (cur->_key < key)
{
cur = parent;
cur = cur->_right;
}
else if (cur->_key > key)
{
cur = parent;
cur = cur->_right;
}
else return false;
}
cur = new Node(key);
if (parent->_key < key)
parent->_right = cur;
else
parent->_left = cur;
return true;
}
void _InOrder(Node* root)
{
if (root == nullptr)
return;
_InOrder(root->_left);
cout << root->_key << " ";
_InOrder(root->_right);
}
void InOrder()
{
_InOrder(_root);
cout << endl;
}
bool Find(const K& key)
{
Node* cur = _root;
while (cur)
{
if (cur->_key < key)
cur = cur->_right;
else if (cur->_key > key)
cur = cur->_left;
else
return true;
}
return false;
}
private:
Node* _root=nullptr;
};
删除节点
一共三种情况
cpp
bool Erase(const K& key)
{
Node* parent = nullptr;
Node* cur = _root;
while (cur)
{
if (cur->_key < key)
{
parent = cur;
cur = cur->_right;
}
else if (cur->_key > key)
{
parent = cur;
cur = cur->_left;
}
else
{
//成功找到节点
if (cur->_left == nullptr)
{
if (cur == root)
{
_root = cur->_right;
}
else
{
if (parent->_right == cur)
parent->_right = cur->_right;
else
parent->_left = cur->_right;
}
delete cur;
}
else if (cur->_right == nullptr)
{
if (cur == root)
{
_root = cur->_left;
}
else
{
if (parent->_left == cur)
parent->_left = cur->_left;
else
parent->_right = cur->_left;
}
delete cur;
}
else
{
Node* rightMinParent = cur;
Node* rightMin = cur->_right;
while (rightMin->_left)
{
rightMinParent = rightMin;
rightMin = rightMin->_left;
}
cur->_key = rightMin->_key;
if (rightMin == rightMinParent->_left)
rightMinParent->_left = rightMin->_right;
else
rightMinParent->_right = rightMin->_right;
delete rightMin;
}
return true;
}
}
return false;
}
102. 二叉树的层序遍历
cpp
vector<vector<int>> levelOrder(TreeNode* root) {
vector<vector<int>> vv;
queue<TreeNode*> q;
if (root)
q.push(root);
while (!q.empty()) {
... }
vv.push_back(v);
}
return vv;
}
107. 二叉树的层序遍历 II
cpp
vector<vector<int>> levelOrderBottom(TreeNode* root) {
vector<vector<int>> vv;
queue<TreeNode*> q;
if(root)
{
q.push(root);
}
while(!q.empty())
{
//通过控制每一层的数据个数,一个循环一层数据输出
//当第n层出完了,第n+1层都进队列了,q.size()就是n+1层的数据个数,循环在继续处理
int levelsize=q.size();
vector<int> v;
for(int i=0;i<levelsize;++i)
{
TreeNode*front=q.front();
q.pop();
v.push_back(front->val);
if(front->left)
q.push(front->left);
if(front->right)
q.push(front->right);
}
vv.push_back(v);
}
reverse(vv.begin(),vv.end());
return vv;
}
236. 二叉树的最近公共祖先
cpp
bool Find(TreeNode* root, TreeNode* x)
{
if(root==NULL)
return false;
return root==x
||Find(root->left,x)
||Find(root->right,x);
}
TreeNode* lowestCommonAncestor(TreeNode* root, TreeNode* p, TreeNode* q) {
if(root==NULL)
return NULL;
if(root==p||root==q)
return root;
bool pInLeft,pInRight,qInleft,qInRight;
pInLeft=Find(root->left,p);
pInRight=!pInLeft;
qInleft=Find(root->left,q);
qInRight=!qInleft;
if((pInLeft&&qInRight)||(pInRight&&qInleft))
{
return root;
}
else if(pInLeft&&qInleft){
return lowestCommonAncestor(root->left,p,q);
}
else
{
return lowestCommonAncestor(root->right,p,q);
}
return NULL;
}
将二叉树转为双向链表
cpp
void ConvertList(TreeNode* cur,TreeNode*& prev)
{
if(cur==nullptr) return;
ConvertList(cur->left,prev);
cur->left=prev;
if(prev) prev->right=cur;
prev=cur;
ConvertList(cur->right,prev);
}
TreeNode* Convert(TreeNode* pRootOfTree) {
TreeNode*prev=nullptr;
ConvertList(pRootOfTree,prev);
TreeNode* head=pRootOfTree;
while (head&&head->left) {
head=head->left;
}
return head;
}