bitmap.go 1.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566
  1. package utils
  2. type BitMap struct {
  3. bits []byte
  4. size int
  5. }
  6. func NewBitMap(size int) *BitMap {
  7. if size == 0 {
  8. size = 250
  9. }
  10. return &BitMap{
  11. bits: make([]byte, size), // 字节的大小,每个字节中存8个bit
  12. size: size * 8, // 整个bitmap的大小
  13. }
  14. }
  15. func (b *BitMap) Set(id int64) {
  16. // 计算id在哪个bit
  17. idx := hash(id) % b.size
  18. // 计算在哪个byte
  19. byteIdx := idx / 8
  20. // 计算byte中的bit位置
  21. bitIdx := idx % 8
  22. b.bits[byteIdx] |= 1 << bitIdx
  23. }
  24. func (b *BitMap) IsSet(id int64) bool {
  25. // 计算id在哪个bit
  26. idx := hash(id) % b.size
  27. // 计算在哪个byte
  28. byteIdx := idx / 8
  29. // 计算byte中的bit位置
  30. bitIdx := idx % 8
  31. return (b.bits[byteIdx] & (1 << bitIdx)) != 0
  32. }
  33. func (b *BitMap) Export() []byte {
  34. return b.bits
  35. }
  36. func Load(bits []byte) *BitMap {
  37. if len(bits) == 0 {
  38. return NewBitMap(0)
  39. }
  40. return &BitMap{
  41. bits: bits,
  42. size: len(bits) * 8,
  43. }
  44. }
  45. func hash(id int64) int {
  46. // 使用BKDR哈希算法
  47. seed := 131313 // 31 131 1313 13131 131313, etc
  48. hash := 0
  49. // 将整数id拆分为每个字节,并使用BKDR哈希算法计算哈希值
  50. for i := 0; i < 8; i++ {
  51. hash = hash*seed + int((id>>(i*8))&0xFF)
  52. }
  53. return hash & 0x7FFFFFFF
  54. }