二叉排序树(BST)

二叉排序树又名二叉搜索树,其任何一个结点的左子树的所有点的值小于父结点,任何一个结点的右子树的所有点的值大于父结点。之所以叫二叉排序树是因为中序遍历输出的结果是一个递增序列。


插入:
每次插入新结点,必须从根结点开始遍历,然后把新结点作为叶结点插入。


查找:
从根结点开始,如果该结点的值小于所查值,在右子树中查找,否则在左子树中查找


删除:
前提:

删除结点,二叉搜索树的性质不变,保证删除后二叉搜索树的性能不下降,必须保证重新链接起来后的树的高度不能增加。
步骤:
删除结点没有孩子结点时,直接删除;
删除结点的左、右孩子有一个为空时,直接用不为空孩子结点替补删除结点
删除结点的左右孩子都不为空时,在右子树中寻找中序遍历的第一个结点(候补结点),然后用候补结点的值替换删除结点。然后从删除结点的右子树开始,删除候补结点(现在树中存在两个值一样的结点,必须把候补结点删除到)

</pre><pre name="code" class="cpp">
</pre><pre name="code" class="cpp">
#pragma once
#include <iostream>

using namespace std;
#define NULL 0

struct ST_NODE
{
	int m_iData;
	ST_NODE* m_pLeftNode;
	ST_NODE* m_pRightNode;

public:
	ST_NODE()
	{
	}

	ST_NODE(int data)
	{
		m_iData = data;
		m_pLeftNode = NULL;
		m_pRightNode = NULL;
	}
};

class CBST
{
public:
	CBST(void);
	~CBST(void);
	void Insert(int data);
	bool ExistData(int data);
	ST_NODE* Find(ST_NODE* node,int data);
	void Delete(int data);
	void DeleteNode(ST_NODE* &node, int data);
	void InorderTraverse();
	void RecursionShow(ST_NODE* node);
public:
	ST_NODE* m_pRoot;

};
</pre><pre name="code" class="cpp"><pre name="code" class="cpp">#include "BST.h"

CBST::CBST(void)
{
	m_pRoot = NULL;
}

CBST::~CBST(void)
{
}

void CBST::Insert(int data)
{
	if (!m_pRoot)
	{
		m_pRoot = new ST_NODE(data);
	}
	else
	{
		ST_NODE* tmp = m_pRoot;

		while(true)
		{
			if (tmp->m_iData > data)
			{
				 if (tmp->m_pLeftNode == NULL)
				 {
					 tmp->m_pLeftNode = new ST_NODE(data);
					 return;
				 }
				tmp = tmp->m_pLeftNode;
			}
			else if (tmp->m_iData < data)
			{
				 if (tmp->m_pRightNode == NULL)
				 {
					 tmp->m_pRightNode = new ST_NODE(data);
					 return;
				 }
				tmp = tmp->m_pRightNode;
			}
			else
			{
				return;
			}
		}
	}

}


bool CBST::ExistData(int data)
{
	if (Find(m_pRoot, data) == NULL)
	{
		return false;
	}

	return true;
}

ST_NODE* CBST::Find(ST_NODE* node,int data)
{
	if (node == NULL)
	{
		return NULL;
	}
	else
	{
		if (node->m_iData == data)
		{
			return node;
		}
		else if (node->m_iData > data)
		{
			return Find(node->m_pLeftNode, data);
		}
		else
		{
			return Find(node->m_pRightNode, data);
		}
	}
	return NULL;
}


void CBST::Delete(int data)
{
	DeleteNode(m_pRoot, data);
}

void CBST::DeleteNode(ST_NODE* &node, int data)
{
	if (node == NULL)
	{
		return;
	}

	if (node->m_iData > data)
	{
		DeleteNode(node->m_pLeftNode, data);
	}
	else if (node->m_iData < data)
	{
		DeleteNode(node->m_pRightNode, data);
	}
	else
	{
		ST_NODE* tmp = node;
		if (node->m_pLeftNode && node->m_pRightNode)
		{
			//在右子树搜寻中序下的第一个节点
			tmp = node->m_pRightNode;
			while(tmp->m_pLeftNode != NULL)
			{
				tmp = tmp->m_pLeftNode;
			}

			node->m_iData = tmp->m_iData;

			DeleteNode(node->m_pRightNode, node->m_iData);
		}
		else
		{
			if (node->m_pLeftNode == NULL)
			{
				node = node->m_pRightNode;
			}
			else
			{
				node = node->m_pLeftNode;
			}

			delete tmp;
			tmp = NULL;
		}
	}
}

void CBST::InorderTraverse()
{
	RecursionShow(m_pRoot);
}

void CBST::RecursionShow(ST_NODE* node)
{
	if (node == NULL)
	{
		return;
	}

	RecursionShow(node->m_pLeftNode);
	cout << node->m_iData << "\t";
	RecursionShow(node->m_pRightNode);
}


 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值