zoukankan      html  css  js  c++  java
  • BST入门

    BST 即 搜索二叉树,它的性质,简而言之,就是对于每一个结点,他的左节点严格小于它,它的右节点严格大于他,满足这样性质的数就是搜索二叉树,它支持求x数的排名(在这里规定,有多个相同的数时,求他的最大排名),求排名x的数,求x数的前驱和后继,加入结点,删除结点

    那么,要满足上面的性质,如果有多个相同的数该如何处理呢?我们的处理办法是增加一个变量cnt,记录这样的数出现的次数即可

    代码实现如下:

    #include<iostream>
    #include<cstdio>
    using namespace std;
    struct node {
        int ls,rs,cnt,v,size;
        node(int left,int right,int size,int value)
            :(ls)left,(rs)right,size(size),v(value),cnt(1){}
        node(){}
    }tree[100001];
    int num;
    inline void update(int root) {
        tree[root].size = tree[tree[root].ls].size+tree[tree[root].rs].size+tree[root].cnt;
    }
    void Insert(int x, int root) {
        if(x==tree[root].v)
            tree[root].cnt++;
            return ;
        else if(x<tree[root].v) {
            if(tree[root].ls) Insert(x,tree[root].ls);
            else tree[tree[root].ls  = ++num ]    = node(0,0,1,x);
        }
        else if(x>tree[root].v) {
            if(tree[root].rs) Insert(x,tree[root].rs);
            else tree[tree[root].rs = ++num] = node(0,0,1,x)    
        }
        return ;
        update(root);
    }
    int rank_value(int x, int root) {
        if(x<=tree[tree[root].ls].size)
            return rank_value(x,tree[root].ls);
        else if(x<=tree[tree[root].ls].size+tree[root].cnt)
            return tree[root].v;
        else return rank_value(x-tree[tree[root].ls].size-tree[root].cnt,tree[root].rs);
    }//查询排名x的数
    int value_rank(int x, int root) {
        if(root) {
            if(tree[root].v<x)
                return value_rank(x,tree[root].ls)
            else if(tree[root].v>x) 
                return value_rank(x,tree[root].rs)+tree[root].cnt+tree[tree[root].ls].size;
            else if(tree[root].v == x) 
                return tree[tree[root].ls].size+tree[root].cnt;
        }//对于一个不存在的数,也可以查询他在序列中的相对位置 
        return 1;
    }//查询数x的排名
    int pre(int x, int root, int ans ) {
        if(x<=tree[root].v) {
            if(!tree[root].ls) return ans;
            else return pre(x,tree[root].ls,ans); 
        }
        if(x>tree[root].v) {
            if(!tree[root].rs) return ans;
            else return pre(x,tree[root].rs,tree[root].v) 
        }
         
    }//查询数x的前驱 
    int main() {
            int n,op,x,root;
        scanf("%d",&n);
        tree[root = ++num] = node(0,0,1,2147483647);
        while(n--) {
            scanf("%d%d",&op,&x);
            if(op==1) {
                cout<<value_rank(x,root)<<endl;//x 的 rank 
            } else if(op==2) {
                cout<<rank_value(x,root)<<endl;//rank为x的数
            } else if(op==3) {
                cout<<pre(x,root,2147483647)<<endl;
            } else if(op==4) {
                cout<<rank_value(value_rank(x+1,root),root)<<endl;//可以替代后继函数 
            } else Insert(x,root);
        }
        return 0;
    } 
  • 相关阅读:
    PHP 5.5.0 Alpha5 发布
    Ubuntu Touch 只是另一个 Android 皮肤?
    MariaDB 10 已经为动态列提供文档说明
    Percona Toolkit 2.1.9 发布,MySQL 管理工具
    Oracle Linux 6.4 发布
    Ruby 2.0.0 首个稳定版本(p0)发布
    Apache Pig 0.11.0 发布,大规模数据分析
    Node.js 0.8.21 稳定版发布
    红薯 MySQL 5.5 和 5.6 默认参数值的差异
    Django 1.5 正式版发布,支持 Python 3
  • 原文地址:https://www.cnblogs.com/delta-cnc/p/12516027.html
Copyright © 2011-2022 走看看