package nixmsg import "container/list" type lruEntry struct { key string val any } // lruCache 固定容量 LRU,删除时同步移除链表节点。 type lruCache struct { cap int ll *list.List m map[string]*list.Element } func newLRU(cap int) *lruCache { if cap <= 0 { cap = 10000 } return &lruCache{ cap: cap, ll: list.New(), m: make(map[string]*list.Element), } } func (c *lruCache) Get(key string) (any, bool) { el, ok := c.m[key] if !ok { return nil, false } c.ll.MoveToFront(el) return el.Value.(*lruEntry).val, true } func (c *lruCache) Put(key string, val any) { if el, ok := c.m[key]; ok { el.Value.(*lruEntry).val = val c.ll.MoveToFront(el) return } el := c.ll.PushFront(&lruEntry{key: key, val: val}) c.m[key] = el for c.ll.Len() > c.cap { back := c.ll.Back() if back == nil { break } ent := back.Value.(*lruEntry) c.ll.Remove(back) delete(c.m, ent.key) } } func (c *lruCache) Delete(key string) { el, ok := c.m[key] if !ok { return } c.ll.Remove(el) delete(c.m, key) } func (c *lruCache) Len() int { return c.ll.Len() } func (c *lruCache) Has(key string) bool { _, ok := c.m[key] return ok }