您好,欢迎来到12图资源库!分享精神,快乐你我!我们只是素材的搬运工!!
  • 首 页
  • 当前位置:首页 > 开发 > WEB开发 >
    面试题:再谈Synchronized完成原理!(3)
    时间:2021-08-06 21:12 来源:网络整理 作者:网络 浏览:收藏 挑错 推荐 打印

                 5     7    10   any 

                10    13    10   any 

    这两者虽然显示效果不同,但他们都是经过 monitor 来完成同步的。

    其中在Java虚拟机(HotSpot)中,Monitor是由ObjectMonitor完成的,其主要数据结构如下(位于HotSpot虚拟机源码ObjectMonitor.hpp文件,C++完成的):

    ObjectMonitor() { 

        _header       = NULL

        _count        = 0; // 用来记载该对象被线程获取锁的次数,这也阐明了synchronized是可重入的 

        _waiters      = 0, 

        _recursions   = 0; 

        _object       = NULL

        _owner        = NULL;  // 指向持有ObjectMonitor对象的线程 

        _WaitSet      = NULL;  // 处于wait形状的线程,会被参加到_WaitSet,调用了wait办法之后会进入这里 

        _WaitSetLock  = 0 ; 

        _Responsible  = NULL ; 

        _succ         = NULL ; 

        _cxq          = NULL ; 

        FreeNext      = NULL ; 

        _EntryList    = NULL ; // 处于等候锁block形状的线程,会被参加到该列表 

        _SpinFreq     = 0 ; 

        _SpinClock    = 0 ; 

        OwnerIsThread = 0 ; 

      } 

    每个 Java 对象在 JVM 的对等对象的头中保存锁形状,指向 ObjectMonitor。

    ObjectMonitor 保存了以后持有锁的线程援用,EntryList 中保存目前等候获取锁的线程,WaitSet 保存 wait 的线程。

    还有一个计数器count,每当线程取得 monitor 锁,计数器 +1,当线程重入此锁时,计数器还会 +1。当计数器不为 0 时,其它尝试获取 monitor 锁的线程将会被保存到EntryList中,并被阻塞。

    当持有锁的线程释放了monitor 锁后,计数器 -1。当计数器归位为 0 时,一切 EntryList 中的线程会尝试去获取锁,但只会有一个线程会成功,没有成功的线程依旧保存在 EntryList 中。

    面试题:再谈Synchronized完成原理!

    (责任编辑:admin)