Treap树堆实现简单Set C++实现

Treap树堆实现简单Set C++实现

Treap树实现

Treap树实现

实现代码

/*
author : eclipse
email  : eclipsecs@qq.com
time   : Sat May 23 10:51:30 2020
*/
#include<bits/stdc++.h>
using namespace std;

struct Node {
    int data;
    Node *left;
    Node *right;
    int priority;
    Node(int value, int level) : data(value), left(NULL), right(NULL), priority(level) {}
};

class Treap {
private:
    Node *root;
    void leftRotate(Node* &p);
    void rightRotate(Node* &p);
    void insert(Node* &p, int value);
    void remove(Node* &p, int value);
public:
    Treap();
    void insert(int value);
    void remove(int x);
    bool search(int x);
    Node* treapRoot();
};

Treap::Treap() {
    root = NULL;
}

void Treap::leftRotate(Node* &p) {
    Node *k = p->right;
    p->right = k->left;
    k->left = p;
    p = k;
}

void Treap::rightRotate(Node* &p) {
    Node *k = p->left;
    p->left = k->right;
    k->right = p;
    p = k;
}

void Treap::insert(int value) {
    insert(root, value);
}

void Treap::insert(Node* &p, int value) {
    if (p == NULL) {
        p = new Node(value, rand());
    } else {

        if (value == p->data) {
            return;
        } else if (value < p->data) {
            insert(p->left, value);
        } else {
            insert(p->right, value);
        }

        if(p->left && p->left->priority > p->priority) {
            rightRotate(p);
        } else if(p->right && p->right->priority < p->priority) {
            leftRotate(p);
        }
    }
}

void Treap::remove(int value) {
    remove(root, value);
}

void Treap::remove(Node* &p, int value) {
    if (!p) {
        return;
    }
    if (p->data == value) {
        if (p->left == NULL) {
            p = p->right;
        } else if (p->right == NULL) {
            p = p->left;
        } else {
            if (p->left->priority > p->right->priority) {
                rightRotate(p);
                remove(p->right, value);
            } else if (p->left->priority < p->right->priority) {
                leftRotate(p);
                remove(p->left, value);
            }
        }
    } else {
        if (value < p->data) {
            remove(p->left, value);
        } else {
            remove(p->right, value);
        }
    }
}

bool Treap::search(int value) {
    Node *p = root;
    while (p) {
        if (p->data == value) {
            return true;
        } else {
            p = p->data < value ? p->right : p->left;
        }
    }
    return false;
}

Node* Treap::treapRoot() {
    return root;
}

class Set {
private:
    Treap treap;
public:
    Set() {};
    void insert(int value);
    void erase(int value);
    bool contain(int value);
    bool empty();
};

void Set::insert(int value) {
    treap.insert(value);
}

void Set::erase(int value) {
    treap.remove(value);
}

bool Set::contain(int value) {
    return treap.search(value);
}

bool Set::empty() {
    return treap.treapRoot() == NULL;
}

int main(int argc, char const *argv[]) {
    Set set;
    int N;
    scanf("%d", &N);
    int value;
    for (int i = 0; i < N; i++) {
        scanf("%d", &value);
        set.insert(value);
    }
    for (int i = 0; i < N; i++) {
        scanf("%d", &value);
        printf("%s ", set.contain(value) ? "TRUE" : "FALSE");
    }
    printf("\n");
    for (int i = 0; i < N; i++) {
        scanf("%d", &value);
        set.erase(value);
    }
    printf("%s\n", set.empty() ? "EMPTY" : "NOT EMPTY");
    return 0;
}

算法思路

  • 主流的STL::set<T>都是用一种动态平衡的BST红黑树实现的,这里利用Treap树简单地实set<int>
  • 依赖Treap树堆的增删查操作即可实现,将其封装在Set类中

输入数据

10
20 19 28 34 123 8900 21334 4345 234 567
20 19 28 34 123 8900 21334 4345 234 567
20 19 28 34 123 8900 21334 4345 234 567

输出数据

TRUE TRUE TRUE TRUE TRUE TRUE TRUE TRUE TRUE TRUE
EMPTY

最后

  • 由于博主水平有限,不免有疏漏之处,欢迎读者随时批评指正,以免造成不必要的误解!
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值