二叉搜索树
二叉搜索树的前提条件与二分查找一样,都是建立在有序的基础上的。二分查找条件是递增或递减,而二叉搜索树的条件是:
1. 左树的非空元素都小于根元素
2. 右树的非空元素都大于根元素
1.Find操作,查找某个元素的节点,返回地址
//递归,效率不高,但更加直观
Position Find(int target, BinTree BST){
if(!BST) return NULL; //查找失败
if(target > BST->data)
return Find(target, BST->right);//前往右树查找
else if(target < BST->data)
return Find(target, BST->left); //前往左树查找
else //找到节点
return BST;
}
//循环实现
Position Find(int target, BinTree BST){
while(BST){
if(target > BST->data)
BST = BST->right;
else if(target < BST->data)
BSt = BST->left;
else return BST;
}
return NULL;
}
2. minFind 与maxFind, 查找最大和最小的元素,返回地址。
//效率不高的递归
Position minFind(BinTree BST){
if(!BST) return NULL;
else if(!BST->left) //向左找到寂寞返回
return BST;
else
return minFind(BST->left); //向左找到天荒地老
}
Position maxFind(BinTree BST){
if(!BST) return NULL;
else if(!BST->right) //向右找到寂寞返回
return BST;
else
return minFind(BST->right); //向右找到天荒地老
}
//迭代
Position maxFind(BinTree BST){
if(BST){
while(BST->right) BST = BST->right;
}
return BST;
}
3-搜索树的插入,同时也要保证树的有序性
BinTree Insert(int target, BinTree BST){
if(!BST){ //树为空则开辟一个节点
BST = malloc(sizeof(struct TreeNode));
BST->data = target;
BST->left = BST->right = NULL;
}else if(target < BST->data){ //开始寻找位置
BST->left = Insert(target, BST->left); //递归插入左树
}else if(target >BST->data){
BST->right = Insert(target, BST->right); //递归插入右树
}
return BST;
}
4-搜索树的删除,删除分三种情况,当删除一个无子节点的节点时,直接删除就好了;d当要删除的节点有一个子节点时,需要把这个子节点挂在删除节点的位置;当有两个子节点时,需要用较大或较小的节点替换,具体看代码
BinTree delete(int target, BinTree BST){
Position temp;
if(!BST) printf("删除元素未找到");
else if(target < BST->data)
//前往左树寻找节点
BST->left = delete(target, BST->left);
else if(target > BST->data)
//前往右树寻找节点
BST->right = delete(target, BST->right);
else { //此时要删除的节点已经找到
if(BST->left && BST->right){ //发现该节点有两个子节点
//前往右子树中寻找最小的节点填充删除的节点
temp = minFind(BST->right);
BST->data = temp->data;
//删除用于填充的节点
BST->right = delete(BST-data, BST->right);
}else{ //惊喜地发现要删除的节点只有一个或没有子节点
temp = BST;
if(!BST->left){ //只有右节点或无节点
BST = BST->right;
}else if(!BST->right){ //只有左节点或无节点
BST = BST->left;
}
free(temp);
}
}
return BST;
}