【问题标题】:why is synchronized keyword slow in java? [duplicate]为什么java中的同步关键字很慢? [复制]
【发布时间】:2016-02-21 19:46:26
【问题描述】:


最近我和一个朋友讨论了 java 中的并发性,他问我为什么 synchronized 关键字在代码块或方法周围很慢。我回答说它很慢,因为它竞争对象监视器。它还提供了一个在保证之前发生的情况,它必须将其缓存中的所有变量与主内存同步,并且在块的末尾它必须刷新缓存。它还可以防止编译器以及 cpu 重新排序指令。然而,他说这些确实会导致速度放缓,但这并不是性能下降的主要原因。本质上,即使在线程遇到同步块时没有争用,它也会从用户模式切换到内核模式,并且线程必须保存状态,然后当它离开块时,它必须再次重新加载状态。我试图在网上找到描述这一点的文献,但我找不到任何文献。我想知道是否有人可以确认这是正确的?为什么java线程在达到同步时应该进入内核模式,为什么不在此之前?这与link中提出的问题不同,因为我在询问从用户模式到内核模式的显式切换,这会导致性能下降?

【问题讨论】:

标签: java multithreading


【解决方案1】:

你朋友说的绝对不正确。

关于同步的昂贵之处,您说得非常正确。最困难的部分实际上是(尤其是在 x86/x86_64 处理器上)比较和交换指令,它比较并将当前线程设置为锁的所有者。在 x86/x86_64 cmpxchg 指令用于此目的,当它到达主内存时,它比任何常规指令都慢。然后正如您提到的,内存屏障会减慢缓存速度。

在其他一些架构上,尤其是基于 RISC 的架构上,通常使用被动加载独占/存储独占,这通常更快。所以这可能因架构而异。

无论如何,Java(和任何其他语言)都试图避免进入内核,并且大多数 mutext 实现只有在几乎明确需要暂停线程时重试几次后才会这样做。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2014-12-05
    • 2010-12-12
    • 2014-01-09
    • 1970-01-01
    • 2012-12-09
    • 1970-01-01
    • 2022-12-19
    • 2014-03-17
    相关资源
    最近更新 更多