hash.go 832 B

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748
  1. // Copyright (c) 2012, Suryandaru Triandana <syndtr@gmail.com>
  2. // All rights reserved.
  3. //
  4. // Use of this source code is governed by a BSD-style license that can be
  5. // found in the LICENSE file.
  6. package util
  7. import (
  8. "encoding/binary"
  9. )
  10. // Hash return hash of the given data.
  11. func Hash(data []byte, seed uint32) uint32 {
  12. // Similar to murmur hash
  13. const (
  14. m = uint32(0xc6a4a793)
  15. r = uint32(24)
  16. )
  17. var (
  18. h = seed ^ (uint32(len(data)) * m)
  19. i int
  20. )
  21. for n := len(data) - len(data)%4; i < n; i += 4 {
  22. h += binary.LittleEndian.Uint32(data[i:])
  23. h *= m
  24. h ^= (h >> 16)
  25. }
  26. switch len(data) - i {
  27. default:
  28. panic("not reached")
  29. case 3:
  30. h += uint32(data[i+2]) << 16
  31. fallthrough
  32. case 2:
  33. h += uint32(data[i+1]) << 8
  34. fallthrough
  35. case 1:
  36. h += uint32(data[i])
  37. h *= m
  38. h ^= (h >> r)
  39. case 0:
  40. }
  41. return h
  42. }