This commit is contained in:
Lenyiin 2024-09-14 13:45:51 +08:00
commit c90d4b1c3c
34 changed files with 1659 additions and 0 deletions

586
Linux/BSTree.hpp Normal file
View File

@ -0,0 +1,586 @@
#pragma once
#include <iostream>
#include <stack>
#include <queue>
namespace Lenyiin
{
template <class K, class V>
struct BSTreeNode
{
BSTreeNode(const K &key = K(), const V &value = V())
: _key(key), _value(value), _left(nullptr), _right(nullptr)
{
}
K _key;
V _value;
BSTreeNode<K, V> *_left;
BSTreeNode<K, V> *_right;
};
template <class K, class V>
class BSTree
{
private:
typedef BSTreeNode<K, V> Node;
Node *_Copy(Node *root)
{
if (root == nullptr)
{
return nullptr;
}
Node *cur = new Node(root->_key, root->_value);
cur->_left = _Copy(root->_left);
cur->_right = _Copy(root->_right);
return cur;
}
public:
// 默认构造
BSTree()
: _root(nullptr)
{
}
// 拷贝构造
BSTree(const BSTree<K, V> &tree)
{
_root = _Copy(tree._root);
}
// 非递归插入
// bool Insert(const K& key, const V& value)
//{
// // 如果根为空, 直接插入
// if (_root == nullptr)
// {
// _root = new Node(key, value);
// return true;
// }
// // 如果根不为空, 找到插入位置
// Node* parent = nullptr;
// Node* cur = _root;
// while (cur)
// {
// if (cur->_key > key)
// {
// parent = cur;
// cur = cur->_left;
// }
// else if (cur->_key < key)
// {
// parent = cur;
// cur = cur->_right;
// }
// else
// {
// return false; // 如果相等, 表示我已经有了, 不需要插入了
// }
// }
// // 插入节点
// cur = new Node(key, value);
// if (parent->_key > key)
// {
// parent->_left = cur;
// }
// else
// {
// parent->_right = cur;
// }
// return true;
//}
// 递归插入
// 辅助函数
Node *_insert(Node *root, const K &key, const V &value)
{
if (root == nullptr)
{
return new Node(key, value);
}
if (key < root->_key)
{
root->_left = _insert(root->_left, key, value);
}
else if (key > root->_key)
{
root->_right = _insert(root->_right, key, value);
}
return root;
}
// 插入
void Insert(const K &key, const V &value)
{
_root = _insert(_root, key, value);
}
// 非递归查找节点
// Node* Find(const K& key)
//{
// Node* cur = _root;
// while (cur)
// {
// if (cur->_key > key)
// {
// cur = cur->_left;
// }
// else if (cur->_key < key)
// {
// cur = cur->_right;
// }
// else
// {
// return cur;
// }
// }
// return nullptr;
//}
// 递归查找节点
// 辅助函数
Node *_find(Node *root, const K &key)
{
if (root == nullptr || root->_key == key)
{
return root;
}
if (key < root->_key)
{
return _find(root->_left, key);
}
else
{
return _find(root->_right, key);
}
}
// 查找节点
Node *Find(const K &key)
{
return _find(_root, key);
}
// 非递归删除节点
// bool Erase(const K& key)
//{
// // 找到要删除的节点
// Node* parent = nullptr;
// Node* cur = _root;
// while (cur)
// {
// if (cur->_key > key)
// {
// parent = cur;
// cur = cur->_left;
// }
// else if (cur->_key < key)
// {
// parent = cur;
// cur = cur->_right;
// }
// else
// {
// break;
// }
// }
// // 没找到
// if (cur == nullptr)
// {
// return false;
// }
// // 找到了
// // 1. 要删除的节点没有左孩子
// 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;
// }
// // 2. 要删除的节点没有右孩子
// 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;
// }
// // 3. 左右都不为空, 不能直接删除, 使用替换法删除
// // 可以找左子树的最大节点或者右子树的最小节点去替代它
// else
// {
// // 右子树最小节点
// Node* rightMinParent = cur;
// Node* rightMin = cur->_right;
// while (rightMin->_left)
// {
// rightMinParent = rightMin;
// rightMin = rightMin->_left;
// }
// // 替换删除的节点
// std::swap(cur->_key, rightMin->_key);
// std::swap(cur->_value, rightMin->_value);
// // 把问题转换成删除 rightMin
// if (rightMinParent->_left == rightMin)
// {
// rightMinParent->_left = rightMin->_right;
// }
// else
// {
// rightMinParent->_right = rightMin->_right;
// }
// delete rightMin;
// }
// return true;
//}
// 递归删除节点
// 辅助函数
Node *_erase(Node *root, const K &key)
{
if (root == nullptr)
{
return root;
}
if (key < root->_key)
{
root->_left = _erase(root->_left, key);
}
else if (key > root->_key)
{
root->_right = _erase(root->_right, key);
}
else
{
if (root->_left == nullptr)
{
Node *ret = root->_right;
delete root;
return ret;
}
if (root->_right == nullptr)
{
Node *ret = root->_left;
delete root;
return ret;
}
Node *minNode = getMin(root->_right);
root->_key = minNode->_key;
root->_right = _erase(root->_right, minNode->_key);
}
return root;
}
Node *getMin(Node *node)
{
while (node->_left != nullptr)
{
node = node->_left;
}
return node;
}
// 删除节点
void Erase(const K &key)
{
_erase(_root, key);
}
// 递归中序遍历
// 辅助函数
// void _InOrder(Node* root)
//{
// if (root == nullptr)
// {
// return;
// }
// _InOrder(root->_left);
// //std::cout << root->_key << " : " << root->_value << std::endl;
// std::cout << root->_key << " ";
// _InOrder(root->_right);
//}
// void InOrder()
//{
// _InOrder(_root);
// std::cout << std::endl;
// }
// 非递归中序遍历
void InOrder()
{
std::stack<Node *> stack;
Node *cur = _root;
while (cur != nullptr || !stack.empty())
{
// 找到最左边的节点
while (cur != nullptr)
{
stack.push(cur);
cur = cur->_left;
}
// 处理当前节点
cur = stack.top();
stack.pop();
std::cout << cur->_key << " ";
// 转向右子树
cur = cur->_right;
}
std::cout << std::endl;
}
// 递归前序遍历
// 辅助函数
// void _PreOrder(Node* root)
//{
// if (root == nullptr)
// {
// return;
// }
// std::cout << root->_key << " "; // 访问根节点
// _PreOrder(root->_left); // 访问左子树
// _PreOrder(root->_right); // 访问右子树
//}
// void PreOrder()
//{
// _PreOrder(_root);
// std::cout << std::endl;
// }
// 非递归前序遍历
void PreOrder()
{
if (_root == nullptr)
{
return;
}
std::stack<Node *> stack;
stack.push(_root);
while (!stack.empty())
{
Node *cur = stack.top();
stack.pop();
std::cout << cur->_key << " "; // 访问当前节点
// 先压入右子树再压入左子树(确保左子树先处理)
if (cur->_right != nullptr)
{
stack.push(cur->_right);
}
if (cur->_left != nullptr)
{
stack.push(cur->_left);
}
}
std::cout << std::endl;
}
// 递归后序遍历
// 辅助函数
// void _PostOrder(Node* root) {
// if (root == nullptr)
// {
// return;
// }
// _PostOrder(root->_left); // 访问左子树
// _PostOrder(root->_right); // 访问右子树
// std::cout << root->_key << " "; // 访问根节点
//}
// void PostOrder()
//{
// _PostOrder(_root);
// std::cout << std::endl;
// }
// 非递归后序遍历
void PostOrder()
{
if (_root == nullptr)
{
return;
}
std::stack<Node *> st;
Node *cur = _root;
Node *lastNode = nullptr; // 最近访问的节点
while (cur || !st.empty())
{
while (cur)
{
st.push(cur);
cur = cur->_left;
}
Node *top = st.top();
if ((top->_right == nullptr) || (lastNode == top->_right))
{
std::cout << top->_key << " ";
lastNode = top;
st.pop();
}
else
{
cur = top->_right;
}
}
std::cout << std::endl;
}
// 层序遍历
void LevelOrder()
{
if (_root == nullptr)
{
return;
}
std::queue<Node *> queue;
queue.push(_root);
while (!queue.empty())
{
Node *cur = queue.front();
queue.pop();
std::cout << cur->_key << " "; // 访问当前节点
if (cur->_left != nullptr)
{
queue.push(cur->_left); // 将左子树压入队列
}
if (cur->_right != nullptr)
{
queue.push(cur->_right); // 将右子树压入队列
}
}
std::cout << std::endl;
}
// 查找前驱节点
Node *findMax(Node *node)
{
while (node->_right != nullptr)
{
node = node->_right;
}
return node;
}
Node *FindPredecessor(Node *node)
{
if (node->_left != nullptr)
{
return findMax(node->_left);
}
Node *cur = _root;
Node *predecessor = nullptr;
while (cur != nullptr)
{
if (node->_key < cur->_key)
{
cur = cur->_left;
}
else if (node->_key > cur->_key)
{
predecessor = cur;
cur = cur->_right;
}
else
{
break;
}
}
return predecessor;
}
// 查找后继节点
Node *findMin(Node *node)
{
while (node->_left != nullptr)
{
node = node->_left;
}
return node;
}
Node *FindSuccessor(Node *node)
{
if (node->_right != nullptr)
{
return findMin(node->_right);
}
Node *cur = _root;
Node *successor = nullptr;
while (cur != nullptr)
{
if (node->_key < cur->_key)
{
successor = cur;
cur = cur->_left;
}
else if (node->_key > cur->_key)
{
cur = cur->_right;
}
else
{
break;
}
}
return successor;
}
private:
Node *_root = nullptr;
};
}

136
Linux/Main.cc Normal file
View File

@ -0,0 +1,136 @@
#include "BSTree.hpp"
#include <string>
using namespace Lenyiin;
void test_BSTree_1()
{
BSTree<int, int> t;
int a[] = {5, 3, 4, 1, 7, 8, 2, 6, 0, 9};
for (const auto &e : a)
{
t.Insert(e, e);
}
// 搜索二叉树的中序遍历
t.InOrder();
// 搜索二叉树的前序遍历
t.PreOrder();
// 搜索二叉树的后序遍历
t.PostOrder();
// 搜索二叉树的层序遍历
t.LevelOrder();
auto node = t.Find(5);
if (node != nullptr)
{
std::cout << node->_value << std::endl;
}
else
{
std::cout << "没找到" << std::endl;
}
auto pre = t.FindPredecessor(node);
if (pre != nullptr)
{
std::cout << node->_key << " 的前驱节点是: " << pre->_key << std::endl;
}
else
{
std::cout << "前驱节点为空" << std::endl;
}
auto suc = t.FindSuccessor(node);
if (suc != nullptr)
{
std::cout << node->_key << " 的后继节点是: " << suc->_key << std::endl;
}
else
{
std::cout << "后继节点为空" << std::endl;
}
// 1. 叶子
t.Erase(5);
t.InOrder();
// 左为空或者右为空
t.Erase(8);
t.Erase(1);
t.InOrder();
// 重复删除
t.Erase(5);
t.InOrder();
}
void test_BSTree_2()
{
BSTree<std::string, std::string> dict;
dict.Insert("sort", "排序");
dict.Insert("string", "字符串");
dict.Insert("vector", "向量");
dict.Insert("map", "映射");
dict.Insert("set", "集合");
dict.Insert("algorithm", "算法");
dict.Insert("iterator", "迭代器");
dict.Insert("stack", "");
dict.Insert("queue", "队列");
dict.Insert("list", "链表");
dict.Insert("deque", "双端队列");
dict.Insert("priority_queue", "优先级队列");
dict.Insert("binary_search", "二分查找");
dict.Insert("lower_bound", "下界");
dict.Insert("upper_bound", "上界");
dict.InOrder();
std::string str;
while (std::cin >> str)
{
BSTreeNode<std::string, std::string> *ret = dict.Find(str);
if (ret)
{
std::cout << ret->_key << ":" << ret->_value << std::endl;
}
else
{
std::cout << "没找到" << std::endl;
}
}
}
void test_BSTree_3()
{
std::string strArr[] = {"西瓜", "苹果", "西瓜", "苹果", "西瓜", "香蕉", "西瓜", "樱桃", "西瓜", "苹果",
"西瓜", "苹果", "西瓜", "香蕉", "西瓜", "樱桃", "西瓜", "苹果", "西瓜", "苹果", "西瓜", "香蕉",
"西瓜", "樱桃", "西瓜", "苹果", "西瓜", "苹果", "西瓜", "香蕉", "西瓜", "樱桃", "西瓜", "苹果",
"西瓜", "苹果", "西瓜", "香蕉", "西瓜", "樱桃", "西瓜", "苹果", "西瓜", "苹果", "西瓜", "香蕉"};
BSTree<std::string, int> countTree;
for (auto str : strArr)
{
BSTreeNode<std::string, int> *ret = countTree.Find(str);
if (ret == nullptr)
{
countTree.Insert(str, 1);
}
else
{
ret->_value++;
}
}
countTree.InOrder();
}
int main()
{
test_BSTree_1();
// test_BSTree_2();
test_BSTree_3();
return 0;
}

6
Linux/Makefile Normal file
View File

@ -0,0 +1,6 @@
main:Main.cc
g++ -o $@ $^
.PHONY:clean
clean:
rm -f main

BIN
Linux/main Normal file

Binary file not shown.

Binary file not shown.

Binary file not shown.

136
Windows_BSTree/BSTree.cpp Normal file
View File

@ -0,0 +1,136 @@
#include "BSTree.hpp"
#include <string>
using namespace Lenyiin;
void test_BSTree_1()
{
BSTree<int, int> t;
int a[] = { 5,3,4,1,7,8,2,6,0,9 };
for (const auto& e : a)
{
t.Insert(e, e);
}
// 搜索二叉树的中序遍历
t.InOrder();
// 搜索二叉树的前序遍历
t.PreOrder();
// 搜索二叉树的后序遍历
t.PostOrder();
// 搜索二叉树的层序遍历
t.LevelOrder();
auto node = t.Find(5);
if (node != nullptr)
{
std::cout << node->_value << std::endl;
}
else
{
std::cout << "没找到" << std::endl;
}
auto pre = t.FindPredecessor(node);
if (pre != nullptr)
{
std::cout << node->_key << " 的前驱节点是: " << pre->_key << std::endl;
}
else
{
std::cout << "前驱节点为空" << std::endl;
}
auto suc = t.FindSuccessor(node);
if (suc != nullptr)
{
std::cout << node->_key << " 的后继节点是: " << suc->_key << std::endl;
}
else
{
std::cout << "后继节点为空" << std::endl;
}
// 1. 叶子
t.Erase(5);
t.InOrder();
// 左为空或者右为空
t.Erase(8);
t.Erase(1);
t.InOrder();
// 重复删除
t.Erase(5);
t.InOrder();
}
void test_BSTree_2()
{
BSTree<std::string, std::string> dict;
dict.Insert("sort", "排序");
dict.Insert("string", "字符串");
dict.Insert("vector", "向量");
dict.Insert("map", "映射");
dict.Insert("set", "集合");
dict.Insert("algorithm", "算法");
dict.Insert("iterator", "迭代器");
dict.Insert("stack", "");
dict.Insert("queue", "队列");
dict.Insert("list", "链表");
dict.Insert("deque", "双端队列");
dict.Insert("priority_queue", "优先级队列");
dict.Insert("binary_search", "二分查找");
dict.Insert("lower_bound", "下界");
dict.Insert("upper_bound", "上界");
dict.InOrder();
std::string str;
while (std::cin >> str)
{
BSTreeNode<std::string, std::string>* ret = dict.Find(str);
if (ret)
{
std::cout << ret->_key << ":" << ret->_value << std::endl;
}
else
{
std::cout << "没找到" << std::endl;
}
}
}
void test_BSTree_3()
{
std::string strArr[] = { "西瓜", "苹果", "西瓜", "苹果", "西瓜", "香蕉", "西瓜", "樱桃", "西瓜", "苹果",
"西瓜", "苹果", "西瓜", "香蕉", "西瓜", "樱桃", "西瓜", "苹果", "西瓜", "苹果", "西瓜", "香蕉",
"西瓜", "樱桃", "西瓜", "苹果", "西瓜", "苹果", "西瓜", "香蕉", "西瓜", "樱桃", "西瓜", "苹果",
"西瓜", "苹果", "西瓜", "香蕉", "西瓜", "樱桃", "西瓜", "苹果", "西瓜", "苹果", "西瓜", "香蕉" };
BSTree<std::string, int> countTree;
for (auto str : strArr)
{
BSTreeNode<std::string, int>* ret = countTree.Find(str);
if (ret == nullptr)
{
countTree.Insert(str, 1);
}
else
{
ret->_value++;
}
}
countTree.InOrder();
}
int main()
{
test_BSTree_1();
//test_BSTree_2();
test_BSTree_3();
return 0;
}

578
Windows_BSTree/BSTree.hpp Normal file
View File

@ -0,0 +1,578 @@
#pragma once
#include <iostream>
#include <stack>
#include <queue>
namespace Lenyiin
{
template <class K, class V>
struct BSTreeNode
{
BSTreeNode(const K& key = K(), const V& value = V())
: _key(key), _value(value), _left(nullptr), _right(nullptr)
{
}
K _key;
V _value;
BSTreeNode<K, V>* _left;
BSTreeNode<K, V>* _right;
};
template <class K, class V>
class BSTree
{
private:
typedef BSTreeNode<K, V> Node;
Node* _Copy(Node* root)
{
if (root == nullptr)
{
return nullptr;
}
Node* cur = new Node(root->_key, root->_value);
cur->_left = _Copy(root->_left);
cur->_right = _Copy(root->_right);
return cur;
}
public:
// 默认构造
BSTree()
: _root(nullptr)
{}
// 拷贝构造
BSTree(const BSTree<K, V>& tree)
{
_root = _Copy(tree._root);
}
// 非递归插入
//bool Insert(const K& key, const V& value)
//{
// // 如果根为空, 直接插入
// if (_root == nullptr)
// {
// _root = new Node(key, value);
// return true;
// }
// // 如果根不为空, 找到插入位置
// Node* parent = nullptr;
// Node* cur = _root;
// while (cur)
// {
// if (cur->_key > key)
// {
// parent = cur;
// cur = cur->_left;
// }
// else if (cur->_key < key)
// {
// parent = cur;
// cur = cur->_right;
// }
// else
// {
// return false; // 如果相等, 表示我已经有了, 不需要插入了
// }
// }
// // 插入节点
// cur = new Node(key, value);
// if (parent->_key > key)
// {
// parent->_left = cur;
// }
// else
// {
// parent->_right = cur;
// }
// return true;
//}
// 递归插入
// 辅助函数
Node* _insert(Node* root, const K& key, const V& value)
{
if (root == nullptr)
{
return new Node(key, value);
}
if (key < root->_key)
{
root->_left = _insert(root->_left, key, value);
}
else if (key > root->_key)
{
root->_right = _insert(root->_right, key, value);
}
return root;
}
// 插入
void Insert(const K& key, const V& value)
{
_root = _insert(_root, key, value);
}
// 非递归查找节点
//Node* Find(const K& key)
//{
// Node* cur = _root;
// while (cur)
// {
// if (cur->_key > key)
// {
// cur = cur->_left;
// }
// else if (cur->_key < key)
// {
// cur = cur->_right;
// }
// else
// {
// return cur;
// }
// }
// return nullptr;
//}
// 递归查找节点
// 辅助函数
Node* _find(Node* root, const K& key)
{
if (root == nullptr || root->_key == key)
{
return root;
}
if (key < root->_key)
{
return _find(root->_left, key);
}
else
{
return _find(root->_right, key);
}
}
// 查找节点
Node* Find(const K& key)
{
return _find(_root, key);
}
// 非递归删除节点
//bool Erase(const K& key)
//{
// // 找到要删除的节点
// Node* parent = nullptr;
// Node* cur = _root;
// while (cur)
// {
// if (cur->_key > key)
// {
// parent = cur;
// cur = cur->_left;
// }
// else if (cur->_key < key)
// {
// parent = cur;
// cur = cur->_right;
// }
// else
// {
// break;
// }
// }
// // 没找到
// if (cur == nullptr)
// {
// return false;
// }
// // 找到了
// // 1. 要删除的节点没有左孩子
// 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;
// }
// // 2. 要删除的节点没有右孩子
// 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;
// }
// // 3. 左右都不为空, 不能直接删除, 使用替换法删除
// // 可以找左子树的最大节点或者右子树的最小节点去替代它
// else
// {
// // 右子树最小节点
// Node* rightMinParent = cur;
// Node* rightMin = cur->_right;
// while (rightMin->_left)
// {
// rightMinParent = rightMin;
// rightMin = rightMin->_left;
// }
// // 替换删除的节点
// std::swap(cur->_key, rightMin->_key);
// std::swap(cur->_value, rightMin->_value);
// // 把问题转换成删除 rightMin
// if (rightMinParent->_left == rightMin)
// {
// rightMinParent->_left = rightMin->_right;
// }
// else
// {
// rightMinParent->_right = rightMin->_right;
// }
// delete rightMin;
// }
// return true;
//}
// 递归删除节点
// 辅助函数
Node* _erase(Node* root, const K& key)
{
if (root == nullptr)
{
return root;
}
if (key < root->_key)
{
root->_left = _erase(root->_left, key);
}
else if (key > root->_key)
{
root->_right = _erase(root->_right, key);
}
else
{
if (root->_left == nullptr)
{
Node* ret = root->_right;
delete root;
return ret;
}
if (root->_right == nullptr)
{
Node* ret = root->_left;
delete root;
return ret;
}
Node* minNode = getMin(root->_right);
root->_key = minNode->_key;
root->_right = _erase(root->_right, minNode->_key);
}
return root;
}
Node* getMin(Node* node)
{
while (node->_left != nullptr)
{
node = node->_left;
}
return node;
}
// 删除节点
void Erase(const K& key)
{
_erase(_root, key);
}
// 递归中序遍历
// 辅助函数
//void _InOrder(Node* root)
//{
// if (root == nullptr)
// {
// return;
// }
// _InOrder(root->_left);
// //std::cout << root->_key << " : " << root->_value << std::endl;
// std::cout << root->_key << " ";
// _InOrder(root->_right);
//}
//void InOrder()
//{
// _InOrder(_root);
// std::cout << std::endl;
//}
// 非递归中序遍历
void InOrder()
{
std::stack<Node*> stack;
Node* cur = _root;
while (cur != nullptr || !stack.empty()) {
// 找到最左边的节点
while (cur != nullptr) {
stack.push(cur);
cur = cur->_left;
}
// 处理当前节点
cur = stack.top();
stack.pop();
std::cout << cur->_key << " ";
// 转向右子树
cur = cur->_right;
}
std::cout << std::endl;
}
// 递归前序遍历
// 辅助函数
//void _PreOrder(Node* root)
//{
// if (root == nullptr)
// {
// return;
// }
// std::cout << root->_key << " "; // 访问根节点
// _PreOrder(root->_left); // 访问左子树
// _PreOrder(root->_right); // 访问右子树
//}
//void PreOrder()
//{
// _PreOrder(_root);
// std::cout << std::endl;
//}
// 非递归前序遍历
void PreOrder()
{
if (_root == nullptr)
{
return;
}
std::stack<Node*> stack;
stack.push(_root);
while (!stack.empty()) {
Node* cur = stack.top();
stack.pop();
std::cout << cur->_key << " "; // 访问当前节点
// 先压入右子树再压入左子树(确保左子树先处理)
if (cur->_right != nullptr)
{
stack.push(cur->_right);
}
if (cur->_left != nullptr) {
stack.push(cur->_left);
}
}
std::cout << std::endl;
}
// 递归后序遍历
// 辅助函数
//void _PostOrder(Node* root) {
// if (root == nullptr)
// {
// return;
// }
// _PostOrder(root->_left); // 访问左子树
// _PostOrder(root->_right); // 访问右子树
// std::cout << root->_key << " "; // 访问根节点
//}
//void PostOrder()
//{
// _PostOrder(_root);
// std::cout << std::endl;
//}
// 非递归后序遍历
void PostOrder()
{
if (_root == nullptr)
{
return;
}
std::stack<Node*> st;
Node* cur = _root;
Node* lastNode = nullptr; // 最近访问的节点
while (cur || !st.empty())
{
while (cur)
{
st.push(cur);
cur = cur->_left;
}
Node* top = st.top();
if ((top->_right == nullptr) || (lastNode == top->_right))
{
std::cout << top->_key << " ";
lastNode = top;
st.pop();
}
else {
cur = top->_right;
}
}
std::cout << std::endl;
}
// 层序遍历
void LevelOrder()
{
if (_root == nullptr)
{
return;
}
std::queue<Node*> queue;
queue.push(_root);
while (!queue.empty())
{
Node* cur = queue.front();
queue.pop();
std::cout << cur->_key << " "; // 访问当前节点
if (cur->_left != nullptr) {
queue.push(cur->_left); // 将左子树压入队列
}
if (cur->_right != nullptr) {
queue.push(cur->_right); // 将右子树压入队列
}
}
std::cout << std::endl;
}
// 查找前驱节点
Node* findMax(Node* node)
{
while (node->_right != nullptr)
{
node = node->_right;
}
return node;
}
Node* FindPredecessor(Node* node)
{
if (node->_left != nullptr)
{
return findMax(node->_left);
}
Node* cur = _root;
Node* predecessor = nullptr;
while (cur != nullptr)
{
if (node->_key < cur->_key)
{
cur = cur->_left;
}
else if (node->_key > cur->_key)
{
predecessor = cur;
cur = cur->_right;
}
else
{
break;
}
}
return predecessor;
}
// 查找后继节点
Node* findMin(Node* node)
{
while (node->_left != nullptr)
{
node = node->_left;
}
return node;
}
Node* FindSuccessor(Node* node)
{
if (node->_right != nullptr)
{
return findMin(node->_right);
}
Node* cur = _root;
Node* successor = nullptr;
while (cur != nullptr)
{
if (node->_key < cur->_key)
{
successor = cur;
cur = cur->_left;
}
else if (node->_key > cur->_key)
{
cur = cur->_right;
}
else
{
break;
}
}
return successor;
}
private:
Node* _root = nullptr;
};
}

View File

@ -0,0 +1,31 @@

Microsoft Visual Studio Solution File, Format Version 12.00
# Visual Studio Version 17
VisualStudioVersion = 17.7.34221.43
MinimumVisualStudioVersion = 10.0.40219.1
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "Windows_BSTree", "Windows_BSTree.vcxproj", "{BAEFFF7F-728A-4BAB-8F43-CFE15FBE2D97}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|x64 = Debug|x64
Debug|x86 = Debug|x86
Release|x64 = Release|x64
Release|x86 = Release|x86
EndGlobalSection
GlobalSection(ProjectConfigurationPlatforms) = postSolution
{BAEFFF7F-728A-4BAB-8F43-CFE15FBE2D97}.Debug|x64.ActiveCfg = Debug|x64
{BAEFFF7F-728A-4BAB-8F43-CFE15FBE2D97}.Debug|x64.Build.0 = Debug|x64
{BAEFFF7F-728A-4BAB-8F43-CFE15FBE2D97}.Debug|x86.ActiveCfg = Debug|Win32
{BAEFFF7F-728A-4BAB-8F43-CFE15FBE2D97}.Debug|x86.Build.0 = Debug|Win32
{BAEFFF7F-728A-4BAB-8F43-CFE15FBE2D97}.Release|x64.ActiveCfg = Release|x64
{BAEFFF7F-728A-4BAB-8F43-CFE15FBE2D97}.Release|x64.Build.0 = Release|x64
{BAEFFF7F-728A-4BAB-8F43-CFE15FBE2D97}.Release|x86.ActiveCfg = Release|Win32
{BAEFFF7F-728A-4BAB-8F43-CFE15FBE2D97}.Release|x86.Build.0 = Release|Win32
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
EndGlobalSection
GlobalSection(ExtensibilityGlobals) = postSolution
SolutionGuid = {A3CDF196-D826-40E9-82D9-B280365A075B}
EndGlobalSection
EndGlobal

View File

@ -0,0 +1,138 @@
<?xml version="1.0" encoding="utf-8"?>
<Project DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<ItemGroup Label="ProjectConfigurations">
<ProjectConfiguration Include="Debug|Win32">
<Configuration>Debug</Configuration>
<Platform>Win32</Platform>
</ProjectConfiguration>
<ProjectConfiguration Include="Release|Win32">
<Configuration>Release</Configuration>
<Platform>Win32</Platform>
</ProjectConfiguration>
<ProjectConfiguration Include="Debug|x64">
<Configuration>Debug</Configuration>
<Platform>x64</Platform>
</ProjectConfiguration>
<ProjectConfiguration Include="Release|x64">
<Configuration>Release</Configuration>
<Platform>x64</Platform>
</ProjectConfiguration>
</ItemGroup>
<PropertyGroup Label="Globals">
<VCProjectVersion>17.0</VCProjectVersion>
<Keyword>Win32Proj</Keyword>
<ProjectGuid>{baefff7f-728a-4bab-8f43-cfe15fbe2d97}</ProjectGuid>
<RootNamespace>WindowsBSTree</RootNamespace>
<WindowsTargetPlatformVersion>10.0</WindowsTargetPlatformVersion>
</PropertyGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
<ConfigurationType>Application</ConfigurationType>
<UseDebugLibraries>true</UseDebugLibraries>
<PlatformToolset>v143</PlatformToolset>
<CharacterSet>Unicode</CharacterSet>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
<ConfigurationType>Application</ConfigurationType>
<UseDebugLibraries>false</UseDebugLibraries>
<PlatformToolset>v143</PlatformToolset>
<WholeProgramOptimization>true</WholeProgramOptimization>
<CharacterSet>Unicode</CharacterSet>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
<ConfigurationType>Application</ConfigurationType>
<UseDebugLibraries>true</UseDebugLibraries>
<PlatformToolset>v143</PlatformToolset>
<CharacterSet>Unicode</CharacterSet>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
<ConfigurationType>Application</ConfigurationType>
<UseDebugLibraries>false</UseDebugLibraries>
<PlatformToolset>v143</PlatformToolset>
<WholeProgramOptimization>true</WholeProgramOptimization>
<CharacterSet>Unicode</CharacterSet>
</PropertyGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
<ImportGroup Label="ExtensionSettings">
</ImportGroup>
<ImportGroup Label="Shared">
</ImportGroup>
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<PropertyGroup Label="UserMacros" />
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
<ClCompile>
<WarningLevel>Level3</WarningLevel>
<SDLCheck>true</SDLCheck>
<PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<ConformanceMode>true</ConformanceMode>
</ClCompile>
<Link>
<SubSystem>Console</SubSystem>
<GenerateDebugInformation>true</GenerateDebugInformation>
</Link>
</ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
<ClCompile>
<WarningLevel>Level3</WarningLevel>
<FunctionLevelLinking>true</FunctionLevelLinking>
<IntrinsicFunctions>true</IntrinsicFunctions>
<SDLCheck>true</SDLCheck>
<PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<ConformanceMode>true</ConformanceMode>
</ClCompile>
<Link>
<SubSystem>Console</SubSystem>
<EnableCOMDATFolding>true</EnableCOMDATFolding>
<OptimizeReferences>true</OptimizeReferences>
<GenerateDebugInformation>true</GenerateDebugInformation>
</Link>
</ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
<ClCompile>
<WarningLevel>Level3</WarningLevel>
<SDLCheck>true</SDLCheck>
<PreprocessorDefinitions>_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<ConformanceMode>true</ConformanceMode>
</ClCompile>
<Link>
<SubSystem>Console</SubSystem>
<GenerateDebugInformation>true</GenerateDebugInformation>
</Link>
</ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
<ClCompile>
<WarningLevel>Level3</WarningLevel>
<FunctionLevelLinking>true</FunctionLevelLinking>
<IntrinsicFunctions>true</IntrinsicFunctions>
<SDLCheck>true</SDLCheck>
<PreprocessorDefinitions>NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<ConformanceMode>true</ConformanceMode>
</ClCompile>
<Link>
<SubSystem>Console</SubSystem>
<EnableCOMDATFolding>true</EnableCOMDATFolding>
<OptimizeReferences>true</OptimizeReferences>
<GenerateDebugInformation>true</GenerateDebugInformation>
</Link>
</ItemDefinitionGroup>
<ItemGroup>
<ClInclude Include="BSTree.hpp" />
</ItemGroup>
<ItemGroup>
<ClCompile Include="BSTree.cpp" />
</ItemGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
<ImportGroup Label="ExtensionTargets">
</ImportGroup>
</Project>

View File

@ -0,0 +1,27 @@
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<ItemGroup>
<Filter Include="源文件">
<UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
<Extensions>cpp;c;cc;cxx;c++;cppm;ixx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
</Filter>
<Filter Include="头文件">
<UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
<Extensions>h;hh;hpp;hxx;h++;hm;inl;inc;ipp;xsd</Extensions>
</Filter>
<Filter Include="资源文件">
<UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
<Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
</Filter>
</ItemGroup>
<ItemGroup>
<ClInclude Include="BSTree.hpp">
<Filter>源文件</Filter>
</ClInclude>
</ItemGroup>
<ItemGroup>
<ClCompile Include="BSTree.cpp">
<Filter>头文件</Filter>
</ClCompile>
</ItemGroup>
</Project>

View File

@ -0,0 +1,4 @@
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="Current" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<PropertyGroup />
</Project>

Binary file not shown.

Binary file not shown.

View File

@ -0,0 +1,11 @@
<?xml version="1.0" encoding="utf-8"?>
<Project>
<ProjectOutputs>
<ProjectOutput>
<FullPath>E:\Git 仓库\公开仓库\6_BSTree\Windows_BSTree\x64\Debug\Windows_BSTree.exe</FullPath>
</ProjectOutput>
</ProjectOutputs>
<ContentFiles />
<SatelliteDlls />
<NonRecipeFileRefs />
</Project>

Binary file not shown.

View File

@ -0,0 +1,2 @@
 BSTree.cpp
Windows_BSTree.vcxproj -> E:\Git 仓库\公开仓库\6_BSTree\Windows_BSTree\x64\Debug\Windows_BSTree.exe

Binary file not shown.

View File

@ -0,0 +1 @@
E:\Git 仓库\公开仓库\6_BSTree\Windows_BSTree\BSTree.cpp;E:\Git 仓库\公开仓库\6_BSTree\Windows_BSTree\x64\Debug\BSTree.obj

View File

@ -0,0 +1,2 @@
PlatformToolSet=v143:VCToolArchitecture=Native64Bit:VCToolsVersion=14.37.32822:TargetPlatformVersion=10.0.22000.0:
Debug|x64|E:\Git 仓库\公开仓库\6_BSTree\Windows_BSTree\|

View File

@ -0,0 +1 @@
E:\Git 仓库\公开仓库\6_BSTree\Windows_BSTree\x64\Debug\Windows_BSTree.exe

Binary file not shown.

Binary file not shown.