【算法设计题】判定给定的二叉树是否为二叉排序树,第7题(C/C++)

 

目录

第7题 判定给定的二叉树是否为二叉排序树

得分点(必背)

题解:判定给定的二叉树是否为二叉排序树

数据结构定义

判断二叉树是否为二叉排序树

详细解释

1. 空二叉树情况

2. 左右子树都无情况

3. 只有左子树情况

4. 只有右子树情况

5. 左右子树都有情况

测试代码

运行结果


🌈 嗨,我是命运之光

🌌 2024,每日百字,记录时光,感谢有你,携手前行~

🚀 携手启航,我们一同深入未知的领域,挖掘潜能,让每一步成长都充满意义。


第7题 判定给定的二叉树是否为二叉排序树

编写算法,判定给定的二叉树是否是一棵二叉排序树。

得分点(必背)

//数据结构定义
typedef struct node {
    int data; // 节点存储的数据
    struct node *lchild, *rchild; // 左右子树指针
} Bitree;
//判断二叉树是否为二叉排序树
int IsSearchTree(const Bitree *s) {
    if (s == NULL) { // 空二叉树情况
        return 1;
    } else if (s->lchild == NULL && s->rchild == NULL) { // 左右子树都无情况
        return 1;
    } else if (s->lchild && s->rchild == NULL) { // 只有左子树情况
        if (s->lchild->data > s->data) { // 左子树的值不应大于根节点的值
            return 0;
        } else {
            return IsSearchTree(s->lchild);
        }
    } else if (s->lchild == NULL && s->rchild) { // 只有右子树情况
        if (s->rchild->data < s->data) { // 右子树的值不应小于根节点的值
            return 0;
        } else {
            return IsSearchTree(s->rchild);
        }
    } else { // 左右子树都有情况
        if (s->lchild->data > s->data || s->rchild->data < s->data) { // 检查左右子树的值是否满足BST性质
            return 0;
        } else {
            return IsSearchTree(s->lchild) && IsSearchTree(s->rchild);
        }
    }
}

题解:判定给定的二叉树是否为二叉排序树

数据结构定义
typedef struct node {
    int data; // 节点存储的数据
    struct node *lchild, *rchild; // 左右子树指针
} Bitree;
  • data:存储节点的数据。
  • lchild:指向左子树的指针。
  • rchild:指向右子树的指针。
判断二叉树是否为二叉排序树
int IsSearchTree(const Bitree *s) {
    if (s == NULL) { // 空二叉树情况
        return 1;
    } else if (s->lchild == NULL && s->rchild == NULL) { // 左右子树都无情况
        return 1;
    } else if (s->lchild && s->rchild == NULL) { // 只有左子树情况
        if (s->lchild->data > s->data) { // 左子树的值不应大于根节点的值
            return 0;
        } else {
            return IsSearchTree(s->lchild);
        }
    } else if (s->lchild == NULL && s->rchild) { // 只有右子树情况
        if (s->rchild->data < s->data) { // 右子树的值不应小于根节点的值
            return 0;
        } else {
            return IsSearchTree(s->rchild);
        }
    } else { // 左右子树都有情况
        if (s->lchild->data > s->data || s->rchild->data < s->data) { // 检查左右子树的值是否满足BST性质
            return 0;
        } else {
            return IsSearchTree(s->lchild) && IsSearchTree(s->rchild);
        }
    }
}
详细解释
1. 空二叉树情况
if (s == NULL) {
    return 1;
}
  • 如果树是空的(根节点为NULL),则它是二叉排序树,返回1(true)。
2. 左右子树都无情况
else if (s->lchild == NULL && s->rchild == NULL) {
    return 1;
}
  • 如果节点 s 没有左右子树,则它是叶子节点,满足BST的性质,返回1(true)。
3. 只有左子树情况
else if (s->lchild && s->rchild == NULL) {
    if (s->lchild->data > s->data) {
        return 0;
    } else {
        return IsSearchTree(s->lchild);
    }
}
  • 如果节点 s 只有左子树:
    • 检查左子树的根节点的值是否大于当前节点的值。如果是,返回0(false)。
    • 否则,递归检查左子树是否为二叉排序树。
4. 只有右子树情况
else if (s->lchild == NULL && s->rchild) {
    if (s->rchild->data < s->data) {
        return 0;
    } else {
        return IsSearchTree(s->rchild);
    }
}
  • 如果节点 s 只有右子树:
    • 检查右子树的根节点的值是否小于当前节点的值。如果是,返回0(false)。
    • 否则,递归检查右子树是否为二叉排序树。
5. 左右子树都有情况

else {
    if (s->lchild->data > s->data || s->rchild->data < s->data) {
        return 0;
    } else {
        return IsSearchTree(s->lchild) && IsSearchTree(s->rchild);
    }
}
  • 如果节点 s 既有左子树又有右子树:
    • 检查左子树的根节点的值是否大于当前节点的值,或者右子树的根节点的值是否小于当前节点的值。如果是,返回0(false)。
    • 否则,递归检查左子树和右子树是否都为二叉排序树,返回它们的逻辑与(即两者都为真时返回1)。

测试代码

为了验证我们的函数,我们需要构建一些二叉树,并调用IsSearchTree函数进行测试。以下是测试代码:

#include <iostream>
using namespace std;

typedef struct node {
    int data;
    struct node *lchild, *rchild;
} Bitree;

// 判断二叉树是否为二叉排序树的函数
int IsSearchTree(const Bitree *s) {
    if (s == NULL) { // 空二叉树情况
        return 1;
    } else if (s->lchild == NULL && s->rchild == NULL) { // 左右子树都无情况
        return 1;
    } else if (s->lchild && s->rchild == NULL) { // 只有左子树情况
        if (s->lchild->data > s->data) { // 左子树的值不应大于根节点的值
            return 0;
        } else {
            return IsSearchTree(s->lchild);
        }
    } else if (s->lchild == NULL && s->rchild) { // 只有右子树情况
        if (s->rchild->data < s->data) { // 右子树的值不应小于根节点的值
            return 0;
        } else {
            return IsSearchTree(s->rchild);
        }
    } else { // 左右子树都有情况
        if (s->lchild->data > s->data || s->rchild->data < s->data) { // 检查左右子树的值是否满足BST性质
            return 0;
        } else {
            return IsSearchTree(s->lchild) && IsSearchTree(s->rchild);
        }
    }
}

// 创建新节点的辅助函数
Bitree* createNode(int data) {
    Bitree* newNode = new Bitree();
    newNode->data = data;
    newNode->lchild = newNode->rchild = NULL;
    return newNode;
}

int main() {
    // 创建一个二叉排序树
    Bitree* root = createNode(10);
    root->lchild = createNode(5);
    root->rchild = createNode(15);
    root->lchild->lchild = createNode(3);
    root->lchild->rchild = createNode(7);
    root->rchild->rchild = createNode(20);

    // 测试是否为二叉排序树
    if (IsSearchTree(root)) {
        cout << "该二叉树是二叉排序树" << endl;
    } else {
        cout << "该二叉树不是二叉排序树" << endl;
    }

    // 创建一个非二叉排序树
    Bitree* root2 = createNode(10);
    root2->lchild = createNode(5);
    root2->rchild = createNode(15);
    root2->lchild->lchild = createNode(3);
    root2->lchild->rchild = createNode(12); // 12 大于 10,不满足二叉排序树性质

    // 测试是否为二叉排序树
    if (IsSearchTree(root2)) {
        cout << "该二叉树是二叉排序树" << endl;
    } else {
        cout << "该二叉树不是二叉排序树" << endl;
    }

    return 0;
}
运行结果
该二叉树是二叉排序树
该二叉树不是二叉排序树

 嗨,我是命运之光。如果你觉得我的分享有价值,不妨通过以下方式表达你的支持:👍 点赞来表达你的喜爱,📁 关注以获取我的最新消息,💬 评论与我交流你的见解。我会继续努力,为你带来更多精彩和实用的内容。

点击这里👉 ,获取最新动态,⚡️ 让信息传递更加迅速。

  • 15
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
判断给定二叉树是否二叉排序树的方法如下: 1. 对于每个节点,其左子树所有节点的值都小于该节点的值,右子树所有节点的值都大于该节点的值。 2. 对于整棵树,每个节点都满足上述条件。 可以采用中序遍历的方法依次比较每个节点的值,如果中序遍历的结果是单调递增的,则该树为二叉排序树。以下是基于此方法的 C++ 代码实现: ```c++ #include <iostream> #include <vector> #include <stack> using namespace std; // 二叉树结点定义 struct TreeNode { int val; TreeNode *left; TreeNode *right; TreeNode(int x) : val(x), left(NULL), right(NULL) {} }; // 中序遍历二叉树 void inorderTraversal(TreeNode* root, vector<int>& v) { stack<TreeNode*> s; TreeNode* p = root; while (p != NULL || !s.empty()) { while (p != NULL) { s.push(p); p = p->left; } if (!s.empty()) { p = s.top(); s.pop(); v.push_back(p->val); p = p->right; } } } // 判断二叉树是否二叉排序树 bool isBST(TreeNode* root) { if (root == NULL) return true; vector<int> v; inorderTraversal(root, v); for (int i = 1; i < v.size(); i++) { if (v[i] <= v[i-1]) return false; } return true; } // 测试 int main() { TreeNode* root = new TreeNode(5); root->left = new TreeNode(3); root->right = new TreeNode(6); root->left->left = new TreeNode(2); root->left->right = new TreeNode(4); root->right->right = new TreeNode(7); if (isBST(root)) { cout << "该二叉树二叉排序树" << endl; } else { cout << "该二叉树不是二叉排序树" << endl; } return 0; } ```
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

命运之光

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

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

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

打赏作者

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

抵扣说明:

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

余额充值