struct hashtable{ //哈希表,用来存state[2]两种状态,其实关键就是重置了[]二重运算符
int key[maxhash],cnt,hash[maxhash];//键,当前映射数,每个状压值的位置
bigint val[maxhash]; //键值
void clear(){ //三个数组全部清空
memset(key,-1,sizeof(key)); //键,key[i]表示第i个映射的状压值
memset(hash,0,sizeof(hash));//hash[i]表示状压值为i的映射在哈希表中的起始位置
memset(val,0,sizeof(val)); //键值,val[i]表示第i个映射的方案数
cnt=0; //哈希表当前映射数目
}
void newnode(int i,int _key){ //创建结点,第I位的键是_KEY
hash[i]=++cnt; //hash第I位就是第CNT个映射
key[cnt]=_key; //KEY存第CNT个状压值
} //VAL存第CNT个状压值的方案数
bigint& operator[](const int _hash){//对[]运算符进行重置,传入的是int类型_hash键,即状压情况,返回bigint方案数
int k; //用于记录是第几个映射,就是说从起始的位置起往右跑找到所存键与当前键相等的那个映射
for(int i=_hash%maxhash;;i++){ //状压值模上最大的状压数量得到其开始位置,冲突则后移直至读出其状态为止
if(i==maxhash)i=0; //达到了最大键的数量就变为0,因有不同状态的状压值模后值相同要处理冲突
if(!hash[i])newnode(i,_hash);//hash表第I位为空表示当前压状值未被打入,则HASH表第I位创建新映射CNT
if(key[hash[i]]==_hash){k=hash[i];break;}//第I位的键就是_hash,表明此状态已存在,读出位置i是第K映射
}//如果hash表第I位已被打入但是其状态值不是_hash就表示有冲突,被往后移了
return val[k];//返回第K个映射的方案数
}
}state[2];//本模板出自插头DP模板题,使用方法:state[now][s]即可获得状压值s对应的方案数
6查找-3散列表
最新推荐文章于 2023-10-31 21:34:57 发布