您的位置:首页 > 编程语言 > Java开发

Java并行程序基础

2017-05-27 08:57 330 查看


线程的生命周期:


线程的基本操作:

1, 新建线程:使用new关键字创建一个线程对象,将它start()起来即可。start()方法会新建一个线程并让这个线程执行run()方法。如果用run()方法来开启线程,只是做为一个普通的方法调用。

2,终止线程:stop()方法会在结束线程时,会直接终止线程,并立即释放这个线程持有的锁。太过于暴力,强行把执行到一半的线程终止,可能会引起一些数据不一致的问题。代码来源于葛一鸣编著的Java高并发程序设计(侵权必删)代码的执行结果表示使用stop()方法会导致数据不一致的结果,所以不要随便使用stop()方法来停止一个线程。

import java.lang.*;
import java.lang.Exception.*;
public class StopThreadUnsafe{
public static User u = new User();
public static class User{
private int id;
private String name;
public User(){
id=0;
name="0";
}
public void setId(int id){
this.id = id;
}
public int getId(){
return this.id;
}
public void setName(String name){
this.name = name;
}
public String getName(){
return name;
}
public String toString(){
return "User [id="+id+",name="+name+"]";
}
}
public static class ChangeObjectThread extends Thread{
public void run(){
while(true){
synchronized(u){
int v = (int)(System.currentTimeMillis()/10000);

u.setId(v);
try{
Thread.sleep(100);
}catch(InterruptedException e){
e.printStackTrace();
}
u.setName(Integer.toString(v));

}
Thread.yield();
}
}
}
public static class ReadObjectThread extends Thread{
public void run(){
while(true){
synchronized(u){
if(u.getId() != Integer.parseInt(u.getName().trim()))
System.out.println(u.toString());
}
Thread.yield();
}
}
}
public static void main(String[] args) throws InterruptedException{
new ReadObjectThread().start();
while(true){
Thread t = new ChangeObjectThread();
t.start();
Thread.sleep(150);
t.stop();
}
}
}

3,线程中断:线程中断并不会使线程立即退出,而是给线程发送一个通知,至于目标线程接到通知后如何处理,完全由目标线程自行决定。

 

与中断线程有关的三个方法:
public void Thread.interrupt()  //中断线程
public void  Thread.isInterrupted() //判断是否被中断
public void Thread.interrupted() //判断是否被中断,并清除当前中断状态。
如果希望线程在中断后退出,就必须为它增加相应的中断处理代码。

4,等待(wait)和通知(notify)

方法签名如下:

4000
public final void wait() throws InterruptedException
public final native void notify()
这两个方法是在Object类中;如果线程A调用了obj.wait()方法,那么线程A就会停止执行,转化为等待状态,直到有其他线程调用了obj.notify()为止才结速等待。

Object.wait()方法必须包含在对应的synchronzied语句中,无论是wait()还是notify()都需要首先获得目标对象的一个监视器,而在方法执行后都会释放这个监视器。

wait和notify的工作流程细节如下:



Object.wait()和Thread.sleep()的区别:都可以让线程等待若干时间

wait()方法可以被唤醒,wait()方法会释放目标对象的锁,而sleep()方法不会释放任何资源。

5,挂起(suspend)和继续执行(resume)线程:

suspend()在导致线程暂停的同时,并不会去释放任何锁资源。任何其他线程想要访问被它暂用的锁的时,都会被牵连,无法正常继续运行。对于被挂起的线程,从它的线程状态看,是Runnable,如果resume操作意外地发生在suspend()前,那么被挂起的线程就很难有机会被执行了。

6,等待线程结束(join)和谦让(yield)

join()方法签名:
public final void join() throws InterruptedException
public final synchronzied void join(long millis) throws InterruptedException
第一个join()方法表示无限等待,它会一直阻塞当前线程,直到目标线程执行完毕。第二个会给出一个最大等待时间。

如果超过给定时间目标线程还在执行,当前线程也会因为“等不及”,而继续往下执行。

yield()方法签名:
public static native void yield();
使当前线程让出CPU,在让出CPU后,还会进行CPU资源的争夺。

内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: