见一见:
template
struct node
{
node* _left;
node* _right;
KEY _key;
node(const KEY& key)
:_left(nullptr)
, _right(nullptr)
, _key(key)
{}
};
//声明:
//typedef struct node node;
//typedef node* node_pointer;
bool insert_nonRecurse(const KEY& key)
{
//a. 树为空
if (_root == nullptr)
{
_root = new node(key);
return true;
}
//b. 树不为空,按性质插入
node_pointer cur = _root;
node_pointer parent = nullptr;
//b.1 找合适位置
while (cur != nullptr)
{
if (key > cur->_key) //b.1.1 key > cur->_key --> 右遍历
{
parent = cur;
cur = cur->_right;
}
else if (key < cur->_key) //b.1.2 key < cur->_key --> 左遍历
{
parent = cur;
cur = cur->_left;
}
else //b.1.3 相等 --> false
{
return false;
}
}
//b.2 连接
cur = new node(key);
if (key > cur->_key)
{
parent->right = cur;
}
else
{
parent->_left = cur;
}
return true;
}
bool insert_recurse(node_pointer& root, const KEY& key)
{
//a. 树为空
if (root == nullptr)
{
root = new node(key);
return true;
}
//b. 树不为空
if (key > root->_key) //右遍历
{
return insert_recurse(root->_right, key);
}
else if (key < root->_key) //左遍历
{
return insert_recurse(root->_left, key);
}
else //相等 --> false
{
return false;
}
}
void inOrder(node_pointer root)
{
if (root == nullptr)
return;
_inOrder(root->_left);
cout << root->_key << " ";
_inOrder(root->_right);
}
bool find(const KEY& key)
{
node_pointer cur = _root;
while (cur != nullptr)
{
if (key > cur->_key) //右遍历
{
cur = cur->_right;
}
else if (key < cur->_key) //左遍历
{
cur = cur->_left;
}
else
{
return true;
}
}
return false;
}
bool erase_nonRecurse(const KEY& key)
{
node_pointer parent = nullptr;
node_pointer cur = _root;
while (cur != nullptr)
{
if (key > cur->_key) //右遍历
{
parent = cur;
cur = cur->_right;
}
else if (key < cur->_key) //左遍历
{
parent = cur;
cur = cur->_left;
}
else //相等 --> 删除
{
/*被删除节点要区分是在其父节点的左子树还是右子树中*/
if (cur->_left == nullptr) //被删节点左子树为空 && 被删节点左右子树都为空
{
if (cur == _root) //头节点处理
{
_root = cur->_right;
}
else
{
if (parent->_left == cur) //被删除节点在父节点左子树
{
parent->_left = cur->_right;
}
else //被删除节点在父节点右子树
{
parent->_right = 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_pointer min_right = cur->_right;
node_pointer parent_min_right = cur;
while (min_right->_left) //取右子树最小值节点
{
parent_min_right = min_right;
min_right = min_right->_left;
}
swap(min_right->_key, cur->_key);
//被删除节点父节点和其节点右子树连接(支持原因:右子树最小值只可能拥有右子树不可能拥有左子树)
if (parent_min_right->_left == min_right) //右子树最小值节点(被删除节点)在其父节点左子树
{
parent_min_right->_left = min_right->_right;
}
else //右子树最小值节点在其父节点右子树
{
parent_min_right->_right = min_right->_right;
}
delete min_right;
}
return true;
}
}
return false;
}
bool _erase_Recurse(node_pointer& root, const KEY& key)
{
if (root == nullptr)
{
return false;
}
if (key > root->_key) //右遍历
{
_erase_Recurse(root->_right, key);
}
else if (key < root->_key) //左遍历
{
_erase_Recurse(root->_left, key);
}
else //相等 --> 删除
{
node_pointer deleted_node = root;
if (root->_left == nullptr) //被删节点左子树为空 && 被删节点左右子树都为空
{
root = root->_right;
}
else if (root->_right == nullptr) //被删节点右子树为空 && 被删节点左右子树都为空
{
root = root->_left;
}
else //左右子树都不为空(策略:右子树最小值和被删节点交换)
{
node_pointer min_right = root->_right;
while (min_right->_left) //取被删节点右子树最小值
{
min_right = min_right->_left;
}
//交换数值
swap(min_right->_key, root->_key);
return _erase_Recurse(root->_right, key); //交换后删除值为min_right节点(右子树遍历)
}
delete deleted_node;
return true;
}
}
首先考虑被删节点的左右子树都不为空&&被删节点的左子树为空右子树不为空&&被删节点的右子树为空左子树不为空&&被删节点左右子树都不为空四种情况(其中,被删节点的左子树为空右子树不为空&&被删节点的右子树为空左子树不为空包含被删节点的左右子树都不为空的情况)
binary_search_tree(const binary_search_tree& tree)
{
_root = _copy(tree._root);
}
node_pointer _copy(node_pointer root)
{
if (root == nullptr)
{
return nullptr;
}
node_pointer new_node = new node(root->_key);
new_node->_left = _copy(root->_left);
new_node->_right = _copy(root->_right);
return new_node;
}
#pragma once
#include
#include
#include
using namespace std;
//模拟实现二叉搜索树
namespace my_tree
{
template
struct node
{
node* _left;
node* _right;
KEY _key;
node(const KEY& key)
:_left(nullptr)
,_right(nullptr)
,_key(key)
{}
};
template
class binary_search_tree
{
private:
typedef node node;
typedef node* node_pointer;
public:
binary_search_tree()
:_root(nullptr)
{}
binary_search_tree(const binary_search_tree& tree)
{
_root = _copy(tree._root);
}
binary_search_tree& operator=(binary_search_tree& tree)
{
_swap(_root, tree._root);
return *this;
}
~binary_search_tree()
{
_destory(_root);
}
void _destory(node_pointer root)
{
if (root == nullptr)
{
return;
}
_destory(root->_left);
_destory(root->_right);
delete root;
root = nullptr;
}
bool insert_nonRecurse(const KEY& key)
{
//a. 树为空
if (_root == nullptr)
{
_root = new node(key);
return true;
}
//b. 树不为空,按性质插入
node_pointer cur = _root;
node_pointer parent = nullptr;
//b.1 找合适位置
while (cur != nullptr)
{
if (key > cur->_key) //b.1.1 key > cur->_key --> 右遍历
{
parent = cur;
cur = cur->_right;
}
else if (key < cur->_key) //b.1.2 key < cur->_key --> 左遍历
{
parent = cur;
cur = cur->_left;
}
else //b.1.3 相等 --> false
{
return false;
}
}
//b.2 连接
cur = new node(key);
if (key > parent->_key) //b.2.1 key > parent_key --> 右连接
{
parent->_right = cur;
}
else //b.2.2 key < parent_key --> 左连接
{
parent->_left = cur;
}
return true;
}
bool insert_recurse(const KEY& key)
{
return _insert_recurse(_root, key);
}
bool find(const KEY& key)
{
node_pointer cur = _root;
while (cur != nullptr)
{
if (key > cur->_key)
{
cur = cur->_right;
}
else if (key < cur->_key)
{
cur = cur->_left;
}
else
{
return true;
}
}
return false;
}
bool erase_nonRecurse(const KEY& key)
{
node_pointer parent = nullptr;
node_pointer cur = _root;
while (cur != nullptr)
{
if (key > cur->_key) //右遍历
{
parent = cur;
cur = cur->_right;
}
else if (key < cur->_key) //左遍历
{
parent = cur;
cur = cur->_left;
}
else //相等 --> 删除
{
/*被删除节点要区分是在其父节点的左子树还是右子树中*/
if (cur->_left == nullptr) //左子树为空 && 左右子树都为空
{
if (cur == _root) //头节点处理
{
_root = cur->_right;
}
else
{
if (parent->_left == cur) //被删除节点在父节点左子树
{
parent->_left = cur->_right;
}
else //被删除节点在父节点右子树
{
parent->_right = 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_pointer min_right = cur->_right;
node_pointer parent_min_right = cur;
while (min_right->_left) //取右子树最小值节点
{
parent_min_right = min_right;
min_right = min_right->_left;
}
swap(min_right->_key, cur->_key);
//被删除节点父节点和其节点右子树连接(支持原因:右子树最小值只可能拥有右子树不可能拥有左子树)
if (parent_min_right->_left == min_right) //右子树最小值节点(被删除节点)在其父节点左子树
{
parent_min_right->_left = min_right->_right;
}
else //右子树最小值节点在其父节点右子树
{
parent_min_right->_right = min_right->_right;
}
delete min_right;
}
return true;
}
}
return false;
}
bool erase_Recurse(const KEY& key)
{
return _erase_Recurse(_root, key);
}
void inOrder()
{
_inOrder(_root);
cout << endl;
}
private:
void _inOrder(node_pointer root)
{
if (root == nullptr)
return;
_inOrder(root->_left);
cout << root->_key << " ";
_inOrder(root->_right);
}
bool _insert_recurse(node_pointer& root, const KEY& key)
{
//a. 树为空
if (root == nullptr)
{
root = new node(key);
return true;
}
//b. 树不为空
if (key > root->_key) //右遍历
{
return _insert_recurse(root->_right, key);
}
else if (key < root->_key) //左遍历
{
return _insert_recurse(root->_left, key);
}
else //相等 --> false
{
return false;
}
}
bool _erase_Recurse(node_pointer& root, const KEY& key)
{
if (root == nullptr)
{
return false;
}
if (key > root->_key) //右遍历
{
_erase_Recurse(root->_right, key);
}
else if (key < root->_key) //左遍历
{
_erase_Recurse(root->_left, key);
}
else //相等 --> 删除
{
node_pointer deleted_node = root;
if (root->_left == nullptr) //被删节点左子树为空 && 被删节点左右子树都为空
{
root = root->_right;
}
else if (root->_right == nullptr) //被删节点右子树为空 && 被删节点左右子树都为空
{
root = root->_left;
}
else //左右子树都不为空
{
node_pointer min_right = root->_right;
while (min_right->_left) //取被删节点右子树最小值
{
min_right = min_right->_left;
}
//交换数值
swap(min_right->_key, root->_key);
return _erase_Recurse(root->_right, key);
}
delete deleted_node;
return true;
}
}
node_pointer _copy(node_pointer root)
{
if (root == nullptr)
{
return nullptr;
}
node_pointer new_node = new node(root->_key);
new_node->_left = _copy(root->_left);
new_node->_right = _copy(root->_right);
return new_node;
}
void _swap(node_pointer& self, node_pointer& other)
{
node_pointer tmp = self;
self = other;
other = tmp;
}
private:
node_pointer _root;
};
}
增删查改时间复杂度:O(N)
namespace key_value
{
template
struct node
{
struct node* _left;
struct node* _right;
KEY _key;
VALUE _value;
node(const KEY& key, const VALUE& value)
:_left(nullptr)
, _right(nullptr)
, _key(key)
, _value(value)
{}
};
template
class binary_search_tree
{
private:
typedef struct node node;
typedef node* node_pointer;
public:
binary_search_tree()
:_root(nullptr)
{}
~binary_search_tree()
{
_destory(_root);
}
void _destory(node_pointer root)
{
if (root == nullptr)
{
return;
}
_destory(root->_left);
_destory(root->_right);
delete root;
root = nullptr;
}
bool insert_nonRecurse(const KEY& key, const VALUE& value)
{
//a. 树为空
if (_root == nullptr)
{
_root = new node(key, value);
return true;
}
//b. 树不为空,按性质插入
node_pointer cur = _root;
node_pointer parent = nullptr;
//b.1 找合适位置
while (cur != nullptr)
{
if (key > cur->_key) //b.1.1 key > cur->_key --> 右遍历
{
parent = cur;
cur = cur->_right;
}
else if (key < cur->_key) //b.1.2 key < cur->_key --> 左遍历
{
parent = cur;
cur = cur->_left;
}
else //b.1.3 相等 --> false
{
return false;
}
}
//b.2 连接
cur = new node(key, value);
if (key > parent->_key) //b.2.1 key > parent_key --> 右连接
{
parent->_right = cur;
}
else //b.2.2 key < parent_key --> 左连接
{
parent->_left = cur;
}
return true;
}
node_pointer find(const KEY& key)
{
node_pointer cur = _root;
while (cur != nullptr)
{
if (key > cur->_key)
{
cur = cur->_right;
}
else if (key < cur->_key)
{
cur = cur->_left;
}
else
{
return cur;
}
}
return nullptr;
}
bool erase_nonRecurse(const KEY& key)
{
node_pointer parent = nullptr;
node_pointer cur = _root;
while (cur != nullptr)
{
if (key > cur->_key) //右遍历
{
parent = cur;
cur = cur->_right;
}
else if (key < cur->_key) //左遍历
{
parent = cur;
cur = cur->_left;
}
else //相等 --> 删除
{
/*被删除节点要区分是在其父节点的左子树还是右子树中*/
if (cur->_left == nullptr) //左子树为空 && 左右子树都为空
{
if (cur == _root) //头节点处理
{
_root = cur->_right;
}
else
{
if (parent->_left == cur) //被删除节点在父节点左子树
{
parent->_left = cur->_right;
}
else //被删除节点在父节点右子树
{
parent->_right = 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_pointer min_right = cur->_right;
node_pointer parent_min_right = cur;
while (min_right->_left) //取右子树最小值节点
{
parent_min_right = min_right;
min_right = min_right->_left;
}
swap(min_right->_key, cur->_key);
//被删除节点父节点和其节点右子树连接(支持原因:右子树最小值只可能拥有右子树不可能拥有左子树)
if (parent_min_right->_left == min_right) //右子树最小值节点(被删除节点)在其父节点左子树
{
parent_min_right->_left = min_right->_right;
}
else //右子树最小值节点在其父节点右子树
{
parent_min_right->_right = min_right->_right;
}
delete min_right;
}
return true;
}
}
return false;
}
void inOrder()
{
_inOrder(_root);
cout << endl;
}
private:
void _inOrder(node_pointer root)
{
if (root == nullptr)
return;
_inOrder(root->_left);
cout << root->_key << " " << root->_value << endl;
_inOrder(root->_right);
}
private:
node_pointer _root;
};
void test()
{
binary_search_tree dict;
dict.insert_nonRecurse("apple", "苹果");
dict.insert_nonRecurse("banana", "香蕉");
dict.insert_nonRecurse("pear", "梨子");
dict.insert_nonRecurse("orange", "橙子");
dict.insert_nonRecurse("strawberry", "草莓");
dict.insert_nonRecurse("pitaya", "火龙果");
dict.insert_nonRecurse("tangerine", "橘子");
string str;
while (cin >> str)
{
node* ret = dict.find(str);
if (ret != nullptr)
cout << ret->_key << "->" << ret->_value << endl;
else
cout << "找不到" << endl;
}
}
}
namespace key_value
{
template
struct node
{
struct node* _left;
struct node* _right;
KEY _key;
VALUE _value;
node(const KEY& key, const VALUE& value)
:_left(nullptr)
, _right(nullptr)
, _key(key)
, _value(value)
{}
};
template
class binary_search_tree
{
private:
typedef struct node node;
typedef node* node_pointer;
public:
binary_search_tree()
:_root(nullptr)
{}
~binary_search_tree()
{
_destory(_root);
}
void _destory(node_pointer root)
{
if (root == nullptr)
{
return;
}
_destory(root->_left);
_destory(root->_right);
delete root;
root = nullptr;
}
bool insert_nonRecurse(const KEY& key, const VALUE& value)
{
//a. 树为空
if (_root == nullptr)
{
_root = new node(key, value);
return true;
}
//b. 树不为空,按性质插入
node_pointer cur = _root;
node_pointer parent = nullptr;
//b.1 找合适位置
while (cur != nullptr)
{
if (key > cur->_key) //b.1.1 key > cur->_key --> 右遍历
{
parent = cur;
cur = cur->_right;
}
else if (key < cur->_key) //b.1.2 key < cur->_key --> 左遍历
{
parent = cur;
cur = cur->_left;
}
else //b.1.3 相等 --> false
{
return false;
}
}
//b.2 连接
cur = new node(key, value);
if (key > parent->_key) //b.2.1 key > parent_key --> 右连接
{
parent->_right = cur;
}
else //b.2.2 key < parent_key --> 左连接
{
parent->_left = cur;
}
return true;
}
node_pointer find(const KEY& key)
{
node_pointer cur = _root;
while (cur != nullptr)
{
if (key > cur->_key)
{
cur = cur->_right;
}
else if (key < cur->_key)
{
cur = cur->_left;
}
else
{
return cur;
}
}
return nullptr;
}
bool erase_nonRecurse(const KEY& key)
{
node_pointer parent = nullptr;
node_pointer cur = _root;
while (cur != nullptr)
{
if (key > cur->_key) //右遍历
{
parent = cur;
cur = cur->_right;
}
else if (key < cur->_key) //左遍历
{
parent = cur;
cur = cur->_left;
}
else //相等 --> 删除
{
/*被删除节点要区分是在其父节点的左子树还是右子树中*/
if (cur->_left == nullptr) //左子树为空 && 左右子树都为空
{
if (cur == _root) //头节点处理
{
_root = cur->_right;
}
else
{
if (parent->_left == cur) //被删除节点在父节点左子树
{
parent->_left = cur->_right;
}
else //被删除节点在父节点右子树
{
parent->_right = 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_pointer min_right = cur->_right;
node_pointer parent_min_right = cur;
while (min_right->_left) //取右子树最小值节点
{
parent_min_right = min_right;
min_right = min_right->_left;
}
swap(min_right->_key, cur->_key);
//被删除节点父节点和其节点右子树连接(支持原因:右子树最小值只可能拥有右子树不可能拥有左子树)
if (parent_min_right->_left == min_right) //右子树最小值节点(被删除节点)在其父节点左子树
{
parent_min_right->_left = min_right->_right;
}
else //右子树最小值节点在其父节点右子树
{
parent_min_right->_right = min_right->_right;
}
delete min_right;
}
return true;
}
}
return false;
}
void inOrder()
{
_inOrder(_root);
cout << endl;
}
private:
void _inOrder(node_pointer root)
{
if (root == nullptr)
return;
_inOrder(root->_left);
cout << root->_key << " " << root->_value << endl;
_inOrder(root->_right);
}
private:
node_pointer _root;
};
void test()
{
string arr[] = { "西瓜", "西瓜", "苹果", "西瓜", "苹果", "苹果", "西瓜", "苹果", "香蕉", "苹果", "香蕉", "梨" };
key_value::binary_search_tree countTree;
for (auto str : arr)
{
auto ret = countTree.find(str);
if (ret == nullptr)
{
countTree.insert_nonRecurse(str, 1);
}
else
{
ret->_value++;
}
}
countTree.inOrder();
}
}