Surge_by_SukkaW/Build/lib/string-hash.ts
2024-10-12 12:37:45 +08:00

58 lines
1.2 KiB
TypeScript

/**
* FNV-1a Hash implementation
* @author Travis Webb (tjwebb) <me@traviswebb.com>
*
* Ported from https://github.com/tjwebb/fnv-plus/blob/master/index.js
*
* Simplified, optimized and add modified for 52 bit, which provides a larger hash space
* and still making use of Javascript's 53-bit integer space.
*/
export function fnv1a52(str: string) {
const len = str.length;
let i = 0,
t0 = 0,
v0 = 0x2325,
t1 = 0,
v1 = 0x8422,
t2 = 0,
v2 = 0x9CE4,
t3 = 0,
v3 = 0xCBF2;
while (i < len) {
v0 ^= str.charCodeAt(i++);
t0 = v0 * 435;
t1 = v1 * 435;
t2 = v2 * 435;
t3 = v3 * 435;
t2 += v0 << 8;
t3 += v1 << 8;
t1 += t0 >>> 16;
v0 = t0 & 65535;
t2 += t1 >>> 16;
v1 = t1 & 65535;
v3 = (t3 + (t2 >>> 16)) & 65535;
v2 = t2 & 65535;
}
return (
(v3 & 15) * 281_474_976_710_656
+ v2 * 4_294_967_296
+ v1 * 65536
+ (v0 ^ (v3 >> 4))
);
}
export function fnv1a(s: string) {
let h = 0x81_1C_9D_C5;
for (let i = 0, l = s.length; i < l; i++) {
h ^= s.charCodeAt(i);
h += (h << 1) + (h << 4) + (h << 7) + (h << 8) + (h << 24);
}
return (h >>> 0);
}
export const stringHash = (payload: string) => fnv1a52(payload).toString(36) + payload.length.toString(36);