线程控制

 

Java的Thread类提供了一组对线程控制的方法,其中常用的有:

 

Thread类的成员静态方法sleep(),使当前正在运行的线程无条件停止运行。必须在方法内指定停止的毫秒值。

 

Thread类的成员函数interrupt方法可以强制唤醒调用对象代表的线程。(无论该线程是以何种方式停止的)

 

Thread类的setDaemon方法可以设置调用对象代表的线程为后台线程,必须要在线程启动前调用。(当程序中只剩余后台线程时,线程自动结束)

 

Thread类的join方法使当前正在运行的线程停止,直到调用对象代表的线程结束。

 

Thread类的yield方法可以使调用对象代表的线程回到等待CPU执行权状态,重新由CPU分发执行权
   


同步下的线程控制:


  线程控制多用于同步线程下,Java也提供了相应的控制功能,对应Lock与synchronized分别有两种组合,使用方式必须在同步区域内,而且调用对象必须与同步对象相关。

 

wait()与notify()以及notifyAll():

 

  因为synchronized的同步对象可以是任意对象,所以以上三个方法被封装在Object内,专门为synchronized区域提供对线程的控制。

 

  wait使当前线程停止,并且会释放持有的同步对象,使其它等待该同步对象的线程可以运行。直到wait方法指定的毫秒值超时,或是被其它线程使用notify方法唤醒,唤醒后接着从wait的下一行向下执行,如果此时该同步区域被其它线程占用,那么被notify后的线程需要在同步区外等待。

 

  一般情况下notify方法唤醒的都是第一个在此同步对象上等待的线程。notifyAll唤醒当前同步对象下的所有线程。

 

  sleep()与wait()有很大的区别。

 

  sleep 属于Thread的静态成员方法。所以在任何地方都可以能过Thread.sleep()调用,使当前线程进入睡眠状态。

 

  wait 是Object的普通成员函数,只能使用在synchronized方法或区域内且必须由synchronized标记的同步对象调用。即被A同步对象wait的线程,必须由A同步对象notify,才能被唤醒。所以这也是wait方法会释放持有同步对象的原因。


  也就是说wait与notify必须放在synchronized的区域或方法内,而且必须由synchronized的区域或方法指定的那个同步对象所调用。否则报IllegalMonitorStateException异常。


  直接不加任何对象调用wait所使用的标记对象锁就是this.wait(),这是很容易忽略的地方。

 

await()与signal()以及signalAll():
 

  对应于Lock,也有同样的三个同步线程控制方法。方法被定义在了interface Condition中。

 

  Lock中有newCondition()方法,可以通过一个Lock或Lock子类的对象调用该方法获取一个在此Lock同步对象上的Condition对象。

 

  然后使用这个Condition对象可以对await与signal以及signalAll方法操作。用法如同wait与notify以及notifyAll在synchronized区域内一样。

 

   Lock与synchronized的区别类似于C++中临界区与互斥对象的区别。synchronized一个同步区对应一个wait和notify。Lock可以对应多个Condition而每个Condition都有自己的await与signal。Lock接口可以对同步代码的操作更广泛,可以一个Lock对象支持多个Condition对象。每newCondition一次都会产生一个新的Condition对象。只要是同一个Lock的newCondition方法得到的Condition对象,都可以在此Lock.lock与Lock.uplock之间使用。

 

  不同Condition对象之间的await与signal操作互不影响。

 

  用更简单的说,notify只能唤醒synchronized同步对象下最先wait的那个线程,或是唤醒synchronized同步对象下全部wait的线程,而Condition对象的signal方法可以唤醒对应的Condition对象await的线程,只要这些Condition对象来自于同一个Lock即可。

 

  其原理也就是在synchronized区域下产生多个有编号的wait与notify组,每个组都被Condition对象封装,互不影响。

 

  synchronized用于规定一个作用域,也可以修饰一个函数。关键词代替C++中的临界区,互斥对象,信号灯,事件对象。happy吗? 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值