【发布时间】:2008-10-23 10:14:49
【问题描述】:
您是在 Hibernate 中始终使用二级缓存,还是先尝试不使用,然后仅在性能下降时使用?
【问题讨论】:
标签: hibernate
您是在 Hibernate 中始终使用二级缓存,还是先尝试不使用,然后仅在性能下降时使用?
【问题讨论】:
标签: hibernate
先让它发挥作用,然后让它变得更快。如果你不需要缓存,就不要实现它。
【讨论】:
在我使用过的应用程序中,数据库在多个应用程序之间共享,其中一些应用程序根本不是 Java。因此,在这些情况下,二级缓存对我来说不是一个选项,因为我不知道其他应用程序何时可以更新数据库。
【讨论】:
我一直在另一个框架(例如 Spring)的上下文中使用 Hibernate,在其中启用缓存几乎是微不足道的。其中许多项目已通过ehcache 对一些关键领域类使用缓存。
话虽如此,这是我们必须在资源之间进行权衡的另一个领域 - 平衡检索性能与内存使用情况。没有测量的优化已经一次又一次地被证明是不好的做法。
收集有关应用程序性能的指标。然后决定如何解决慢点。缓存可能是您最不必担心的问题。
【讨论】:
如果你做对了(小心选择 N+1 等),在绝大多数情况下,如果没有二级缓存,性能应该是可以接受的
【讨论】:
我们首先尝试不使用它,并且仅在性能下降时使用它。
【讨论】:
引用著名的 Donald Knuth 的话:“程序员会浪费大量时间来思考或担心程序中非关键部分的速度,而在考虑调试和维护时,这些提高效率的尝试实际上会产生强烈的负面影响. 我们应该忘记小的效率,比如大约 97% 的时间:过早的优化是万恶之源。但我们不应该放弃关键的 3% 的机会。”
如果您发现性能问题,只有这样您才能开始优化。而且您应该只优化最大的瓶颈,并在需要时逐步降低。
然而,在 NHibernate 中实现这种优化在大多数情况下对调试和维护的影响可以忽略不计,并且通常可以通过对代码的极少添加来实现。
如果您广泛依赖延迟加载,拥有只读表,不必担心与不使用 NHibernate 的应用程序的并发性,性能是一个问题,并且您了解如何使用二级缓存进行优化(意味着您已经知道这个问题的答案),那么你应该使用二级缓存。
【讨论】:
现在有一个与此相关的休眠特定问题。还有臭名昭著的 LazyInitializationException。基本上,您需要在实体附加到持久性上下文时初始化所有惰性关联。两种方法:
这两种方法会产生完全不同的代码片段,因此将一种方法迁移到另一种可能是一项艰巨的工作。问题是方法1.在不使用二级缓存的情况下会导致大量查询,因此人们可以决定使用方法2导致查询发烧。但是,当您稍后打开 2 级缓存时,方法 2 中的查询不会从缓存中加载数据,而是将结果实体放入其中,从而使查询执行速度比没有缓存时慢。这会导致复杂的事情,比如必须使用查询缓存。
因此,对我来说(在这种特殊情况下)似乎更好的方法是首先为所有实体启用缓存,这通常是微不足道的,然后在开发过程中为不需要它的实体禁用它.
【讨论】: