github.com/chain5j/chain5j-pkg@v1.0.7/collection/maps/linked_hashmap/linked_hashmap.go (about) 1 // Package linkedHashMap 2 // 3 // @author: xwc1125 4 package linkedHashMap 5 6 import ( 7 "container/list" 8 "sync" 9 10 "github.com/chain5j/logger" 11 ) 12 13 type Node struct { 14 node *list.Element 15 val interface{} 16 } 17 18 type LinkedHashMap struct { 19 linklistLock *sync.RWMutex 20 linklist *list.List 21 hashmap *sync.Map 22 } 23 24 func NewLinkedHashMap() *LinkedHashMap { 25 return &LinkedHashMap{ 26 linklist: list.New(), 27 linklistLock: new(sync.RWMutex), 28 hashmap: new(sync.Map), 29 } 30 } 31 32 func (m *LinkedHashMap) Lock() { 33 m.linklistLock.Lock() 34 } 35 36 func (m *LinkedHashMap) Unlock() { 37 m.linklistLock.Unlock() 38 } 39 40 func (m *LinkedHashMap) RLock() { 41 m.linklistLock.RLock() 42 } 43 44 func (m *LinkedHashMap) RUnlock() { 45 m.linklistLock.RUnlock() 46 } 47 48 // Add 添加 49 func (m *LinkedHashMap) Add(key interface{}, val interface{}) bool { 50 _, isExists := m.hashmap.Load(key) 51 if isExists { 52 return false 53 } 54 55 m.Lock() 56 linkListNode := m.linklist.PushBack(key) 57 m.Unlock() 58 m.hashmap.Store(key, &Node{ 59 node: linkListNode, 60 val: val, 61 }) 62 63 return true 64 } 65 func (m *LinkedHashMap) AddFront(key interface{}, val interface{}) bool { 66 _, isExists := m.hashmap.Load(key) 67 if isExists { 68 return false 69 } 70 71 m.Lock() 72 linkListNode := m.linklist.PushFront(key) 73 m.Unlock() 74 m.hashmap.Store(key, &Node{ 75 node: linkListNode, 76 val: val, 77 }) 78 79 return true 80 } 81 82 // Get 获取数据 83 func (m *LinkedHashMap) Get(key interface{}) (interface{}, bool) { 84 node, isExists := m.hashmap.Load(key) 85 if !isExists { 86 return nil, false 87 } 88 89 return &node.(*Node).val, true 90 } 91 92 // Exist 判断是否存在 93 func (m *LinkedHashMap) Exist(key interface{}) bool { 94 _, isExists := m.hashmap.Load(key) 95 return isExists 96 } 97 98 // Remove 删除 99 func (m *LinkedHashMap) Remove(key interface{}) { 100 node, isExists := m.hashmap.Load(key) 101 if !isExists { 102 return 103 } 104 105 m.linklistLock.Lock() 106 m.hashmap.Delete(key) 107 m.linklistLock.Unlock() 108 m.linklist.Remove(node.(*Node).node) 109 return 110 } 111 112 // Len 获取len 113 func (m *LinkedHashMap) Len() int { 114 return m.linklist.Len() 115 } 116 117 // =========批量处理========= 118 119 // BatchAdd 批量添加 120 func (m *LinkedHashMap) BatchAdd(kvs ...KV) { 121 if kvs == nil || len(kvs) == 0 { 122 return 123 } 124 var ( 125 noExistKVs = make([]KV, 0) 126 ) 127 128 for _, kv := range kvs { 129 _, isExists := m.hashmap.Load(kv.Key) 130 if !isExists { 131 noExistKVs = append(noExistKVs, kv) 132 } else { 133 logger.Warn("hashmap exist key", "key", kv.Key) 134 } 135 } 136 if len(noExistKVs) == 0 { 137 return 138 } 139 140 m.linklistLock.Lock() 141 defer m.linklistLock.Unlock() 142 for _, kv := range noExistKVs { 143 linkListNode := m.linklist.PushBack(kv.Key) 144 m.hashmap.Store(kv.Key, &Node{ 145 node: linkListNode, 146 val: kv.Val, 147 }) 148 } 149 return 150 } 151 152 // GetLinkList 获取linklist 153 func (m *LinkedHashMap) GetLinkList() *list.List { 154 return m.linklist 155 }