数据结构-查找

#include<bits/stdc++.h>

using namespace std;


typedef struct BSTNode{
	int data;
	BSTNode *lchild;
	BSTNode *rchild;
}BSTNode, *BSTree;
 
bool Search(BSTree bst, int k, BSTree f, BSTree *p){//查找成功时,p指向值为k的节点,查找失败时,则p指向遍历的最后一个节点 
	if(!bst){
		*p = f;
		return false;
	}
	if(bst->data == k){
		*p = bst;
		return true;
	}
	else if(bst->data < k){
		return Search(bst->rchild, k, bst, p);
	}
	else{
		return Search(bst->lchild, k, bst, p); 
	}
}

BSTNode* InitNode(int data){
	BSTNode *tmp = (BSTNode*)malloc(sizeof(BSTNode));
	if(!tmp){
		exit(0);
	}
	tmp->data = data;
	tmp->lchild = NULL;
	tmp->rchild = NULL;
	return tmp;
}

bool Insert(BSTree *bst, int k){
	
	if(*bst == NULL){//如果这棵树为空,将他初始化为根节点 
		*bst = InitNode(k);
		return true;
	}
	
	BSTNode *p;
	
	if(!Search(*bst, k, NULL, &p)){//如果二叉树内不存在这个节点,就插入 
		BSTNode *q = InitNode(k);
		if(k < p->data){
			p->lchild = q;
		}
		else if(k > p->data){
			p->rchild = q; 
		}
		return true;
	}
	else{
		cout<<k<<"节点已存在"<<endl;
	}
} 

BSTNode* FindParent(BSTree bst, BSTNode *child){//找寻这个节点的父母节点 
	if(bst == NULL){
		return NULL;
	}
	
	if(bst->lchild == child || bst->rchild == child){
		return bst;
	}
	else if(bst->lchild != NULL){
		FindParent(bst->lchild, child);
	}
	else if(bst->rchild != NULL){
		FindParent(bst, child);
	}
} 

int Delete(BSTree *bst, int k){
	if(*bst == NULL){
		exit(1);
	}
	
	BSTNode *p;
	BSTNode *f = NULL;
	BSTNode *q, *s;
	
	if(Search(*bst, k, NULL, &p)){
		if(!p->lchild && p->rchild != NULL){
			q = p->rchild;
			p->data = q->data;
			p->rchild = q->rchild;
			p->lchild = q->lchild;
			free(q);
		}
		else if(!p->rchild  && p->lchild != NULL){
			q = p->lchild;
			p->data = q->data;
			p->rchild = q->rchild;
			p->lchild = q->lchild;
			free(q);
		}
		else if(p->rchild && p->lchild){
			q = p;
			s = p->lchild;
			while(s->rchild){
				q = s;
				s = s->rchild;
			}
			//s此时的值是p节点的最大的子节点的值 
			p->data = s->data;//只改变了节点的值,节点指向左右孩子的指针没有变 
			
			if(q != p){
				q->rchild = s->lchild;
			}
			else{
				q->lchild = s->lchild;
			}
			free(s);
		}
		else{//要删除的节点是叶节点或只有一个根节点 
			if(*bst == p){//只有一个根节点 
				free(*bst);
				*bst = NULL;
				return true;
			}
			
			BSTNode* parent = FindParent(*bst, p);//回溯找到这个节点的父母节点 
			if(parent->lchild == p){
				parent->lchild = NULL;
			} 
			else{
				parent->rchild = NULL;
			}
			free(p); 
		} 
		return 1;
	}
} 

void Traver(BSTree bst){//先序遍历排序二叉树 
	if(bst != NULL){
		Traver(bst->lchild);
		cout<<bst->data<<" ";
		Traver(bst->rchild);
	}
	return ;
}

void menu1(){
	
	cout<<"请选择你需要的功能:"<<endl;
	cout<<"1、输入序列"<<endl;
	cout<<"2、顺序查找"<<endl;
	cout<<"3、折半查找"<<endl;
	cout<<"4、排序二叉树的插入、删除、查找、遍历(此方法需单独输入序列,如果要使用该方法,请直接选择4)"<<endl;
	cout<<"5、退出"<<endl;
	
	return ; 
}

void menu2(){
	
	cout<<"请选择你需要的功能:"<<endl;
	cout<<"1.向二叉树内插入元素"<<endl;
	cout<<"2.删除二叉树内的元素"<<endl;
	cout<<"3.查找二叉树内的元素"<<endl;
	cout<<"4.中序遍历二叉树"<<endl;
	cout<<"5.退出"<<endl; 
	return ; 
}

bool Er(int a[], int &iu, int k, int l, int r){
	bool pool = false;
	while(l <= r){
		int mid = (l + r) / 2;
		if(a[mid] == k){
			pool = true;
			iu = mid;
			break; 
		}
		else if(a[mid] > k){
			r = mid - 1;
		}
		else if(a[mid] < k){
			l = mid + 1;
		}
	}
	if(pool){
		return 1;
	}
	else{
		return false;
	}
}

int main()
{
	bool pool = false;//标记是否已输入序列 
	while(1){
		int a[10000];
		int n, r, k, m;
		menu1();
		cin>>r;
		
		if(r == 1){
			cout<<"请输入序列含有的元素数量:"<<endl;
			cin>>n;
			cout<<"请输入元素序列:"<<endl;
			for(int i = 0; i < n; i ++ ){
				cin>>a[i];
			}  
			cout<<"输入完成!"<<endl;
			pool = true;
		} 
		
		else if(r == 2){
			if(pool){
				cout<<"请输入你要查找的元素:";
				cin>>k;
				bool flag = false;
				for(int i = 0; i <n; i ++ ){
					if(a[i] == k){
						m = i;
						flag = true;
						break;
					}
				}
				if(!flag){
					cout<<"你要查找的元素不在刚才输入的序列内!"<<endl;
				}
				else{
					cout<<"你要查找的元素在序列的第"<<m + 1<<"位"<<endl; 
				}
			}
			else{
				cout<<"请先输入序列"<<endl;
			}
		}
		
		else if(r == 3){
			if(pool){
				cout<<"请输入你要查找的元素:";
				cin>>k;
				int iu;
				if(Er(a, iu, k, 0, n - 1)){
					cout<<"你要查找的元素在序列的第"<<iu + 1<<"位"<<endl;
				}
				else{
					cout<<"你要查找的元素不在刚才输入的序列内!"<<endl;
				}
			}
			else{
				cout<<"请先输入序列"<<endl;
			}
		}
		else if(r == 4){
			BSTNode *r = NULL;
			while(1){
				menu2();
				int y;
				cin>>y;
				if(y == 1){ 
					while(1){
						cout<<"请输出要插入的数:";
						int oi;
						cin>>oi;
						Insert(&r, oi);
						cout<<"请选择是否要继续输入:"<<endl;
						cout<<"1.继续输入"<<endl;
						cout<<"2.退出输入"<<endl;
						int u;
						cin>>u;
						if(u == 1){
							continue;
						}
						else if(u == 2){
							break;
						}
					}
				}
				else if(y == 2){
					cout<<"请输入你要删除的值"<<endl;
					int k;
					cin>>k;
					Delete(&r, k);
					cout<<"删除成功!"<<endl;
				}
				else if(y == 3){//查找 
					cout<<"请输入你要查找的值:"; 
					int k;
					cin>>k; 
					BSTNode *p;
					if(Search(r, k, NULL, &p)){
						cout<<"该节点在排序二叉树中"<<endl; 
					}
					else{
						cout<<"该节点不在排序二叉树中"<<endl;
					}
				} 
				else if(y == 4){//中序遍历二叉树 
					cout<<"中序遍历二叉树的结果为:";
					Traver(r);
					cout<<endl;
				}
				else if(y == 5){
					cout<<"感谢使用!"<<endl;
					break;
				}
				else{
					cout<<"请输入正确的操作序号!"<<endl; 
				}
				cout<<endl;
			}
		}
		
		else if(r == 5){
			cout<<"谢谢使用!"<<endl;
			break;
		}
		
		else{
			cout<<"请输入正确的操作序号!"<<endl; 
		} 
		cout<<endl;
	}
	return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值