二叉搜索树的增删改查

870 阅读1分钟

什么是二叉搜索树

  • 若他的左子树不为空,则左子树上的所有结点值均小于它的根结点的值
  • 若他的右子树不为空,则它的右子树上的所有值均大于它的根结点的值
  • 它的左右子树也分别是二叉搜索树

二叉树的结构

typedef struct BiTNode{

    int data;

    struct BiTNode * lchild,*rchild;

}BiTNodfe,*BiTree;

二叉搜索树的插入

Status InsertBST(BiTree * T, **int** key){
    BiTree p;
    if (!SearchBST(*T, key, NULL,&p)) {
        BiTree tem = (BiTree)malloc(sizeof(BiTNode));
        tem->data = key;
        tem->lchild = NULL;
        tem->rchild = NULL;

        if (p == NULL) {
            *T = tem;
        } else if(key > p->data){
            p->rchild = tem;
        } else {
            p->lchild = tem;
        }
        return  TRUE;
    }
    return FALSE;
}

二叉搜索树的删除

二叉树的删除我们需要讨论几种情况
  • 1.叶子结点删除:只需要删除该结点(双亲结点的左/右滞空)
  • 2.有一个左子树,右子树为空(只需要将该结点重新赋值为它自己的左子树)
  • 3.有一个右子树,左子树为空(只需要将该结点重新赋值为他自己的右子树)
  • 4.既有左子树也有右子树
    • 1.由于二叉搜索树的中序排序是升序排列
    • 2.直接用前驱替换被删除结点
      1. 将前驱结点的前驱(当前驱结点是右子树那么直接删除 当前驱结点有左子树 那么只需要将左子树移动到该结点 )

1是特殊的2 3 所以这里只有两种情况

Status Delete(BiTree * p){
    BiTree temp,s;
    if((*p)->lchild == NULL){
        temp = *p;
        *p = (*p)->rchild;
        free(temp);
    } else if((*p)->rchild == NULL){
        temp = *p;
        *p = (*p)->lchild;
        free(temp);
    } else {
        temp = *p;
        s = temp->lchild
        while (s->rchild) {
            temp = s;
            s= s->rchild;
        }
        (*p)->data = s->data;
        if (temp == (*p)) {
            temp->lchild = s->lchild;
        } else {
            temp->rchild = s->lchild;
        }
        free(s);
    }
    return TRUE;
}