有bug的AVL平衡树

/*
AVL平衡树,调了很久始终有bug
先放着。


测试数据
set 1 11
set 2 22
set 9 999
set 10 101010
set 11 11111
set 12 12121
set 19 1919
set 17 1717
set 16 1616
set 15 15


set 5 55
set 1 11
set 2 22
set 4 44
set 3 33
set 7 77
set 6 66

set sdfs  dsfs
set sghjg sdfsdsf
set 第 大幅度
set 了 地方看
set 难题 多对多


*/
#include <stdio.h>
#include <string.h>
#include <stdlib.h> 
#define MaxSize 100 

typedef struct node *node_pointer;
typedef struct node
{
	int num_key;//关键字
	int bf;///平衡因子
	char key[10];
	char data[20];
	node_pointer left,right;
}node;
int s[50];//左边走为0 ,右边走为1 .
int si=0;
int stop=0;//更新断点

void set(node_pointer *root);
void insert(node_pointer *root,node_pointer now_node);
void avl(node_pointer* pingheng);
void ll_avl(node_pointer* pingheng);//ll调整
void rr_avl(node_pointer* pingheng);//rr调整
void lr_avl(node_pointer* pingheng);//lr调整
void rl_avl(node_pointer* pingheng);//rl调整
node_pointer get_node(char*key,char *zhi);
int get_key(char *key);
void lxu(node_pointer head);
void changebf(node_pointer *root);//改变bf


void main()
{
	node_pointer root=NULL;
    printf("请输入  set如set key value.   get如get key;  ceshi;    quit退出\n");
	char caozuo[10];
	int sel;
     do{
         scanf("%s",&caozuo);
         if (strcmp(caozuo,"set")==0)
            sel=1;
         else if (strcmp(caozuo,"get")==0)
            sel=2;
        else if (strcmp(caozuo,"look")==0)
            sel=3;
        else if (strcmp(caozuo,"quit")==0)
            sel=0;
        else if (strcmp(caozuo,"ceshi")==0)
            sel=4;
        else sel=-1;


         switch(sel)
        {
          case 0:printf("\t\t\t^-^再见!^-^ \t\t\t\n");system("pause");break;
          case 1:     set(&root);break;
//          case 2:getvalue(&root);printf("\n\n");break;
          case 4:lxu(root);printf("\n\n");break;
          //case 3:look();printf("\n");break;
          default: printf("请输入正确的选项号!");printf("\n\n");break;
        }
    }while(sel!=0);
}

void set(node_pointer *root)
{
  char key[10],zhi[20];
  scanf("%s %s",&key,&zhi);
  node_pointer now_node=get_node(key,zhi);

  insert(root,now_node);
}

void insert(node_pointer *root,node_pointer now_node)//bf的变化失败了,待于改正
{
	si=0;
	stop=0;

	if (*root == NULL)//空树时
	      *root=now_node;
	else
	{
		node_pointer dang=*root;//当前
        node_pointer* pre=root;//上一个,指向指针的指针
        node_pointer* pingheng=NULL;//用于判断是否非平衡了
        while(1)
        {
			if( 0 == strcmp(dang->key,now_node->key) )//相同的key
				{
					strcpy(dang->data,now_node->data);
					free(now_node);
					return;//直接返回了,没有失去平衡
				}
			else
			{
				if(now_node->num_key <= dang->num_key  )//小于等于,左走
					{ 

						s[si++]=0;
						if( (dang->bf+1)  == 2)
						{
							stop=si;
							pingheng=pre;//始终为失衡的最低点
						}


						pre=&((*dang).left);//变量的地址
						dang=dang->left;//变量的值
						if(dang==NULL)
							{
								*pre=now_node;
								break;
							}
					}
				else if(now_node->num_key > dang->num_key )//大于,右走
					{
						
						s[si++]=1;
						if((dang->bf-1)  == -2 )
						{
							stop=si;
							pingheng=pre;//始终为失衡的最低点
						}

						pre=&((*dang).right);
						dang=dang->right;
						if(dang==NULL)
							{
								*pre=now_node;
								break;
							}
					}
			}

		}
			//处理平衡
		if (pingheng ==NULL)
		{
			changebf(root);
		}
		else 
		{
			avl(pingheng);
		}
	}
}
void changebf(node_pointer *root)
{
	int i=0;
	node_pointer temp=*root;
	for ( i = 0; i < si-1; ++i)
	{
		if (s[i]==0)
		{
			++(temp->bf);
			temp=(temp)->left;
		}
		else if(s[i]==1)
		{
			--(temp->bf);
			temp=(temp)->right;			
		}
	}



}
void avl(node_pointer* pingheng)
{
	node_pointer here=*pingheng;
	if( s[stop]==0 &&  s[stop+1]==0)
	{	ll_avl(pingheng); }
	else if( s[stop]==0 && s[stop+1]==1)
	{	lr_avl(pingheng); }
	else if( s[stop]==1 &&  s[stop+1]==0)
	{	rl_avl(pingheng); }
	else if( s[stop]==1 &&  s[stop+1]==1)
	{	rr_avl(pingheng); }
}

void ll_avl(node_pointer* pingheng)
{
	node_pointer temp = (*pingheng)->left;
	(*pingheng)->left = temp->right;
	temp->right=*pingheng;
	*pingheng=temp;

	temp->bf=0;
	temp->right->bf=0;
}
void lr_avl(node_pointer* pingheng)
{
	node_pointer temp_a=(*pingheng);
	node_pointer temp_b=(*pingheng)->left;
	*pingheng= temp_b->right;

	 temp_a->left=(*pingheng)->right;
	 temp_b->right=(*pingheng)->left;

	(*pingheng)->right=temp_a;
	(*pingheng)->left=temp_b;

	if( s[stop+2]== 0 )
	{
		temp_a->bf= -1;
		temp_b->bf= 0;
	}
	else
	{
		temp_a->bf= 0;
		temp_b->bf= 1;		
	}

	(*pingheng)->bf =0;
}

void rl_avl(node_pointer* pingheng)
{
	node_pointer temp_a=(*pingheng);
	node_pointer temp_b=(*pingheng)->right;
	*pingheng= temp_b->left;

	 temp_a->right=(*pingheng)->left;
	 temp_b->left=(*pingheng)->right;

	(*pingheng)->left=temp_a;
	(*pingheng)->right=temp_b;

	if( s[stop+2]== 0 )
	{
		temp_a->bf= 0;
		temp_b->bf= -1;
	}
	else
	{
		temp_a->bf= 1;
		temp_b->bf= 0;		
	}

	(*pingheng)->bf =0;
}

void rr_avl(node_pointer* pingheng)
{
	node_pointer temp = (*pingheng)->right;
	(*pingheng)->right = temp->left;
	temp->left=*pingheng;
	*pingheng=temp;	

	temp->bf=0;
	temp->left->bf=0;

}

node_pointer get_node(char*key,char *zhi)
{
  node_pointer now_node=(node_pointer)malloc(sizeof(node));
  now_node->num_key=get_key(key);
  strcpy(now_node->key,key);
  strcpy(now_node->data,zhi);
  now_node->bf=0;
  now_node->left=NULL;
  now_node->right=NULL;
  return now_node;
}
int get_key(char *key)
{ 
    int number = 0;    
    while(*key)    
       number+=*key++ ;   

  return number;  
}
void lxu(node_pointer head)  
{  
node_pointer st[MaxSize],p=head;  
  int dui_front=0,dui_rear=0;  
  /*   
	printf("%d->%s->%s ",p->num_key,p->key,p->data); 
    printf("%d->%s->%s ",p->left->num_key,p->left->key,p->left->data); 
    printf("%d->%s->%s ",p->right->num_key,p->right->key,p->right->data); 

  */
   st[dui_rear++ % MaxSize]=head;  
   while(true){  
         p=st[dui_front++ % MaxSize];//调用队头,并且输出  
         printf("%d->%d->%s->%s ",p->bf,p->num_key,p->key,p->data);  
        if(p->left)st[dui_rear++ % MaxSize]=p->left;//进  
        if(p->right)st[dui_rear++ % MaxSize]=p->right;  
  
        if(dui_front >= dui_rear)break;//返回到了树顶了  
    }  
}  
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

紫云的博客

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值