github.com/maruel/nin@v0.0.0-20220112143044-f35891e3ce7e/hash_map.go (about) 1 // Copyright 2011 Google Inc. All Rights Reserved. 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 package nin 16 17 import "unsafe" 18 19 // murmurHash2, by Austin Appleby 20 func murmurHash2(key []byte, len2 uint32) uint32 { 21 const seed = uint32(0xDECAFBAD) 22 const m = uint32(0x5bd1e995) 23 const r = 24 24 h := uint32(seed ^ len2) 25 data := 0 26 for len2 >= 4 { 27 k := *(*uint32)(unsafe.Pointer(&key[data*4])) 28 k *= m 29 k ^= k >> r 30 k *= m 31 h *= m 32 h ^= k 33 data += 4 34 len2 -= 4 35 } 36 switch len2 { 37 case 3: 38 h ^= uint32(key[data*4+2]) << 16 39 fallthrough 40 case 2: 41 h ^= uint32(key[data*4+1]) << 8 42 fallthrough 43 case 1: 44 h ^= uint32(key[data*4]) 45 h *= m 46 } 47 h ^= h >> 13 48 h *= m 49 h ^= h >> 15 50 return h 51 } 52 53 /* 54 template<> 55 type hash struct { 56 57 sizeT operator()(string key) const { 58 return MurmurHash2(key.str, key.len) 59 } 60 61 type argumentType string 62 type resultType uint 63 64 using stdext::hashMap 65 using stdext::hashCompare 66 67 type StringPieceCmp struct { 68 sizeT operator()(const string& key) const { 69 return MurmurHash2(key.str, key.len) 70 } 71 bool operator()(const string& a, const string& b) const { 72 int cmp = memcmp(a.str, b.str, min(a.len, b.len)) 73 if (cmp < 0) { 74 return true 75 } else if (cmp > 0) { 76 return false 77 } else { 78 return a.len < b.len 79 } 80 } 81 } 82 83 // A template for hashMaps keyed by a StringPiece whose string is 84 // owned externally (typically by the values). Use like: 85 // ExternalStringHash<Foo*>::Type foos; to make foos into a hash 86 // mapping StringPiece => Foo*. 87 template<typename V> 88 type ExternalStringHashMap struct { 89 } 90 type Type unorderedMap<string, V> 91 type Type hashMap<string, V, StringPieceCmp> 92 */