美文网首页
哈希存储的简单实现

哈希存储的简单实现

作者: 俩孩的爸 | 来源:发表于2019-05-13 19:49 被阅读0次

之前一直都不知道哈希表怎么就能那么快的存取的,今天就来好好研究一番,并且使用C语言简单的实现一下。
刚刚百度了一番,其实哈希存储的实现主要分成两个步骤来考虑:
1、申请一块连续的存储空间,把空间分割成m个桶,用来存储数据。
2、实现一个散列算法,把key经过算法散列对应到我们的m个桶上。

国际惯例,上代码:

main函数部分

#include <stdio.h>
#include <stdlib.h>

int hash(int, int);
void hset(int*, int, int, int);
int hget(int*, int, int);

void main() {
    int m = 100;
    size_t size = (size_t) (sizeof(int) * m);
    int* p = malloc(size);
    int k = 1, v = 1024;
    hset(p, m, k, v);
    printf("设置KEY - VALUE : %d - %d \n", k, v);
    printf("获取KEY - VALUE : %d - %d \n", k, hget(p, m, k));
    free(p);
}

哈希算法,超简单版:

int hash(int key, int m) {
    return key % m;
}

hset函数:

void hset(int* p, int m, int k, int v) {
    int hash_key = hash(k, m);
    p += hash_key;
    *p = v;
}

hget函数:

int hget(int* p, int m, int k) {
    int hash_key = hash(k, m);
    p += hash_key;
    return *p;
}

ooh my god,就是他!!!!!!!!!!!
这么简单吗?就这么简单吗?
嗯呢,就是这么简单。
好意外,好惊喜!(__) 嘻嘻……

言归正传,来看看这个简单的哈希存储是怎么实现的。

1-1内存示意图

图1-1可以看出,整个哈希存储是由一块连续的存储空间,分割成m个桶,每个桶里存储着具体的数据,通的大小由桶内数据类型决定。

桶初始化过程:

int m = 100;  // 定义桶的数量
size_t size = (size_t) (sizeof(int) * m); // 根据桶里存放的数据类型,计算需要的内存空间
int* p = malloc(size); //申请内存

OK,初始化工作完成,我们申请了一块连续的存储空间,可以存放100个桶,每个桶里存放了一个int型数据,每个桶的大小4字节。

也就是我们的这个hashmap可以存放100条int类型的数据,接下来会有大兄弟问了,人家的哈希表能存储理论无限多的数据,怎么你的才能存储100条,或者说有限条数据呢?人家哈希表能存储各种数据类型,你怎么就能存int呢?人家key随意设置,你的为啥1和101就互相覆盖了?人家的……
对呀,那都是人家的哈希表,我的就能存储100条int型数据。O(∩_∩)O哈哈~
开玩笑的,上面那些问题都是高阶哈希表具备的功能,包括自动扩容,任意类型存储,还有哈希碰撞的解决,这些都不在这篇文章的讨论范围内,后续我会专门写文章来解释的。

看一看哈希算法

int hash(int key, int m) {
    return key % m;
}

其实这不是一个严格意义上的哈希算法,但是他却把我们的输入散列到我们所有桶上,要想得到一个好的哈希算法还是挺难的,所以我们这部分可以留给大家自行百度,我只是演示一下这个功能。
通过上面的算法,我们所有的输入都可以散列到一个具体的桶上,这个值就可以帮助我们做哈希定位。

hset和hget

void hset(int* p, int m, int k, int v) {
    int hash_key = hash(k, m);
    p += hash_key;
    *p = v;
}

int hget(int* p, int m, int k) {
    int hash_key = hash(k, m);
    p += hash_key;
    return *p;
}

不管是set还是get,都有执行了这两句

int hash_key = hash(k, m); // 获得哈希值
p += hash_key; //根据哈希值对指针进行偏移 

偏移后的指针,指向的地址就是存储值的内存地址,接下来就简单了,对指针指向的地址赋值就是set,通过指针地址获得数据就是get。

至此,我们的一个简单哈希表就实现了,是不是超简单,希望这篇文章能给菜鸟们帮助,也同时希望大牛们提出宝贵的意见建议。

相关文章

  • 哈希存储的简单实现

    之前一直都不知道哈希表怎么就能那么快的存取的,今天就来好好研究一番,并且使用C语言简单的实现一下。刚刚百度了一番,...

  • 存储引擎的底层数据结构

    1. 哈希存储引擎 介绍 哈希存储引擎是哈希表的持久化实现,支持增、删、改以及随机读取的操作。但不支持顺序扫描。一...

  • 15_哈希表(Hash Table)

    哈希表初识 哈希表,也叫做散列表 它是如何实现高效处理数据的?假设我们利用哈希表来实现映射,存储三对数据:put(...

  • 看看HashMap的源码

    HashMap Java中的HashMap是哈希表(散列表)的实现。哈希表存储的数据是键值对,它能实现快速的查找和...

  • Tourist with Data Structure Thir

    探索哈希表 概念 哈希集合:哈希集合是集合数据结构的实现之一,用于存储非重复值。哈希映射 :哈希映射是映射数据结构...

  • 《高性能mysql》笔记-索引

    索引基础 索引类型B-Tree索引(默认指明索引)按照顺序存储数据 哈希索引概念:哈希索引基于哈希表实现,只有精确...

  • 01. HBase的LSM存储思想

    什么是LSM树? 三种基本的存储引擎——LSM树的由来 哈希存储引擎 是哈希表的持久化实现,支持增、删、改以及随...

  • LSM树由来、设计思想以及应用到HBase的索引

    讲LSM树之前,需要提下三种基本的存储引擎,这样才能清楚LSM树的由来: 哈希存储引擎 是哈希表的持久化实现,支持...

  • LSM-Tree设计思想

    需要提下三种基本的存储引擎,这样才能清楚LSM树的由来: 哈希存储引擎 是哈希表的持久化实现,支持增、删、改以及...

  • HashMap

    HashMap本质是哈希表,通过k-v存储数据,映射关系通过哈希函数构造。 哈希函数的实现方式 1.直接定址法:取...

网友评论

      本文标题:哈希存储的简单实现

      本文链接:https://www.haomeiwen.com/subject/cavqaqtx.html