Compare commits

...

3 Commits

3 changed files with 34 additions and 9 deletions

View File

@ -12,7 +12,7 @@ type LRU[T any] struct {
} }
type item[T any] struct { type item[T any] struct {
key string key string
value *T value T
eol time.Time eol time.Time
} }
@ -30,7 +30,7 @@ func (lru *LRU[T]) Set(key string, value T, ttl time.Duration) (evicted bool) {
if element, ok := lru.items[key]; ok { if element, ok := lru.items[key]; ok {
lru.queue.MoveToFront(element) lru.queue.MoveToFront(element)
item := element.Value.(*item[T]) item := element.Value.(*item[T])
item.value = &value item.value = value
item.eol = eol item.eol = eol
return return
@ -43,7 +43,7 @@ func (lru *LRU[T]) Set(key string, value T, ttl time.Duration) (evicted bool) {
item := &item[T]{ item := &item[T]{
key: key, key: key,
value: &value, value: value,
eol: eol, eol: eol,
} }
@ -68,7 +68,7 @@ func (lru *LRU[T]) Get(name string) (value T, ok bool) {
lru.queue.MoveToFront(element) lru.queue.MoveToFront(element)
return *item.value, true return item.value, true
} }
func (lru *LRU[T]) evict() { func (lru *LRU[T]) evict() {

View File

@ -1,6 +1,7 @@
package lru package lru
import ( import (
"fmt"
"github.com/stretchr/testify/assert" "github.com/stretchr/testify/assert"
"testing" "testing"
"time" "time"
@ -39,7 +40,7 @@ func TestEvictExpired(t *testing.T) {
assert.False(t, cache.Set("first", 1, 1000*time.Millisecond)) assert.False(t, cache.Set("first", 1, 1000*time.Millisecond))
assert.False(t, cache.Set("second", 2, 100*time.Millisecond)) assert.False(t, cache.Set("second", 2, 100*time.Millisecond))
time.Sleep(200*time.Millisecond) time.Sleep(200 * time.Millisecond)
assert.True(t, cache.Set("third", 3, 1000*time.Millisecond)) assert.True(t, cache.Set("third", 3, 1000*time.Millisecond))
@ -58,7 +59,7 @@ func TestSetExisted(t *testing.T) {
assert.False(t, cache.Set("first", 1, 200*time.Millisecond)) assert.False(t, cache.Set("first", 1, 200*time.Millisecond))
assert.False(t, cache.Set("second", 2, 500*time.Millisecond)) assert.False(t, cache.Set("second", 2, 500*time.Millisecond))
time.Sleep(100*time.Millisecond) time.Sleep(100 * time.Millisecond)
assert.False(t, cache.Set("first", 11, 1000*time.Millisecond)) assert.False(t, cache.Set("first", 11, 1000*time.Millisecond))
assert.True(t, cache.Set("third", 3, 1000*time.Millisecond)) assert.True(t, cache.Set("third", 3, 1000*time.Millisecond))
@ -76,3 +77,24 @@ func TestDummy(t *testing.T) { // for coverage 100% coverage
cache := New[int](0) cache := New[int](0)
cache.evict() cache.evict()
} }
// We will be storing many short strings as the key and value
func Benchmark(b *testing.B) {
cache := New[string](10)
ttl := 1000 * time.Millisecond
b.Run("Set", func(b *testing.B) {
for i := 0; i < b.N; i++ {
cache.Set(fmt.Sprintf("item:%d", i), fmt.Sprintf("item:%d", i), ttl)
}
})
b.Run("Get", func(b *testing.B) {
for i := 0; i < b.N; i++ {
value, ok := cache.Get(fmt.Sprintf("item:%d", i))
if ok {
_ = value
}
}
})
}

View File

@ -1,9 +1,12 @@
package uniqueschars package uniqueschars
import "unicode" import (
"unicode"
"unicode/utf8"
)
func Unique(s string) bool { func Unique(s string) bool {
m := make(map[rune]struct{}, 50) m := make(map[rune]struct{}, utf8.RuneCountInString(s)/2)
for _, c := range s { for _, c := range s {
c := unicode.ToLower(c) c := unicode.ToLower(c)