众所周知,Java的同步方法或者同步块即锁的机制,目的是使用sychronized方法或者sychronized块时,当一个线程进入sychronized区域时,其他线程不可能再进入;一旦前一个线程离开sychronized区域,其他线程即可以进入(无需前一个释放锁的线程来唤醒它们)!    具体的实现机制可能有两种:
    第一种,当一个线程进入sychronized区域时,其他试图进入的线程均被阻塞,当前者离开时,其他线程均被系统唤醒,然后去竞争锁。
    第二种,当一个线程进入sychronized区域时,其他试图进入的线程均被不能进入,但是它们并未真正阻塞,而是不断测试锁而不得,当前者离开时,它们之中一个即获得锁。
    显然,这两种机制效果是等同的,对于程序员来说,不必关心究竟Java虚拟机用的是哪一个。当然,第一种机制更合理、高效,因为得不到锁的线程可以不再进入调度队列,从而不必占据CPU时间。很可能Java虚拟机使用的就是第一种机制——目前在我文献中还没有查确切的结论,请懂行的网友谈谈。

解决方案 »

  1.   

    推荐你们去看看《深入JAVA虚拟机》一书,有详尽的解释,何必在这里讨论。
      

  2.   

    讨论这个问题的缘由是:《操作系统》课程中进程和线程的并发控制是一个很重要的内容,在那里定义了各种同步机制,例如信号量、管程、进程(线程)通信等等,但是那些都是基于底层原理的算法(伪代码表示),如果我们要将这些同步算法真正用到程序设计中,就会发现没有那么简单,因为支持多线程的程序设计语言,例如Java,一般都会自动提供一些标准的同步技术,例如锁、同步方法和同步块、线程挂起和阻塞方法等等,而这些技术的细节往往和《操作系统》课程中提到的并不一致,某些线程同步问题只要简单地运用Java内置的锁和同步方法即能解决,而有些问题则必须自己再设计进一步的方案,初学者往往容易在这个地方混淆。除了Java之外,很多程序设计语言都有多线程的支持,例如C++(常用的Posix线程和win32线程两种,还有最新的Boost线程)、C#等,具体的实现机制是不太一样的。