總體思想:分多種情況討論
1.被刪除節點沒有子樹的情況,直接刪除,並修改對應父節點的指標為空白。
2.對於只有一個子樹的情況,考慮將其子樹作為其父節點的子樹,關於是左還是右,根據被刪除的節點確定。
3.最複雜的是有兩個子數的情況,可以考慮兩種方法,都是同樣的思想:用被刪除節點A的左子樹的最右節點或者A的右子樹的最左節點作為替代A的節點,並修改相應的最左或最右節點的父節點的指標,修改方法類似2 ,不做細緻討論
/*************二叉樹的節點的刪除***********/
/*********該程式描述了從遞迴建立二叉樹到尋找*********/
/*********以及刪除的全過程,也算是對前面幾個*********/
/*********程式的聯習與總結***************************/
#include<stdio.h>
#include<stdlib.h>
#define Maxsize 16
//定義二叉樹節點
struct treenode
{
int data;
struct treenode* left;
struct treenode* right;
};
typedef treenode Node;
typedef Node* btree;
//遞迴建立二叉樹
btree create_btree(int* nodelist,int postion)
{
btree newnode;
if(nodelist[postion]==0||postion>=Maxsize)
return NULL;
else
{
newnode=(btree) malloc(sizeof(Node));
newnode->data=nodelist[postion];
newnode->left=create_btree(nodelist,postion*2);
newnode->right=create_btree(nodelist,postion*2+1);
return newnode;
}
}
/********尋找二叉樹的節點********/
btree search(btree root,int node)
{
btree point;
point=root;
if(point==NULL)
return root;
else
if(point->data==node)
return point;
else
if(point->data>node)
search(point->left,node);
else
search(point->right,node);
}
/********第二種尋找方法,記錄其父節點的值********/
btree binary_search(btree point,int node,int *postion)
{
btree parent;
parent=point;
*postion=0;
while(point!=NULL)
{
if(point->data==node)
return parent;
else
{
parent=point;
if(point->data>node)
{
point=point->left;
*postion=-1;
}
else
{
point=point->right;
*postion=1;
}
}
}
return NULL;
}
/**********刪除二叉樹節點的操作***********/
btree deletenode(btree root,int node)
{
btree parent;
btree point;
btree child;
int postion;
parent=binary_search(root,node,&postion);
//二叉樹為空白的情況
if(parent==NULL)
return root;
else
{
switch(postion)
{ case -1:point=parent->left;break;
case 1 :point=parent->right;break;
case 0 :point=parent;break;
}
if(point->left==NULL&&point->right==NULL)
{
switch(postion)
{
case -1:parent->left=NULL;break;
case 1:parent->right=NULL;break;
case 0:parent=NULL;break;
}
free(point);
return root;
}
if(point->left==NULL&&point->right!=NULL)
{
if(postion==-1)
parent->left=point->right;
else
if(postion==1)
parent->right=point->right;
else
root=root->right;
free(point);
return root;
}
if(point->left!=NULL&&point->right==NULL)
{
if(postion==-1)
parent->left=point->left;
else
if(postion==1)
parent->right=point->left;
else
root=root->left;
return root;
}
if(point->left!=NULL&& point->right!=NULL)
{
parent=point;
child=point->left;
while(child->right!=NULL)
{
parent=child;
child=child->right;
}
point->data=child->data;
if(parent->left=child)
parent->left=child->left;
else
parent->right=child->left;
free(child);
return root;
}
}
}
/*********中序遍曆二叉樹*************/
void Inorder(btree point)
{
if(point!=NULL)
{
Inorder(point->left);
printf("[%2d]",point->data);
Inorder(point->right);
}
}
/*********主程式測試函數***********/
void main()
{
btree root=NULL;
int deletetree;
int nodelist[16]={0,5,4,6,2,0,0,8,1,3,0,0,0,0,7,9};
root=create_btree(nodelist,1);
printf("/n the original tree is");
Inorder(root);
printf("/n");
printf("Input the value of the number /n");
int test;
scanf("%d",&test);
root=deletenode(root,test);
printf("/n the deleted tree is /n");
Inorder(root);
printf("/n");
}