添加 SkipList Sbt 等样例, 完善了输出的属性列表

This commit is contained in:
huangsimin 2019-08-28 18:11:51 +08:00
parent c032a243d8
commit f235eb4f63
5 changed files with 117 additions and 52 deletions

View File

@ -1,5 +1,5 @@
CC := g++ CC := g++
C_FLAGS := -std=c++17 -Wall -Wextra -g -O2 C_FLAGS := -std=c++17 -Wall -Wextra -g -O2 -Wno-unused-parameter -Wno-unused-function
BIN := bin BIN := bin
SRC := src SRC := src
@ -23,4 +23,4 @@ run: all
./$(BIN)/$(EXECUTABLE) ./$(BIN)/$(EXECUTABLE)
$(BIN)/$(EXECUTABLE): $(SRC)/* $(BIN)/$(EXECUTABLE): $(SRC)/*
$(CC) $(C_FLAGS) -I$(INCLUDE) -L$(LIB) $^ -o $@ $(LIBRARIES) $(CC) $(C_FLAGS) -I$(INCLUDE) -L$(LIB) $^ -o $@ $(LIBRARIES)

1
include/skiplist Submodule

@ -0,0 +1 @@
Subproject commit b24908c2d6e5b9a355f797cc536dd2d1c627251b

3
run.sh
View File

@ -1,5 +1,8 @@
make clean all
./bin/main 1 ./bin/main 1
./bin/main 1_1 ./bin/main 1_1
./bin/main 2 ./bin/main 2
./bin/main 2_1 ./bin/main 2_1
./bin/main 3 ./bin/main 3
./bin/main 3_1
./bin/main 4

View File

@ -6,12 +6,13 @@
#include <string> #include <string>
#include <map> #include <map>
#include <random> #include <random>
#include "skiplist/skiplist.h"
using namespace std; using namespace std;
using chrono::high_resolution_clock; using chrono::high_resolution_clock;
using std::string; using std::string;
int IntCompare(int v1, int v2) { int IntCompare(ULONG v1, ULONG v2) {
if (v1 > v2) { if (v1 > v2) {
return 1; return 1;
} else if (v1 < v2) { } else if (v1 < v2) {
@ -23,7 +24,7 @@ int IntCompare(int v1, int v2) {
const ULONG N = 5000000; const ULONG N = 5000000;
vector<unsigned int> vec; vector<ULONG> vec;
map<string, void (*)()> funcmap ; map<string, void (*)()> funcmap ;
void init() { void init() {
@ -49,10 +50,7 @@ void init() {
} }
void Case1() { void Case1() {
std::map<int, int> m; std::map<ULONG, ULONG> m;
default_random_engine e;
std::uniform_int_distribution<> dist{0, 1000000000};
high_resolution_clock::time_point t1 = high_resolution_clock::time_point t1 =
high_resolution_clock::now(); //返回时间戳 high_resolution_clock::now(); //返回时间戳
@ -64,7 +62,7 @@ void Case1() {
high_resolution_clock::time_point t2 = high_resolution_clock::time_point t2 =
high_resolution_clock::now(); //返回时间戳 high_resolution_clock::now(); //返回时间戳
std::cout << (t2 - t1).count() / N << std::endl; std::cout << (t2 - t1).count() / N << " ns/op" << std::endl;
std::cout << "end RBTree Case <Put> Benchmark" << std::endl; std::cout << "end RBTree Case <Put> Benchmark" << std::endl;
@ -72,10 +70,7 @@ void Case1() {
} }
void Case1_1() { void Case1_1() {
std::map<int, int> m; std::map<ULONG, ULONG> m;
default_random_engine e;
std::uniform_int_distribution<> dist{0, 1000000000};
for (ULONG i = 0; i < N; i++) { for (ULONG i = 0; i < N; i++) {
auto v = vec[i]; auto v = vec[i];
@ -92,12 +87,12 @@ void Case1_1() {
high_resolution_clock::time_point t2 = high_resolution_clock::time_point t2 =
high_resolution_clock::now(); //返回时间戳 high_resolution_clock::now(); //返回时间戳
std::cout << (t2 - t1).count() / N << std::endl; std::cout << (t2 - t1).count() / N << " ns/op" << std::endl;
std::cout << "end RBTree Case <Get> Benchmark" << std::endl; std::cout << "end RBTree Case <Get> Benchmark" << std::endl;
} }
void Case2() { void Case2() {
VBTree<int, int> m(IntCompare); VBTree<ULONG, ULONG> m(IntCompare);
high_resolution_clock::time_point t1 = high_resolution_clock::time_point t1 =
high_resolution_clock::now(); //返回时间戳 high_resolution_clock::now(); //返回时间戳
@ -108,15 +103,12 @@ void Case2() {
high_resolution_clock::time_point t2 = high_resolution_clock::time_point t2 =
high_resolution_clock::now(); //返回时间戳 high_resolution_clock::now(); //返回时间戳
std::cout << (t2 - t1).count() / N << std::endl; std::cout << (t2 - t1).count() / N << " ns/op" << std::endl;
std::cout << "end VBTree Case <Put> Benchmark" << std::endl; std::cout << "end VBTree Case <Put> Benchmark" << std::endl;
} }
void Case2_1() { void Case2_1() {
VBTree<int, int> m(IntCompare); VBTree<ULONG, ULONG> m(IntCompare);
default_random_engine e;
std::uniform_int_distribution<> dist{0, 1000000000};
for (ULONG i = 0; i < N; i++) { for (ULONG i = 0; i < N; i++) {
auto v = vec[i]; auto v = vec[i];
@ -133,16 +125,13 @@ void Case2_1() {
high_resolution_clock::time_point t2 = high_resolution_clock::time_point t2 =
high_resolution_clock::now(); //返回时间戳 high_resolution_clock::now(); //返回时间戳
std::cout << (t2 - t1).count() / N << std::endl; std::cout << (t2 - t1).count() / N << " ns/op" << std::endl;
std::cout << "end VBTree Case <Get> Benchmark" << std::endl; std::cout << "end VBTree Case <Get> Benchmark" << std::endl;
} }
void Case3() { void Case3() {
BinaryTree tree; BinaryTree tree;
default_random_engine e;
std::uniform_int_distribution<> dist{0, 1000000000};
high_resolution_clock::time_point t1 = high_resolution_clock::time_point t1 =
high_resolution_clock::now(); //返回时间戳 high_resolution_clock::now(); //返回时间戳
@ -153,10 +142,75 @@ void Case3() {
high_resolution_clock::time_point t2 = high_resolution_clock::time_point t2 =
high_resolution_clock::now(); //返回时间戳 high_resolution_clock::now(); //返回时间戳
std::cout << (t2 - t1).count() / N << std::endl; std::cout << (t2 - t1).count() / N << " ns/op" << std::endl;
std::cout << "end SBT Case <Put> Benchmark" << std::endl; std::cout << "end SBT Case <Put> Benchmark" << std::endl;
} }
void Case3_1() {
BinaryTree tree;
for (ULONG i = 0; i < N; i++) {
auto v = vec[i];
tree.insert(v);
}
high_resolution_clock::time_point t1 =
high_resolution_clock::now(); //返回时间戳
for (auto iter = vec.begin(); iter != vec.end(); iter++) {
tree.find(*iter);
}
high_resolution_clock::time_point t2 =
high_resolution_clock::now(); //返回时间戳
std::cout << (t2 - t1).count() / N << " ns/op" << std::endl;
std::cout << "end SBT Case <find(Get)> Benchmark" << std::endl;
}
void Case4() {
struct skiplist *list = skiplist_new();
high_resolution_clock::time_point t1 =
high_resolution_clock::now(); //返回时间戳
for (ULONG i = 0; i < N; i++) {
auto v = vec[i];
skiplist_insert(list, v, v);
}
high_resolution_clock::time_point t2 =
high_resolution_clock::now(); //返回时间戳
std::cout << (t2 - t1).count() / N << " ns/op" << std::endl;
std::cout << "end SkipList Case <insert(Put)> Benchmark" << std::endl;
}
void Case4_1() {
struct skiplist *list = skiplist_new();
for (ULONG i = 0; i < N; i++) {
auto v = vec[i];
skiplist_insert(list, v, v);
}
high_resolution_clock::time_point t1 =
high_resolution_clock::now(); //返回时间戳
for (auto iter = vec.begin(); iter != vec.end(); iter++) {
skiplist_search(list, *iter);
}
high_resolution_clock::time_point t2 =
high_resolution_clock::now(); //返回时间戳
std::cout << (t2 - t1).count() / N << " ns/op" << std::endl;
std::cout << "end SkipList Case <search(Get)> Benchmark" << std::endl;
}
int main(int argc, char *argv[]) { int main(int argc, char *argv[]) {
init(); init();
@ -167,8 +221,13 @@ int main(int argc, char *argv[]) {
funcmap["2_1"] = Case2_1; funcmap["2_1"] = Case2_1;
funcmap["3"] = Case3; funcmap["3"] = Case3;
funcmap["3_1"] = Case3_1;
cout << argv[1] << endl; funcmap["4"] = Case4;
funcmap["4_1"] = Case4_1;
cout << endl;
cout << "case: " << argv[1] << endl;
string fname = argv[1]; string fname = argv[1];
funcmap[fname](); funcmap[fname]();
} }

View File

@ -2,25 +2,27 @@
#include <iostream> #include <iostream>
using namespace std; using namespace std;
typedef unsigned long ULONG;
class SBTNode { class SBTNode {
public: public:
//size:子树大小(就是以当前结点为根构成的树有多少结点) //size:子树大小(就是以当前结点为根构成的树有多少结点)
//data:权值,就是树上的结点储存的值 //data:权值,就是树上的结点储存的值
//value:应该是临时储存权值的 //value:应该是临时储存权值的
int data, size, value; ULONG data, size, value;
SBTNode * lchild, * rchild, * father; SBTNode * lchild, * rchild, * father;
//构造函数,参数分别为 权值,以当前结点为根的树的大小,父亲结点 //构造函数,参数分别为 权值,以当前结点为根的树的大小,父亲结点
SBTNode(int init_data, int init_size = 0, SBTNode * init_father = NULL); SBTNode(ULONG init_data, ULONG init_size = 0, SBTNode * init_father = NULL);
~SBTNode(); ~SBTNode();
//下面依次是 //下面依次是
//二叉排序树的插入搜索找前驱找后继移除某个度为0或1的结点移除某个权值的点找出第k大的元素 //二叉排序树的插入搜索找前驱找后继移除某个度为0或1的结点移除某个权值的点找出第k大的元素
void insert(int value); void insert(ULONG value);
SBTNode * search(int value); SBTNode * search(ULONG value);
SBTNode * predecessor(); SBTNode * predecessor();
SBTNode * successor(); SBTNode * successor();
void remove_node(SBTNode * delete_node); void remove_node(SBTNode * delete_node);
bool remove(int value); bool remove(ULONG value);
int select(int k); ULONG select(ULONG k);
}; };
class BinaryTree { class BinaryTree {
@ -31,17 +33,17 @@ public:
~BinaryTree(); ~BinaryTree();
//下面依次是 //下面依次是
//二叉树的插入 查找 删除结点 找出第k大的树都是以上面的结点类的函数为基础的 //二叉树的插入 查找 删除结点 找出第k大的树都是以上面的结点类的函数为基础的
void insert(int value); void insert(ULONG value);
bool find(int value); bool find(ULONG value);
bool remove(int value); bool remove(ULONG value);
int select(int k); ULONG select(ULONG k);
}; };
//这里搞了个权值为0的结点避免在边界情况时对空指针NULL进行特判所以将所有原本指向空指针的情况都改为指向一个 ZPTR并将其 size 设置为 0从而降低代码复杂度。 //这里搞了个权值为0的结点避免在边界情况时对空指针NULL进行特判所以将所有原本指向空指针的情况都改为指向一个 ZPTR并将其 size 设置为 0从而降低代码复杂度。
SBTNode ZERO(0); SBTNode ZERO(0);
SBTNode * ZPTR = &ZERO; SBTNode * ZPTR = &ZERO;
SBTNode::SBTNode(int init_data, int init_size, SBTNode * init_father) { SBTNode::SBTNode(ULONG init_data, ULONG init_size, SBTNode * init_father) {
data = init_data; data = init_data;
size = init_size; size = init_size;
lchild = ZPTR; lchild = ZPTR;
@ -108,7 +110,7 @@ SBTNode * right_rotate(SBTNode * node) {
//利用上面的左右旋进行调整的函数 //利用上面的左右旋进行调整的函数
//flag为false处理左子树更高的情况否则处理右子树更高的情况 //flag为false处理左子树更高的情况否则处理右子树更高的情况
//node:要调整的子树的根结点 //node:要调整的子树的根结点
SBTNode * maintain(SBTNode * node, bool flag) { SBTNode * maULONGain(SBTNode * node, bool flag) {
//左子树比右子树高(或者叫深度要深) //左子树比右子树高(或者叫深度要深)
if (flag == false) { if (flag == false) {
//LL型左子树的左子树的元素个数大于右子树的元素个数应进行右旋 //LL型左子树的左子树的元素个数大于右子树的元素个数应进行右旋
@ -150,17 +152,17 @@ SBTNode * maintain(SBTNode * node, bool flag) {
//递归调用,处理可能左子树的左子树高度更高的情况 //递归调用,处理可能左子树的左子树高度更高的情况
//false表示左子树较高 //false表示左子树较高
node->lchild = maintain(node->lchild, false); node->lchild = maULONGain(node->lchild, false);
//其右子树的右子树高度更高的情况 //其右子树的右子树高度更高的情况
node->rchild = maintain(node->rchild, true); node->rchild = maULONGain(node->rchild, true);
//最后再对子树根结点的左右子树递归进行调整 //最后再对子树根结点的左右子树递归进行调整
node = maintain(node, false); node = maULONGain(node, false);
node = maintain(node, true); node = maULONGain(node, true);
//返回调整后的子树的根结点 //返回调整后的子树的根结点
return node; return node;
} }
SBTNode * insert(SBTNode * node, int value) { SBTNode * insert(SBTNode * node, ULONG value) {
if (value == node->data) { if (value == node->data) {
return node; return node;
} else { } else {
@ -179,10 +181,10 @@ SBTNode * insert(SBTNode * node, int value) {
} }
} }
} }
return maintain(node, value > node->data); return maULONGain(node, value > node->data);
} }
SBTNode * SBTNode::search(int value) { SBTNode * SBTNode::search(ULONG value) {
if (data == value) { if (data == value) {
return this; return this;
} else if (value > data) { } else if (value > data) {
@ -242,7 +244,7 @@ void SBTNode::remove_node(SBTNode * delete_node) {
delete delete_node; delete delete_node;
} }
bool SBTNode::remove(int value) { bool SBTNode::remove(ULONG value) {
SBTNode * delete_node, * current_node; SBTNode * delete_node, * current_node;
current_node = search(value); current_node = search(value);
if (current_node == ZPTR) { if (current_node == ZPTR) {
@ -261,9 +263,9 @@ bool SBTNode::remove(int value) {
return true; return true;
} }
int SBTNode::select(int k) { ULONG SBTNode::select(ULONG k) {
//rank表示当前结点在子树的排位 //rank表示当前结点在子树的排位
int rank = lchild->size + 1; ULONG rank = lchild->size + 1;
//若rank等于第k小的k说明就是要找的值直接返回权值即可 //若rank等于第k小的k说明就是要找的值直接返回权值即可
if (rank == k) { if (rank == k) {
return data; return data;
@ -288,7 +290,7 @@ BinaryTree::~BinaryTree() {
} }
} }
void BinaryTree::insert(int value) { void BinaryTree::insert(ULONG value) {
if (root == NULL) { if (root == NULL) {
//初始化时只有根结点所以子树大小为1 //初始化时只有根结点所以子树大小为1
root = new SBTNode(value, 1); root = new SBTNode(value, 1);
@ -297,7 +299,7 @@ void BinaryTree::insert(int value) {
} }
} }
bool BinaryTree::find(int value) { bool BinaryTree::find(ULONG value) {
if (root->search(value) == NULL) { if (root->search(value) == NULL) {
return false; return false;
} else { } else {
@ -305,10 +307,10 @@ bool BinaryTree::find(int value) {
} }
} }
bool BinaryTree::remove(int value) { bool BinaryTree::remove(ULONG value) {
return root->remove(value); return root->remove(value);
} }
int BinaryTree::select(int k) { ULONG BinaryTree::select(ULONG k) {
return root->select(k); return root->select(k);
} }