当前位置:首页 > C++知识 > 正文内容

哈希表与哈希函数

亿万年的星光2个月前 (09-13)C++知识195

1. 哈希表(Hash Table)

1.1 基本概念

哈希表是一种通过哈希函数将键(key)映射到表中特定位置来访问记录的数据结构。它提供了平均时间复杂度为O(1)的查找、插入和删除操作。

1.2 核心组成

  1. 键(Key): 用于查找和标识数据的唯一标识符

  2. 值(Value): 与键关联的实际数据

  3. 哈希函数(Hash Function): 将键转换为数组索引的函数

  4. 哈希桶(Buckets): 存储键值对的容器数组

  5. 冲突解决机制: 处理多个键映射到同一索引的情况

1.3 工作原理

键 → 哈希函数 → 哈希值 → 数组索引 → 存储/检索值

1.4 性能特点

  • 平均时间复杂度:

    • 插入: O(1)

    • 查找: O(1)

    • 删除: O(1)

  • 最坏情况时间复杂度: O(n) (当所有键都冲突时)

2. 哈希函数(Hash Function)

2.1 基本概念

哈希函数是将任意大小的数据映射到固定大小值的函数。在哈希表中,它将键转换为数组索引。

2.2 理想哈希函数的特性

  1. 确定性: 相同的键总是产生相同的哈希值

  2. 均匀性: 哈希值应均匀分布在输出空间

  3. 高效性: 计算速度快

  4. 抗碰撞性: 不同键产生相同哈希值的概率低

2.3 常见哈希函数类型

2.3.1 除法哈希法

hash(key) = key % table_size

2.3.2 乘法哈希法

hash(key) = floor(table_size * (key * A - floor(key * A))) 
其中 0 < A < 1

2.3.3 通用哈希法

hash(key) = ((a * key + b) % p) % table_size其中p是大素数,a,b是随机数

2.3.4 字符串哈希函数

// DJB2哈希函数
unsigned long djb2_hash(const char *str) {
    unsigned long hash = 5381;
    int c;
    while ((c = *str++)) {
        hash = ((hash << 5) + hash) + c; // hash * 33 + c
    }
    return hash;
}





2.4 哈希函数设计原则

  1. 考虑键的类型: 整数、字符串、对象等需要不同的处理

  2. 利用键的所有信息: 确保键的每个部分都影响哈希值

  3. 避免规律性: 防止键的模式导致哈希值聚集

  4. 测试均匀性: 实际测试哈希值分布情况


2.5 哈希表与平衡树的比较

特性哈希表平衡树(如红黑树)
平均查找时间O(1)O(log n)
最坏查找时间O(n)O(log n)
范围查询不支持支持
内存使用通常较少通常较多
实现复杂度较简单较复杂



实现方式:

#include <unordered_map> // 哈希表
#include <unordered_set> // 哈希集合

int main() {
    // 哈希表示例
    std::unordered_map<std::string, int> wordCount;
    
    // 插入元素
    wordCount["apple"] = 5;
    wordCount.insert({"banana", 3});
    
    // 查找元素
    if(wordCount.find("apple") != wordCount.end()) {
        std::cout << "apple count: " << wordCount["apple"] << std::endl;
    }
    
    // 哈希集合示例
    std::unordered_set<int> uniqueNumbers;
    uniqueNumbers.insert(1);
    uniqueNumbers.insert(2);
    uniqueNumbers.insert(1); // 重复元素不会被插入
    
    return 0;
}



扫描二维码推送至手机访问。

版权声明:本文由青少年编程知识记录发布,如需转载请注明出处。

分享给朋友:

相关文章

【数据结构】并查集2

【数据结构】并查集2

上一篇文章,简单介绍了并查集。这篇文章,介绍一下并查集的改进以及优化。find函数的优化(路径压缩)因为并查集的merge操作:void merge(int a, int...

【数论】二项式定理

【数论】二项式定理

一、基本概念上面这个式子就叫做二项式定理,又称牛顿二项式定理,该定理给出两个数之和的整数次幂诸如展开为类似项之和的恒等式。二项式定理可以推广到任意实数次幂,即广义二项式定理。 初中高中阶段比...

C++中的max和min函数(最大值,最小值)

1.头文件      最大值最小值函数所在头文件是#include<algorithm>2.用法#include<iostream> #incl...

取模运算总结——数论

编程竞赛有相当一部分题目的结果过于庞大,整数类型无法存储,往往只要求输出取模的结果。例如(a+b)%p,若a+b的结果我们存储不了,再去取模,结果显然不对,我们为了防止溢出,可以先分别对a取模,b取模...

【贪心】区间选点

【贪心】区间选点

【题目描述】数轴上有n个闭区间[ai, bi],取尽量少的点,使得每个区间内都至少有一个点。(不同区间内含的点可以是同一个,1<=n<=10000,1<=ai<=bi<=...

【STL】二分查找函数(算法)—binary_search

【说明】binary_search() 实现了一个二分查找算法。它会在前两个参数指定范围内搜索等同于第三个参数的元素。指定范围的迭代器必须是正向迭代器而且元素必须可以使用 < 运算符来比较。这个...