2009-04-22 103 views
1

我正在测试我的Java应用程序的任何性能瓶颈。该应用程序使用concurrent.jar进行锁定。Java性能降低锁的移除

我有一个很高的计算调用,它为其操作调用锁定和解锁函数。 在从代码中移除锁定 - 解锁机制时,我看到了与我的预期相反的多次折叠导致的性能下降。除此之外,观察到CPU消耗增加,这让我觉得程序运行速度更快,但实际上并非如此。

Q1。当我们移除锁时,性能下降的原因是什么?

顺祝商祺!

回答

3

这可能是一个相当常见的发现,具体取决于您正在做什么以及您正在使用什么作为锁定的替代方法。

实质上,会发生什么情况是,像ReentrantLock这样的构造具有一些内置的逻辑,当它们实际上无法获取锁时,它们知道“什么时候退后”。这减少了重复尝试获取锁的逻辑中烧毁的CPU数量,如果使用更简单的锁定结构,则会发生这种情况。

作为一个例子,看看我匆忙搭上的图表here。它显示了不断访问数组中随机元素的线程吞吐量,并使用与锁定机制不同的构造。沿着X轴是线程的数量; Y轴是吞吐量。蓝线是一个ReentrantLock;黄色,绿色和棕色线条使用自旋锁的变体。注意线程数量较少时,自旋锁可以提供更高的吞吐量,但是随着线程数量的增加,ReentrantLock的退出逻辑开始执行,并且结束时性能更好,而争用率更高,自旋锁只是坐着燃烧CPU。

顺便说一句,这真的是在双处理器机器上进行的试运行;我还在亚马逊云中运行它(实际上是一款8路至强处理器),但我浑浑噩噩......错过了该文件,但我会找到它或者很快再次运行实验,并进行培训并发布更新。但是我记得你有一个基本相似的模式。

更新:无论是锁定代码或没有,可以在一些多处理器架构发生的一个现象是,随着多个处理器对内存执行大量的访问,你可以最终充斥内存总线,以及影响处理器相互减速。(这与以太网有点相似 - 您添加到网络中的机器越多,发送数据时发生冲突的机会就越多。)

3

简介它。这里的其他任何东西都只是一个猜测而已。

使用像YourKit探查不仅会告诉你哪些方法是“热点”的CPU时间方面,而且它还会告诉你在哪里线程花费大量的时间BLOCKED或等待

+0

我不同意这里的答案凯文。我已经介绍了我的代码,并且不会借我任何地方。为了简化这些事情,我在CPUS上运行的代码(8个CPU盒)是CPU密集型的过程。 CPU时间方面的热点对于1.带锁的代码和2.不带锁的代码完全相同。很显然,第二秒钟锁定调用丢失了,但是当我说这是一个CPU密集型进程时,没有锁定的代码2的性能应该更高。 您有其他想法吗? 感谢Kevin的回复 – pankajt 2009-05-09 12:47:11

1

难道还要正确执行?例如,应用程序服务器中出现了一个情况,其中一个不同步的HashMap导致了偶尔的无限循环。不难看出工作如何重复。

+0

我试图比较有和没有锁的应用程序的性能。当然,当锁被删除时,我在某些线程运行中得到了“并发修改异常”。 – pankajt 2009-04-23 05:31:12

+0

并非每个错误都被检测到。你不会像喜欢那样比较。 – 2009-04-23 13:01:29

0

当您删除共享内存保护时,看到性能下降和CPU使用率增加的最可能的罪魁祸首是竞态条件。两个或更多线程可以不断地在共享对象上来回翻转状态标志。

更多描述您的应用程序的目的将有助于诊断。