Skip to content
This repository was archived by the owner on Sep 20, 2023. It is now read-only.

Commit afbcb9e

Browse files
aQuaaQua
aQua
authored and
aQua
committed
146 finish
1 parent 9708000 commit afbcb9e

File tree

2 files changed

+63
-43
lines changed

2 files changed

+63
-43
lines changed

Algorithms/0146.lru-cache/lru-cache.go

+60-43
Original file line numberDiff line numberDiff line change
@@ -33,68 +33,85 @@ func Constructor(capacity int) LRUCache {
3333

3434
// Get 获取 cache 中的数据
3535
func (c *LRUCache) Get(key int) int {
36+
// 利用 hashTable 查询 key
3637
if node, ok := c.nodes[key]; ok {
37-
c.moveToHead(node)
38+
// key 存在的话
39+
// 把对应的 node 移动到 cache 的双向链的 first 位
40+
c.moveToFirst(node)
3841
return node.val
3942
}
43+
44+
// key 不存在,按照题意,返回 -1
4045
return -1
4146
}
4247

43-
func (c *LRUCache) removeLast() {
48+
// Put is 放入新数据
49+
func (c *LRUCache) Put(key int, value int) {
50+
node, ok := c.nodes[key]
51+
52+
if ok { // 更新旧 node
53+
// 更新 node 中的值
54+
node.val = value
55+
// 把 node 放入双向链的 first 位
56+
c.moveToFirst(node)
57+
} else { // 放入新 node
58+
if c.len == c.cap {
59+
// cache 已满,删除 last 位,为新 node 腾地方
60+
// 删除 hashTable 中的记录
61+
delete(c.nodes, c.last.key)
62+
// 删除双向链中的 last 位
63+
c.removeLast()
64+
} else {
65+
c.len++
66+
}
67+
// 为 key 和 value 新建一个节点
68+
node = &doublyLinkedNode{
69+
key: key,
70+
val: value,
71+
}
72+
// 在 hashTable 中添加记录
73+
c.nodes[key] = node
74+
// 把新 node 放入 first 位
75+
c.insertToFirst(node)
76+
}
77+
}
4478

45-
if c.last.prev != nil {
79+
func (c *LRUCache) removeLast() {
80+
if c.last.prev != nil { // 双向链长度 >1
4681
c.last.prev.next = nil
47-
} else {
82+
} else { // 双向链长度 == 1,firt,last 指向同一个节点
4883
c.first = nil
4984
}
5085

5186
c.last = c.last.prev
5287
}
5388

54-
func (c *LRUCache) moveToHead(nd *doublyLinkedNode) {
55-
if nd == c.first {
89+
func (c *LRUCache) moveToFirst(node *doublyLinkedNode) {
90+
switch node {
91+
case c.first:
5692
return
93+
case c.last:
94+
c.removeLast()
95+
default:
96+
// 在双向链中,删除 node 节点
97+
node.prev.next = node.next
98+
node.next.prev = node.prev
5799
}
58100

59-
if nd.prev != nil {
60-
nd.prev.next = nd.next
61-
}
62-
63-
if nd.next != nil {
64-
nd.next.prev = nd.prev
65-
}
66-
67-
if nd == c.last {
68-
c.last = nd.prev
69-
}
70-
if c.first != nil {
71-
nd.next = c.first
72-
c.first.prev = nd
73-
}
74-
75-
c.first = nd
76-
nd.prev = nil
77-
if c.last == nil {
78-
c.last = c.first
79-
}
101+
// 策略是
102+
// 如果需要移动 node 的话
103+
// 先删除,再插入
104+
c.insertToFirst(node)
80105
}
81106

82-
// Put is 放入新数据
83-
func (c *LRUCache) Put(key int, value int) {
84-
nd, ok := c.nodes[key]
85-
86-
if !ok {
87-
if c.len == c.cap {
88-
delete(c.nodes, c.last.key)
89-
c.removeLast()
90-
} else {
91-
c.len++
92-
}
93-
nd = &doublyLinkedNode{}
107+
func (c *LRUCache) insertToFirst(node *doublyLinkedNode) {
108+
if c.last == nil { // **空**双向链
109+
c.last = node
110+
} else { // **非空**双向链
111+
// 默认 node != nil
112+
node.next = c.first
113+
c.first.prev = node
94114
}
95115

96-
nd.val = value
97-
nd.key = key
98-
c.moveToHead(nd)
99-
c.nodes[key] = nd
116+
c.first = node
100117
}

Algorithms/0146.lru-cache/lru-cache_test.go

+3
Original file line numberDiff line numberDiff line change
@@ -70,4 +70,7 @@ func Test_1(t *testing.T) {
7070

7171
cache.Put(3, 3)
7272
// [(3,3)]
73+
74+
cache.Put(3, 33)
75+
// [(3,33)]
7376
}

0 commit comments

Comments
 (0)