|
1 | 1 | package helpisu
|
2 | 2 |
|
3 |
| -import ( |
4 |
| - "sync" |
5 |
| -) |
| 3 | +import "sync" |
6 | 4 |
|
7 | 5 | /*
|
8 | 6 | Cache ジェネリックで、スレッドセーフなマップキャッシュ
|
9 |
| - リセットしても初期キャパシティを記憶しています |
| 7 | + sync.Mapのジェネリックなラッパーです |
10 | 8 | */
|
11 | 9 | type Cache[K comparable, V any] struct {
|
12 |
| - m *sync.Pool |
13 |
| - c int |
| 10 | + m *sync.Map |
14 | 11 | }
|
15 | 12 |
|
16 | 13 | // NewCache 新たなCacheを作成
|
17 |
| -func NewCache[K comparable, V any](capacity int) *Cache[K, V] { |
| 14 | +func NewCache[K comparable, V any]() *Cache[K, V] { |
18 | 15 | return &Cache[K, V]{
|
19 |
| - m: &sync.Pool{ |
20 |
| - New: func() interface{} { |
21 |
| - return make(map[K]V, capacity) |
22 |
| - }, |
23 |
| - }, |
24 |
| - c: capacity, |
| 16 | + m: &sync.Map{}, |
25 | 17 | }
|
26 | 18 | }
|
27 | 19 |
|
28 | 20 | // Get 指定したKeyのキャッシュを取得
|
29 | 21 | func (c *Cache[K, V]) Get(key K) (value V, ok bool) {
|
30 |
| - cache, _ := c.m.Get().(map[K]V) |
31 |
| - defer c.m.Put(cache) |
32 |
| - value, ok = cache[key] |
| 22 | + cache, ok := c.m.Load(key) |
| 23 | + if !ok { |
| 24 | + return |
| 25 | + } |
| 26 | + |
| 27 | + value, ok = cache.(V) |
| 28 | + |
| 29 | + return |
| 30 | +} |
| 31 | + |
| 32 | +// GetAndDelete 指定したKeyのキャッシュを取得して削除 |
| 33 | +func (c *Cache[K, V]) GetAndDelete(key K) (value V, ok bool) { |
| 34 | + cache, ok := c.m.LoadAndDelete(key) |
| 35 | + if !ok { |
| 36 | + return |
| 37 | + } |
| 38 | + |
| 39 | + value, ok = cache.(V) |
33 | 40 |
|
34 | 41 | return
|
35 | 42 | }
|
36 | 43 |
|
37 | 44 | // Set 指定したKey-Valueのセットをキャッシュに入れる
|
38 | 45 | func (c *Cache[K, V]) Set(key K, value V) {
|
39 |
| - cache, _ := c.m.Get().(map[K]V) |
40 |
| - cache[key] = value |
41 |
| - c.m.Put(cache) |
| 46 | + c.m.Store(key, value) |
42 | 47 | }
|
43 | 48 |
|
44 | 49 | // Delete 指定したKeyのキャッシュを削除
|
45 | 50 | func (c *Cache[K, V]) Delete(key K) {
|
46 |
| - cache, _ := c.m.Get().(map[K]V) |
47 |
| - delete(cache, key) |
48 |
| - c.m.Put(cache) |
| 51 | + c.m.Delete(key) |
49 | 52 | }
|
50 | 53 |
|
51 | 54 | // Reset 全てのキャッシュを削除
|
52 | 55 | func (c *Cache[K, V]) Reset() {
|
53 |
| - cache, _ := c.m.Get().(map[K]V) |
54 |
| - for key := range cache { |
55 |
| - delete(cache, key) |
56 |
| - } |
57 |
| - |
58 |
| - c.m.Put(cache) |
| 56 | + c.m = &sync.Map{} |
59 | 57 | }
|
0 commit comments