首先我简单介绍一下搜索二叉树的概念及有关性质,纯属个人观点,如有错误,欢迎不吝赐教。
1、搜索二叉树的概念:根结点的左子树都小于它,它的右子树都大于它,且它的左子树与右子树都是搜素二叉树。
2、二叉搜索树(搜索二叉树):搜索二叉树即是排序二叉树,中序遍历它的结果是有序的(升序)。
- 每个节点都有一个作为搜索依据的关键码(key),所有节点的关键码互不相同。
- 左子树上所有节点的关键码(key)都小于根节点的关键码(key)。
- 右子树上所有节点的关键码(key)都大于根节点的关键码(key)。
- 左右子树都是二叉搜索树。
搜索二叉树的非递归插入:
思想:
代码如下:
//非递归插入
bool
Insert(
const
K
&
key
,
const
V
&
value
)
{
if
(_root ==
NULL
)
{
_root =
new
Node
(
key
,
value
);
return
true
;
}
Node
* parent =
NULL
;
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
{
return
false
;
}
}
if
(parent->_key <
key
)
parent->_right =
new
Node
(
key
,
value
);
else
parent->_left =
new
Node
(
key
,
value
);
return
true
;
}
递归插入算法如下:
//递归插入
bool
InsertR(
const
K
&
key
,
const
V
&
value
)
{
return
_InsertR(_root,
key
,
value
);
}
bool
_InsertR(
Node
*&
root
,
const
K
&
key
,
const
V
&
value
)
{
if
(
root
==
NULL
)
{
root
=
new
Node
(
key
,
value
);
return
true
;
}
if
(
root
->_key >
key
)
return
_InsertR(
root
->_left,
key
,
value
);
else
if
(
root
->_key <
key
)
return
_InsertR(
root
->_right,
key
,
value
);
else
return
false
;
}
查找指定节点(非递归方法):
Node
* 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
cur;
}
}
return
NULL
;
}
递归方法查找指定的节点:
Node
* 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
cur;
}
}
return
NULL
;
}
删除指定节点(非递归方法):
//删除指定节点
bool
Remove(
const
K
&
key
)
{
Node
* parent =
NULL
;
Node
* cur = _root;
//cur不为空
while
(cur)
{
if
(cur->_key <
key
)
{
parent = cur;
cur = cur->_right;
}
else
if
(cur->_key >
key
)
{
parent = cur;
cur = cur->_left;
}
else
{
break
;
//相等时直接break掉
}
}
//cur为空时,没有找到指定删除的节点,返回false
if
(cur ==
NULL
)
{
return
false
;
}
//cur的左子树为空
if
(cur->_left ==
NULL
)
{
//parent==NULL,说明cur是根节点,要删除cur(由上步可知cur的左子树为空),所以要删除cur,只需要让_root指向cur->right即可。
if
(parent ==
NULL
)
{
_root = cur->_right;
}
else
{
if
(parent->_left == cur)
parent->_left = cur->_right;
else
parent->_right = cur->_right;
}
delete
cur;
}
else
if
(cur->_right ==
NULL
)
{
if
(parent ==
NULL
)
{
_root = cur->_left;
}
else
{
if
(parent->_left == cur)
parent->_left = cur->_left;
else
parent->_right = cur->_left;
}
delete
cur;
}
else
{
// 找右子树里面的最左结点
parent = cur;
Node
* subLeft = cur->_right;
while
(subLeft->_left)
{
parent = subLeft;
subLeft = subLeft->_left;
}
cur->_key = subLeft->_key;
cur->_value = subLeft->_value;
if
(parent->_left == subLeft)
parent->_left = subLeft->_right;
else
parent->_right = subLeft->_right;
delete
subLeft;
}
return
true
;
}
递归删除:
//递归删除
bool
RemoveR(
const
K
&
key
)
{
return
_RemoveR(_root,
key
);
}
bool
_RemoveR(
Node
*&
root
,
const
K
&
key
)
{
if
(
root
==
NULL
)
return
false
;
if
(
root
->_key >
key
)
{
return
_RemoveR(
root
->_left,
key
);
}
else
if
(
root
->_key <
key
)
{
return
_RemoveR(
root
->_right,
key
);
}
else
{
if
(
root
->_left ==
NULL
)
{
root
=
root
->_right;
}
else
if
(
root
->_right ==
NULL
)
{
root
=
root
->_left;
}
else
{
}
}
return
true
;
}
#pragma once
#include<iostream>
#include<string>
template<class K,class V>
//构造搜索化二叉树结构体
struct BSTreeNode
{
K _key;
V _value;
BSTreeNode<K, V> *_left;
BSTreeNode<K, V> *_right;
//构造函数
BSTreeNode(const K& key,const V& value)
:_key(key)
,_value(value)
,_left(NULL)
,_right(NULL)
{}
};
template<class K, class V>
class BSTree
{
typedef BSTreeNode<K, V> Node;
public:
BSTree()
:_root(NULL)
{}
//非递归插入
bool Insert(const K& key, const V& value)
{
if (_root == NULL)
{
_root = new Node(key, value);
return true;
}
Node* parent = NULL;
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
{
return false;
}
}
if (parent->_key < key)
parent->_right = new Node(key, value);
else
parent->_left = new Node(key, value);
return true;
}
//递归插入
bool InsertR(const K& key, const V& value)
{
return _InsertR(_root, key, value);
}
bool _InsertR(Node*& root, const K& key, const V& value)
{
if (root == NULL)
{
root = new Node(key, value);
return true;
}
if (root->_key > key)
return _InsertR(root->_left, key, value);
else if (root->_key < key)
return _InsertR(root->_right, key, value);
else
return false;
}
Node* 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 cur;
}
}
return NULL;
}
Node* FindR(const K& key)
{
return _FindR(key);
}
Node* _FindR(Node* root, const K& key)
{
if (root == NULL)
{
return NULL;
}
if (root->_key < key)
{
return _FindR(root->_right, key);
}
else if (root->_key > key)
{
return _FindR(root->_left, key);
}
else
{
return root;
}
}
//删除指定节点
bool Remove(const K& key)
{
Node* parent = NULL;
Node* cur = _root;
//cur不为空
while (cur)
{
if (cur->_key < key)
{
parent = cur;
cur = cur->_right;
}
else if (cur->_key > key)
{
parent = cur;
cur = cur->_left;
}
else
{
break;//相等时直接break掉
}
}
//cur为空时,没有找到指定删除的节点,返回false
if (cur == NULL)
{
return false;
}
//cur的左子树为空
if (cur->_left == NULL)
{
//parent==NULL,说明cur是根节点,要删除cur(由上步可知cur的左子树为空),所以要删除cur,只需要让_root指向cur->right即可。
if (parent == NULL)
{
_root = cur->_right;
}
else
{
if (parent->_left == cur)
parent->_left = cur->_right;
else
parent->_right = cur->_right;
}
delete cur;
}
else if (cur->_right == NULL)
{
if (parent == NULL)
{
_root = cur->_left;
}
else
{
if (parent->_left == cur)
parent->_left = cur->_left;
else
parent->_right = cur->_left;
}
delete cur;
}
else
{
// 找右子树里面的最左结点
parent = cur;
Node* subLeft = cur->_right;
while (subLeft->_left)
{
parent = subLeft;
subLeft = subLeft->_left;
}
cur->_key = subLeft->_key;
cur->_value = subLeft->_value;
if (parent->_left == subLeft)
parent->_left = subLeft->_right;
else
parent->_right = subLeft->_right;
delete subLeft;
}
return true;
}
//递归删除
bool RemoveR(const K& key)
{
return _RemoveR(_root, key);
}
bool _RemoveR(Node*& root, const K& key)
{
if (root == NULL)
return false;
if (root->_key > key)
{
return _RemoveR(root->_left, key);
}
else if (root->_key < key)
{
return _RemoveR(root->_right, key);
}
else
{
if (root->_left == NULL)
{
root = root->_right;
}
else if (root->_right == NULL)
{
root = root->_left;
}
else
{
}
}
return true;
}
//中序遍历
void InOrder()
{
_InOrder(_root);
cout << endl;
}
void _InOrder(Node* root)
{
if (root == NULL)
return;
}
protected:
Node* _root;
};
void TestTree()
{
BSTree<int, int> t;
int a[] = { 5, 3, 4, 1, 7, 8, 2, 6, 0, 9 };
for (size_t i = 0; i < sizeof(a) / sizeof(a[0]); ++i)
{
t.Insert(a[i], i);
}
t.InOrder();
cout << "IsBlance?" << t.IsBlanceTree() << endl;
t.Remove(8);
t.Remove(7);
t.Remove(2);
t.Remove(1);
t.InOrder();
t.Remove(0);
t.Remove(1);
t.Remove(2);
t.Remove(3);
t.Remove(4);
t.Remove(5);
t.Remove(6);
t.Remove(7);
t.Remove(8);
t.Remove(9);
t.InOrder();
}
void TestDict()
{
BSTree<string, string> dict;
dict.Insert("Tree", "树");
dict.Insert("Sort", "哈希");
dict.Insert("Hash", "排序");
dict.InOrder();
BSTreeNode<string, string>* ret = dict.Find("Sort");
ret->_value = "排序";
ret = dict.Find("Hash");
ret->_value = "哈希";
dict.InOrder();
}
#include<iostream>
#include<string>
template<class K,class V>
//构造搜索化二叉树结构体
struct BSTreeNode
{
K _key;
V _value;
BSTreeNode<K, V> *_left;
BSTreeNode<K, V> *_right;
//构造函数
BSTreeNode(const K& key,const V& value)
:_key(key)
,_value(value)
,_left(NULL)
,_right(NULL)
{}
};
template<class K, class V>
class BSTree
{
typedef BSTreeNode<K, V> Node;
public:
BSTree()
:_root(NULL)
{}
//非递归插入
bool Insert(const K& key, const V& value)
{
if (_root == NULL)
{
_root = new Node(key, value);
return true;
}
Node* parent = NULL;
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
{
return false;
}
}
if (parent->_key < key)
parent->_right = new Node(key, value);
else
parent->_left = new Node(key, value);
return true;
}
//递归插入
bool InsertR(const K& key, const V& value)
{
return _InsertR(_root, key, value);
}
bool _InsertR(Node*& root, const K& key, const V& value)
{
if (root == NULL)
{
root = new Node(key, value);
return true;
}
if (root->_key > key)
return _InsertR(root->_left, key, value);
else if (root->_key < key)
return _InsertR(root->_right, key, value);
else
return false;
}
Node* 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 cur;
}
}
return NULL;
}
Node* FindR(const K& key)
{
return _FindR(key);
}
Node* _FindR(Node* root, const K& key)
{
if (root == NULL)
{
return NULL;
}
if (root->_key < key)
{
return _FindR(root->_right, key);
}
else if (root->_key > key)
{
return _FindR(root->_left, key);
}
else
{
return root;
}
}
//删除指定节点
bool Remove(const K& key)
{
Node* parent = NULL;
Node* cur = _root;
//cur不为空
while (cur)
{
if (cur->_key < key)
{
parent = cur;
cur = cur->_right;
}
else if (cur->_key > key)
{
parent = cur;
cur = cur->_left;
}
else
{
break;//相等时直接break掉
}
}
//cur为空时,没有找到指定删除的节点,返回false
if (cur == NULL)
{
return false;
}
//cur的左子树为空
if (cur->_left == NULL)
{
//parent==NULL,说明cur是根节点,要删除cur(由上步可知cur的左子树为空),所以要删除cur,只需要让_root指向cur->right即可。
if (parent == NULL)
{
_root = cur->_right;
}
else
{
if (parent->_left == cur)
parent->_left = cur->_right;
else
parent->_right = cur->_right;
}
delete cur;
}
else if (cur->_right == NULL)
{
if (parent == NULL)
{
_root = cur->_left;
}
else
{
if (parent->_left == cur)
parent->_left = cur->_left;
else
parent->_right = cur->_left;
}
delete cur;
}
else
{
// 找右子树里面的最左结点
parent = cur;
Node* subLeft = cur->_right;
while (subLeft->_left)
{
parent = subLeft;
subLeft = subLeft->_left;
}
cur->_key = subLeft->_key;
cur->_value = subLeft->_value;
if (parent->_left == subLeft)
parent->_left = subLeft->_right;
else
parent->_right = subLeft->_right;
delete subLeft;
}
return true;
}
//递归删除
bool RemoveR(const K& key)
{
return _RemoveR(_root, key);
}
bool _RemoveR(Node*& root, const K& key)
{
if (root == NULL)
return false;
if (root->_key > key)
{
return _RemoveR(root->_left, key);
}
else if (root->_key < key)
{
return _RemoveR(root->_right, key);
}
else
{
if (root->_left == NULL)
{
root = root->_right;
}
else if (root->_right == NULL)
{
root = root->_left;
}
else
{
}
}
return true;
}
//中序遍历
void InOrder()
{
_InOrder(_root);
cout << endl;
}
void _InOrder(Node* root)
{
if (root == NULL)
return;
}
protected:
Node* _root;
};
void TestTree()
{
BSTree<int, int> t;
int a[] = { 5, 3, 4, 1, 7, 8, 2, 6, 0, 9 };
for (size_t i = 0; i < sizeof(a) / sizeof(a[0]); ++i)
{
t.Insert(a[i], i);
}
t.InOrder();
cout << "IsBlance?" << t.IsBlanceTree() << endl;
t.Remove(8);
t.Remove(7);
t.Remove(2);
t.Remove(1);
t.InOrder();
t.Remove(0);
t.Remove(1);
t.Remove(2);
t.Remove(3);
t.Remove(4);
t.Remove(5);
t.Remove(6);
t.Remove(7);
t.Remove(8);
t.Remove(9);
t.InOrder();
}
void TestDict()
{
BSTree<string, string> dict;
dict.Insert("Tree", "树");
dict.Insert("Sort", "哈希");
dict.Insert("Hash", "排序");
dict.InOrder();
BSTreeNode<string, string>* ret = dict.Find("Sort");
ret->_value = "排序";
ret = dict.Find("Hash");
ret->_value = "哈希";
dict.InOrder();
}