散列表通过将关键字值映射到表中某个位置上来存储元素。由给定的关键字值,根据映射,计算得到元素的存储位置来访问元素。
在散列技术中,冲突是指对于关键字集合中的两个关键字值Ki和Kj,当Ki != Kj时,有h(Ki)==h(Kj),h是散列函数。
目前比较常用的散列函数有:除留余数法、平方取中法、折叠法、数字分析法。
一个散列表中冲突是难以避免的,所以要寻求解决冲突的方法。拉链法和开地址法是两种常用的方法。拉链的方法也称开散列法,开地址法又称闭散列法。
拉链法就是为每个散列地址建立一个单链表,表中存储所有具有该散列值的元素。
开地址法是在冲突发生时,通过一种策略来探查下一个空位置,比如有线性探查法、伪随机探查法、二次探查法和双散列法。
下面代码用的是拉链法。
//
// Created by huxijie on 17-3-22.
// 散列表
#include <iostream>
using namespace std;
template <typename T>
struct Node{
T element;
Node<T> *next;
};
//用拉链法解决冲突的散列表类
template <typename T>
class HashTable{
private:
const int capacity; //散列表的容量,选择素数比较好
Node<T>** ht; //散列表每项存放的是链表
int Hash(const T& x); //hash函数
public:
HashTable(const int size);
~HashTable();
bool Insert(const T x); //插入x
bool Remove(const T x); //删除x
bool IsExisted(const T& x); //x是否存在