一般的字符串哈希:我们设置一个进制\(x\),把这个串\(s\)看做一个\(x\)进制数。
\(Num=s1*x^0+s2*x^1+s3*x^2+s4*x^3+…\)
然后对一个比较大的质数取模。
这种\(hash\)方法在随机情况下冲突的概率比较小,除非对着哈希构造方法卡。
模数一般选用一个较大的质数来减小冲突的概率。
但在实践中可以发现使用自然溢出\((unsigned\ long\ long)\)的防冲突概率是最小的,毕竟这是一个\((2^{64})\)的模数。
所以最保险的哈希方法是自然溢出加上对大质数取模。
模数:\(1e9+7,1e9+9,19260817,998244353, 1e7+9, 1e7+7,5e5+9\)
进制数:\(131,13331\)
\(code\):
ull hashh(char s[])
{
int l=strlen(s);
ull num=0;
for(int i=0;i<l;++i)
num=num*base+(ull)s[i];
return num&0x7fffffff;
}
\(code\):
ull f[maxn],bas[maxn];
for(int i=1;i<=n;++i)
{
f[i]=f[i-1]*base+s[i]-'a'+1;//存储字符串从前往后的哈希值
bas[i]=bas[i-1]*base;
}
bool check(int l1,int r1,int l2,int r2)
{
return f[r1]-f[l1-1]*bas[r1-l1+1]==f[r2]-f[l2-1]*bas[r2-l2+1];//比较两段是否相同
}