数据结构:二叉查找树

//二叉查找树
#include<stdio.h>
#include<stdlib.h>
typedef struct TreeNode{
	int Element;
	struct TreeNode *Left;
	struct TreeNode *Right;
}TreeNode;
static TreeNode *T;
TreeNode *MakeEmpty(TreeNode *);
TreeNode *Find(int ,TreeNode *);
TreeNode *FindMin(TreeNode *);
TreeNode *FindMax();
TreeNode *Insert(int x,TreeNode *);
TreeNode *Delete(int );
int Retrieve(TreeNode *);
void error(char *);
void initial_tree(int );
void print_tree(TreeNode * T);
/*
对于满二叉树
	A
    B	      E
 C    D	   F      G
//序号表示执行的顺序
A -->free(T) 7
	B -->free(T) 3
		C -->free(T) 1
		D-->free(T) 2
	E -->free(T) 6
		F -->free(T) 4
		G -->free(T) 5
*/
TreeNode *MakeEmpty(TreeNode *T){
	if(T != NULL){
		MakeEmpty(T->Left);
		MakeEmpty(T->Right);
		free(T);
	}
	return NULL;
}

TreeNode *Find(int x,TreeNode *T){
	if(T == NULL){
		return NULL;
	}

	if(x<T->Element){
		return Find(x,T->Left);
	}
	else{
		if(x>T->Element){
			return Find(x,T->Right);
		}
		else{
			return T;
		}
	}
}

TreeNode *FindMin(TreeNode *T){
	if(T==NULL){
		return NULL;
	}
	while(T->Left != NULL){
		T = T->Left; 
	}
	return T;
}
TreeNode *FindMax(){
	if(T==NULL){
		return NULL;
	}
	while(T->Right!= NULL){
		T = T->Right; 
	}
	return T;
}
void error(char *s){
	printf("%s",s);
}
/*T	T->left = Insert(X,T->Left)    return T
		T_1=T->left,T_1->left=Insert(X,T_1->Left)	return T_1
			T_2=T_1->left,T_2->left=Insert(X,T_2->Left) return T_2 
*/
TreeNode *Insert(int x,TreeNode *T){
	if(T==NULL){
		/*then Create and return a one_node tree*/
		T=(TreeNode *)malloc(sizeof(TreeNode));
		if(T==NULL){
			error("Out of space!!!");
		}
		else{
			T->Element =x;
			T->Left = NULL;
			T->Right = NULL;
		}
	}
	if(x<T->Element){
		T->Left = Insert(x,T->Left);
	}
	else{
		if(x>T->Element){                                                      
			T->Right=Insert(x,T->Right);
		}
	//if x is in the tree already,we will do nothing
	}
	return T;
}

//删除操作 最复杂
/*情况一:删除的节点是一片树叶,直接删除?
  情况二:删除的节点只有一个儿子,可直接可直接唯一的儿子替代自己的位置
  情况三:删除的节点有两个儿子,一般方法:使用右子树最小的值代替原来的值,
  		需要处理的有两个地方.1,最小值代替删除的值的位置(直接改变要删除的值
  		为找到的最小值即可)2,最小值原来的右子树需要处理。(最小值肯定没有左子树
  		所以再次递归找到最小值,按情况一或者二处理即可)
*/
TreeNode *Delete(int x,TreeNode * T){
	TreeNode * Tmp;
	if(T == NULL){
		error("no element are found");
		return NULL;
	}
	
	if(x < T->Element){
		T->Left=Delete(x,T->Left);
	}
	else if(x>T->Element){
		T->Right= Delete(x,T->Right);
	}
	else{
		if(T->Left!=NULL && T->Right!=NULL){
			//replace with smallest in right subtree
			Tmp = FindMin(T->Right);
			T->Element = Tmp->Element;
			T->Right =Delete(T->Element,T->Right);
		}
		else{
			Tmp=T;
			if(T->Left == NULL){
				T=T->Right;
			}else if(T->Right ==NULL){
				T=T->Left;
			}
			free(Tmp);
		}
	}
	return T;
}
void initial_tree(int x){
	T=(TreeNode *)malloc(sizeof(TreeNode));
	T->Element =x;
	T->Left=NULL;
	T->Right=NULL;
}
//从小到大打出相应的数据,采用中序遍历的方法
void print_tree(TreeNode * T){
	if(T!=NULL){
		print_tree(T->Left);
		printf("%d ",T->Element);
		print_tree(T->Right);
	}

}
void main(){
	//验证 是否正确,创建一棵树
	int i;
	int a[]={100,101,50,40,60,55,65,56,61};
	initial_tree(a[0]);
	for(i=1;i<9;i++){
		Insert(a[i],T);
	}
	print_tree(T);
	Delete(50,T);
	print_tree(T);
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值