forked from exCore2/EffectZones
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathTimeBasedEntityCache.cs
More file actions
79 lines (66 loc) · 2.04 KB
/
TimeBasedEntityCache.cs
File metadata and controls
79 lines (66 loc) · 2.04 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
namespace EffectZones;
using ExileCore2.PoEMemory.MemoryObjects;
using System;
using System.Collections.Concurrent;
using System.Linq;
using System.Threading;
public class TimeBasedEntityCache
{
private readonly ConcurrentDictionary<uint, (Entity Entity, DateTime Timestamp)> _cache;
private readonly TimeSpan _expirationTime;
private readonly Timer _cleanupTimer;
public TimeBasedEntityCache(TimeSpan expirationTime)
{
_cache = new ConcurrentDictionary<uint, (Entity Entity, DateTime Timestamp)>();
_expirationTime = expirationTime;
// Create a timer that runs cleanup every 100ms
_cleanupTimer = new Timer(CleanupExpiredEntities, null, 0, 100);
}
public void Add(Entity entity)
{
if (entity == null)
throw new ArgumentNullException(nameof(entity));
_cache.AddOrUpdate(
entity.Id,
_ => (entity, DateTime.UtcNow),
(_, _) => (entity, DateTime.UtcNow)
);
}
public Entity Get(uint id)
{
if (_cache.TryGetValue(id, out var cachedItem))
{
if (DateTime.UtcNow - cachedItem.Timestamp <= _expirationTime)
{
return cachedItem.Entity;
}
// If the entity is expired, remove it and return null
_cache.TryRemove(id, out _);
}
return null;
}
public Entity[] GetAll()
{
var now = DateTime.UtcNow;
return _cache
.Where(kvp => now - kvp.Value.Timestamp <= _expirationTime)
.Select(kvp => kvp.Value.Entity)
.ToArray();
}
private void CleanupExpiredEntities(object state)
{
var now = DateTime.UtcNow;
var expiredKeys = _cache
.Where(kvp => now - kvp.Value.Timestamp > _expirationTime)
.Select(kvp => kvp.Key)
.ToList();
foreach (var key in expiredKeys)
{
_cache.TryRemove(key, out _);
}
}
public void Dispose()
{
_cleanupTimer?.Dispose();
}
}