使用c++设计skiplist数据结构
时间: 2023-09-22 14:06:39 浏览: 100
c++实现数据结构
好的,我可以为您介绍一下使用C++设计skiplist数据结构的基本思路和实现方法。Skiplist是一种基于链表的数据结构,支持高效的查找、插入和删除操作,其核心思想是通过在链表中添加多级索引(即跳表),以实现快速查找的目的。
以下是一个简单的skiplist的C++实现代码:
```c++
#include <iostream>
#include <cstdlib>
#include <ctime>
using namespace std;
const int MAX_LEVEL = 16; // 定义skiplist的最大层数
// 定义节点结构体
struct Node {
int value;
Node **forward; // 存储每层索引的指针
Node(int level, int value) {
this->value = value;
forward = new Node*[level+1];
memset(forward, 0, sizeof(Node*)*(level+1));
}
~Node() {
delete[] forward;
}
};
// 定义skiplist类
class SkipList {
public:
SkipList();
~SkipList();
void insert(int value);
void remove(int value);
bool contains(int value);
void print();
private:
int level;
Node *header;
double probability() {
return (double) rand() / RAND_MAX;
}
int randomLevel() {
int lvl = 0;
while (probability() < 0.5 && lvl < MAX_LEVEL) {
lvl++;
}
return lvl;
}
};
// 初始化skiplist
SkipList::SkipList() {
level = 0;
header = new Node(MAX_LEVEL, 0);
srand(time(NULL));
}
// 销毁skiplist
SkipList::~SkipList() {
if (header != NULL) {
delete header;
}
}
// 插入节点
void SkipList::insert(int value) {
Node *update[MAX_LEVEL+1];
memset(update, 0, sizeof(Node*)*(MAX_LEVEL+1));
Node *x = header;
for (int i = level; i >= 0; i--) {
while (x->forward[i] != NULL && x->forward[i]->value < value) {
x = x->forward[i];
}
update[i] = x;
}
x = x->forward[0];
if (x == NULL || x->value != value) {
int lvl = randomLevel();
if (lvl > level) {
for (int i = level+1; i <= lvl; i++) {
update[i] = header;
}
level = lvl;
}
x = new Node(lvl, value);
for (int i = 0; i <= lvl; i++) {
x->forward[i] = update[i]->forward[i];
update[i]->forward[i] = x;
}
}
}
// 删除节点
void SkipList::remove(int value) {
Node *update[MAX_LEVEL+1];
memset(update, 0, sizeof(Node*)*(MAX_LEVEL+1));
Node *x = header;
for (int i = level; i >= 0; i--) {
while (x->forward[i] != NULL && x->forward[i]->value < value) {
x = x->forward[i];
}
update[i] = x;
}
x = x->forward[0];
if (x->value == value) {
for (int i = 0; i <= level; i++) {
if (update[i]->forward[i] != x) {
break;
}
update[i]->forward[i] = x->forward[i];
}
delete x;
while (level > 0 && header->forward[level] == NULL) {
level--;
}
}
}
// 查找节点
bool SkipList::contains(int value) {
Node *x = header;
for (int i = level; i >= 0; i--) {
while (x->forward[i] != NULL && x->forward[i]->value < value) {
x = x->forward[i];
}
}
x = x->forward[0];
return x != NULL && x->value == value;
}
// 打印skiplist
void SkipList::print() {
for (int i = 0; i <= level; i++) {
Node *x = header->forward[i];
cout << "Level " << i << ": ";
while (x != NULL) {
cout << x->value << " ";
x = x->forward[i];
}
cout << endl;
}
}
int main() {
SkipList sl;
sl.insert(1);
sl.insert(2);
sl.insert(3);
sl.insert(5);
sl.insert(4);
sl.print();
sl.remove(3);
sl.print();
cout << sl.contains(3) << endl;
cout << sl.contains(5) << endl;
return 0;
}
```
这里我们定义了一个Node结构体,用于存储skiplist中的节点信息,其中包括节点的值和每层索引的指针。然后我们定义了一个SkipList类,实现了插入、删除、查找和打印等操作。在插入操作中,我们使用随机数生成每个节点的层数,以实现跳表的效果;在删除操作中,我们首先查找到要删除的节点,然后按照相应的层数更新每层索引的指针,最后删除该节点即可。在查找操作中,我们从最高层逐层向下查找,直到找到目标节点或者遍历完整个skiplist。
希望这个简单的skiplist C++实现代码可以帮助您更好地理解和使用该数据结构。
阅读全文