4-12 二叉搜索树的操作集 (30分)

本题要求实现给定二叉搜索树的5种常用操作。

函数接口定义:

BinTree Insert( BinTree BST, ElementType X );

BinTree Delete( BinTree BST, ElementType X );

Position Find( BinTree BST, ElementType X );

Position FindMin( BinTree BST );

Position FindMax( BinTree BST );

其中BinTree结构定义如下:

typedef struct TNode *Position;

typedef Position BinTree;

struct TNode{

ElementType Data;

BinTree Left;

BinTree Right;

};

函数Insert将X插入二叉搜索树BST并返回结果树的根结点指针;
函数Delete将X从二叉搜索树BST中删除,并返回结果树的根结点指针;如果X不在树中,则打印一行Not Found并返回原树的根结点指针;
函数Find在二叉搜索树BST中找到X,返回该结点的指针;如果找不到则返回空指针;
函数FindMin返回二叉搜索树BST中最小元结点的指针;
函数FindMax返回二叉搜索树BST中最大元结点的指针。

裁判测试程序样例:

#include <stdio.h>
#include <stdlib.h>

typedef int ElementType;
typedef struct TNode *Position;
typedef Position BinTree;
struct TNode{
    ElementType Data;
    BinTree Left;
    BinTree Right;
};

void PreorderTraversal( BinTree BT ); /* 先序遍历,由裁判实现,细节不表 */
void InorderTraversal( BinTree BT );  /* 中序遍历,由裁判实现,细节不表 */

BinTree Insert( BinTree BST, ElementType X );
BinTree Delete( BinTree BST, ElementType X );
Position Find( BinTree BST, ElementType X );
Position FindMin( BinTree BST );
Position FindMax( BinTree BST );

int main()
{
    BinTree BST, MinP, MaxP, Tmp;
    ElementType X;
    int N, i;

    BST = NULL;
    scanf("%d", &N);
    for ( i=0; i<N; i++ ) {
        scanf("%d", &X);
        BST = Insert(BST, X);
    }
    printf("Preorder:"); PreorderTraversal(BST); printf("\n");
    MinP = FindMin(BST);
    MaxP = FindMax(BST);
    scanf("%d", &N);
    for( i=0; i<N; i++ ) {
        scanf("%d", &X);
        Tmp = Find(BST, X);
        if (Tmp == NULL) printf("%d is not found\n", X);
        else {
            printf("%d is found\n", Tmp->Data);
            if (Tmp==MinP) printf("%d is the smallest key\n", Tmp->Data);
            if (Tmp==MaxP) printf("%d is the largest key\n", Tmp->Data);
        }
    }
    scanf("%d", &N);
    for( i=0; i<N; i++ ) {
        scanf("%d", &X);
        BST = Delete(BST, X);
    }
    printf("Inorder:"); InorderTraversal(BST); printf("\n");

    return 0;
}
/* 你的代码将被嵌在这里 */

输入样例:

10

5 8 6 2 4 1 0 10 9 7

5

6 3 10 0 5

5

5 7 0 10 3

输出样例:

Preorder: 5 2 1 0 4 8 6 7 10 9

6 is found

3 is not found

10 is found

10 is the largest key

0 is found

0 is the smallest key

5 is found

Not Found

Inorder: 1 2 4 6 8 9

#include <stdio.h>
#include <stdlib.h>

typedef int ElementType;
typedef struct TNode *Position;
typedef Position BinTree;
struct TNode{
    ElementType Data;
    BinTree Left;
    BinTree Right;
};

void PreorderTraversal( BinTree BT ); /* 先序遍历,由裁判实现,细节不表 */
void InorderTraversal( BinTree BT );  /* 中序遍历,由裁判实现,细节不表 */

BinTree Insert( BinTree BST, ElementType X );
BinTree Delete( BinTree BST, ElementType X );
Position Find( BinTree BST, ElementType X );
Position FindMin( BinTree BST );
Position FindMax( BinTree BST );

int main()
{
    BinTree BST, MinP, MaxP, Tmp;
    ElementType X;
    int N, i;

    BST = NULL;
    scanf("%d", &N);
    for ( i=0; i<N; i++ ) {
        scanf("%d", &X);
        BST = Insert(BST, X);
    }
    printf("Preorder:"); PreorderTraversal(BST); printf("\n");
    MinP = FindMin(BST);
    MaxP = FindMax(BST);
    scanf("%d", &N);
    for( i=0; i<N; i++ ) {
        scanf("%d", &X);
        Tmp = Find(BST, X);
        if (Tmp == NULL) printf("%d is not found\n", X);
        else {
            printf("%d is found\n", Tmp->Data);
            if (Tmp==MinP) printf("%d is the smallest key\n", Tmp->Data);
            if (Tmp==MaxP) printf("%d is the largest key\n", Tmp->Data);
        }
    }
    scanf("%d", &N);
    for( i=0; i<N; i++ ) {
        scanf("%d", &X);
        BST = Delete(BST, X);
    }
    printf("Inorder:"); InorderTraversal(BST); printf("\n");

    return 0;
}
BinTree Insert( BinTree BST, ElementType X ){
    if(!BST) {          /* 若原树为空,生成并返回一个结点的二叉搜索树 */
        BST = (BinTree)malloc(sizeof(struct TNode));
        BST ->Data = X;
        BST ->Left = BST ->Right = NULL;
    }else {         /* 开始寻找要插入元素的位置 */
        if(X < BST ->Data ) {
            BST ->Left = Insert(BST ->Left, X);
        }else if(X > BST ->Data ) {
            BST ->Right = Insert(BST ->Right, X);
        }
        /* X已经存在,不用操作 */
    }
    return BST;
}
BinTree Delete( BinTree BST, ElementType X ){
    Position Tmp;
    if(!BST)    printf("Not Found\n");
    else {
        if( X < BST->Data)
            BST ->Left = Delete(BST->Left, X);          /* 左子树递归删除 */
        else if(X > BST->Data )
            BST ->Right = Delete(BST->Right , X);       /* 右子树递归删除*/
        else {                                          /* 找到需要删除的结点 */
            if(BST->Left && BST->Right) {               /* 被删除的结点有左右子结点 */
                Tmp=FindMin(BST->Right);                /* 在右子树中找到最小结点填充删除结点 */
                BST->Data = Tmp ->Data;
                BST->Right=Delete(BST->Right,BST->Data);/* 递归删除要删除结点的右子树中最小元素 */
            }else {                                     /* 被删除结点有一个或没有子结点*/
                Tmp = BST;
                if(!BST->Left) BST = BST->Right;        /*有右孩子或者没孩子*/
                else if(!BST->Right)    BST = BST->Left;/*有左孩子,一定要加else,不然BST可能是NULL,会段错误*/
                free(Tmp);                              /*如无左右孩子直接删除*/
            }
        }
    }
    return BST;
}
Position Find( BinTree BST, ElementType X ){
    if(!BST)    return NULL;
    if(BST->Data==X)    return BST;
    if(X>BST->Data)     return Find(BST->Right,X);
    if(X<BST->Data)     return Find(BST->Left,X);

    /*  以下几种写法均可,推荐第上面这一种 

    if(!BST)    return NULL;
    if(BST->Data==X)    return BST;
    if(X>BST->Data)     Find(BST->Right,X);
    if(X<BST->Data)     Find(BST->Left,X);

    if(BST){
        if(BST->Data==X)    return BST;
        if(X>BST->Data)     Find(BST->Right,X);     //如果不写return,则返回过来的值并没有继续返回给最开始的函数
        if(X<BST->Data)     Find(BST->Left,X);
    }
    else return NULL;   

    if(BST){
        if(BST->Data==X)    return BST;
        if(X>BST->Data)     return  Find(BST->Right,X);
        if(X<BST->Data)     return  Find(BST->Left,X);
    }
    return NULL;

    if(BST){
        if(BST->Data==X)    return BST;
        if(X>BST->Data)     return Find(BST->Right,X);
        if(X<BST->Data)     return Find(BST->Left,X);
    }
    else return NULL;
    */
}
/*如果return NULL前面不写else且Find前也不写else,则最后递归返回的也没return,最后只能是执行到了return NULL
返回了,而如果find 前加上了return则就把递归的结果利用起来了,最后加不加else也无所谓了,而如果直接最后else,
不加return find也是可以的,加上了else之后就不会被每一次返回时最后的return NULL给覆盖掉,所以也行。 */
Position FindMin( BinTree BST ){
    if(BST){
        while(BST->Left){
            BST=BST->Left;
        }
    }
    return BST;
}
Position FindMax( BinTree BST ){
    if(BST){
        while(BST->Right){
            BST=BST->Right;
        }
    }
    return BST;
}

题目链接:

https://pta.patest.cn/pta/test/15/exam/3/question/927

时间: 2024-10-11 18:07:36

4-12 二叉搜索树的操作集 (30分)的相关文章

6-12 二叉搜索树的操作集

6-12 二叉搜索树的操作集(30 分) 本题要求实现给定二叉搜索树的5种常用操作. 函数接口定义: BinTree Insert( BinTree BST, ElementType X ); BinTree Delete( BinTree BST, ElementType X ); Position Find( BinTree BST, ElementType X ); Position FindMin( BinTree BST ); Position FindMax( BinTree BST

二叉搜索树的操作集(30 分)

6-12 二叉搜索树的操作集(30 分) 本题要求实现给定二叉搜索树的5种常用操作. 函数接口定义: BinTree Insert( BinTree BST, ElementType X ); BinTree Delete( BinTree BST, ElementType X ); Position Find( BinTree BST, ElementType X ); Position FindMin( BinTree BST ); Position FindMax( BinTree BST

PTA 7-2 二叉搜索树的结构(26 分)

这道题 错在了 交错树样例 , 少了4 分 ,谁知道什么原因的可以告诉我,感激不尽 7-2 二叉搜索树的结构(30 分) 二叉搜索树或者是一棵空树,或者是具有下列性质的二叉树: 若它的左子树不空,则左子树上所有结点的值均小于它的根结点的值:若它的右子树不空,则右子树上所有结点的值均大于它的根结点的值:它的左.右子树也分别为二叉搜索树.(摘自百度百科) 给定一系列互不相等的整数,将它们顺次插入一棵初始为空的二叉搜索树,然后对结果树的结构进行描述.你需要能判断给定的描述是否正确.例如将{ 2 4 1

数据结构 - 从二叉搜索树说到AVL树(一)之二叉搜索树的操作与详解(Java)

二叉搜索树(Binary Search Tree),简称BST,顾名思义,一颗可以用于搜索的二叉树.BST在数据结构中占有很重要的地位,一些高级树结构都是其的变种,例如AVL树.红黑树等,因此理解BST对于后续树结构的学习有很好的作用.同时利用BST可以进行排序,称为二叉排序,也是很重要的一种思想. 二叉树的性质:任意一个节点的所有左子树元素都比该元素值要小,而所有右子树元素都比该元素值要大. 符合该性质的二叉树就是一颗二叉搜索树,当然前提下是树中不允许有重复元素. 所有的二叉搜索树的中序遍历序

二叉搜索树 并查集

BST:二叉搜索树 二叉搜索树的特点:左孩子<根节点<右孩子 二叉搜索树可以有效的管理数的集合 (1)查找 查找数值,大于根节点向右查找,小于根节点向做查找,递归直到找到或者找不到为止. (2)插入 类似于查找,找到相应的位置之后,将那个位置插入新的节点即可. (3)删除 删除就稍微的复杂一点: 需要删除的点没有左孩子,直接将右孩子提上去 需要删除的点的左孩子没有右孩子,直接将左孩子提上去 除此之外,将左孩子的子孙的最大节点提上去. 代码实现: struct node{ int data; n

L2-004 这是二叉搜索树吗? (25 分) (树)

链接:https://pintia.cn/problem-sets/994805046380707840/problems/994805070971912192 题目: 一棵二叉搜索树可被递归地定义为具有下列性质的二叉树:对于任一结点, 其左子树中所有结点的键值小于该结点的键值: 其右子树中所有结点的键值大于等于该结点的键值: 其左右子树都是二叉搜索树. 所谓二叉搜索树的“镜像”,即将所有结点的左右子树对换位置后所得到的树. 给定一个整数键值序列,现请你编写程序,判断这是否是对一棵二叉搜索树或其

二叉搜索树的操作

2018-07-31 15:46:34 一.插入 Insert into a Binary Search Tree 问题描述: 问题求解: public TreeNode insertIntoBST(TreeNode root, int val) { if (root == null) { TreeNode node = new TreeNode(val); return node; } if (root.val > val) root.left = insertIntoBST(root.lef

漫谈二叉搜索树的基本算法(三种思路实现查询操作)

  前面我们说了二叉树前序中序后序遍历的递归非递归算法的实现,下面我们再来说说二叉搜索树~   二叉排序树分为静态查找(find)和动态查找(insert.delete) 二叉搜索树:一棵二叉树,可以为空:如果不为空,满足下列性质: 1.非空左子树的所有键值小于其根结点的键值. 2.非空右子树的所有键值大于其根结点的键值 3.左右子树都是二叉搜索树!! 2.以上是二叉搜索树(也叫二叉排序树)的一些基本操作,此处我们先说一下二叉树的结点定义·· 代码中判断当前结点位置情况的辅助方法以及简单的 ge

PTA L2-004 这是二叉搜索树吗?-判断是否是对一棵二叉搜索树或其镜像进行前序遍历的结果 团体程序设计天梯赛-练习集

L2-004 这是二叉搜索树吗? (25 分) 一棵二叉搜索树可被递归地定义为具有下列性质的二叉树:对于任一结点, 其左子树中所有结点的键值小于该结点的键值: 其右子树中所有结点的键值大于等于该结点的键值: 其左右子树都是二叉搜索树. 所谓二叉搜索树的“镜像”,即将所有结点的左右子树对换位置后所得到的树. 给定一个整数键值序列,现请你编写程序,判断这是否是对一棵二叉搜索树或其镜像进行前序遍历的结果. 输入格式: 输入的第一行给出正整数 N(≤).随后一行给出 N 个整数键值,其间以空格分隔. 输