应用程序中有多少 Caffeine Cache 实例太多了?

How many Caffeine Cache instances in an application is too much?

我有一个用例,我想根据字符串键缓存一个元素映射,其中映射中的每个元素都可以有自己的到期时间。我打算使用缓存缓存并利用 Caffeine 中非常酷的变量到期时间。

类似的东西。

Cache<String, Cache<String, ObjectWithVariableExpiry>>

现在,内部缓存应该是动态创建的,父缓存可以有数千个条目。我想知道这样做是否可以,或者这是否是对咖啡因的一种非常糟糕的使用。我担心的是,对于每个内部 Cache<String, ObjectWithVariableExpiry>,计时器 threads/logic 可能会成为资源消耗者。

非常感谢任何建议。

我想如果不进行分析以查看对堆、对象流失、增长率等的影响,就没有关于“太多”的答案。

是否存在需要嵌套缓存的行为,或者具有复合键的单个缓存是否足够?这将具有相同数量的条目和变量过期时间,但避免了新缓存实例的开销。通常嵌套是围绕组执行操作,例如customer-specific 缓存并使所有条目无效。如果是这种情况,还有其他选择,例如向密钥添加世代 ID,从而使老一代不会被懒惰地检索和驱逐。内部数据结构被分摊为 O(1),因此条目数对性能的影响很小。

缓存实例的开销是内存,因为缓存不会创建自己的线程。缓存由 ConcurrentHashMap 支持,使用多个环形缓冲区、一个用于变量过期的时间轮、用于防止错误共享的填充,以及一个 CountMin 草图(如果大小有界)。这使得缓存更重的对象,但对于一个集合来说并不过分。如果为提示过期设置 Scheduler,那么它将为每个缓存实例安排一个计时器。

很可能不会有问题。缓存是为并发和长期使用而设计的。这意味着对于 non-concurrent 具有高实例创建的情况,它不是最佳的,比如一个 http 请求的范围。它当然可以正常工作,但与更简单的数据结构相比,给垃圾收集器增加了更多压力。

不幸的是,这个问题不足以给出一个好的答案。可能没关系,如果有负面影响,您可能有简单的解决方案,并且负载测试可能会提供更强的信心。