多线程(一)线程常用方法

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/lyj434786736lyj/article/details/81126587

一、Thread的构造方法

常用的就前面的几个:

1.Thread(Runnable target)。参数为实现了Runnable接口的类。

2.Thread(String name)。参数为线程的名字。

3.Thread(Runnable target,String name)。

二、常用方法

start:启动线程。

yield:注意这是一个静态的方法。使当前运行线程释放处理器资源。

sleep:这也是一个静态方法,即使当前运行线程休眠millis毫秒。后一个参数nanos基本不起什么作用,源码只是对其做了四舍五入的判断,感兴趣的同学自行查阅。

join:Thread提供了让一个线程等待另一个线程完成的方法——join()方法。当在某个程序执行流中调用其他线程的join()方法时,调用线程将被阻塞,直到被join()加入的join()线程执行完为止。其中,join():等待被join()的线程执行完成后,调用线程再执行;join(long millis):调用线程等待被join的线程的时间最长为millis毫秒。如果在millis毫秒内被join的线程还没有执行结束,则不再等待。

下面用一段代码解释一下join方法:

	public static void main(String[] args) throws InterruptedException {
		//启动子线程
		new JoinThread("新线程").start();
		for(int i=0;i<100;i++){
			if(i==20){
				JoinThread jt=new JoinThread("被Join的线程");
				jt.start();
				//main线程调用了jt线程的join()方法,main线程
				//必须等jt执行结束才会向下执行
				jt.join();
			}
			System.out.println(Thread.currentThread().getName()+" "+i);
		}
	}

上述代码中,在main方法中调用了jt线程,实际上main线程即为调用线程,jt即为被join()的线程。若执行jt.join(),则jt线程执行完main线程才会执行;若执行jt,join(2000),则若jt线程执行2000毫秒后仍未执行完,main线程也启动,和jt并行执行。

currentThread:返回当前正在运行的线程。

三、方法代码演示

下面通过一段有意思的代码演示各种方法。

//军队线程
//模拟作战双方的行为
public class ArmyRunnable implements Runnable {

	//volatile保证了线程可以正确的读取其他线程写入的值
	//可见性 ref JMM, happens-before原则
	volatile boolean keepRunning = true;

	@Override
	public void run() {
		while(keepRunning){
			//发动5连击
			for(int i=0;i<5;i++){
				System.out.println(Thread.currentThread().getName()+"进攻对方["+i+"]");
				//让出了处理器时间,下次该谁进攻还不一定呢!
				Thread.yield();
			}
		}
		System.out.println(Thread.currentThread().getName()+"结束了战斗!");
	}
}
//关键历史人物线程
public class KeyPersonThread extends Thread {

	public void run(){
		System.out.println(Thread.currentThread().getName()+"开始了战斗!");
		for(int i=0;i<10;i++){
			System.out.println(Thread.currentThread().getName()+"左突右杀,攻击隋军...");
		}
		System.out.println(Thread.currentThread().getName()+"结束了战斗!");
	}
}
/**
 * 隋唐演义大戏舞台
 */
public class Stage extends Thread {

	public void run(){
		
		System.out.println("欢迎观看隋唐演义");
		//让观众们安静片刻,等待大戏上演
		try {
			Thread.sleep(5000);
		} catch (InterruptedException e1) {
			e1.printStackTrace();
		}
		System.out.println("大幕徐徐拉开");
		
		try {
			Thread.sleep(5000);
		} catch (InterruptedException e1) {
			e1.printStackTrace();
		}
		
		System.out.println("话说隋朝末年,隋军与农民起义军杀得昏天黑地...");
		
		ArmyRunnable armyTaskOfSuiDynasty = new ArmyRunnable();
		ArmyRunnable armyTaskOfRevolt = new ArmyRunnable();
		
		//使用Runnable接口创建线程
		Thread  armyOfSuiDynasty = new Thread(armyTaskOfSuiDynasty,"隋军");
		Thread  armyOfRevolt = new Thread(armyTaskOfRevolt,"农民起义军");
		
		//启动线程,让军队开始作战
		armyOfSuiDynasty.start();
		armyOfRevolt.start();
		
		//舞台线程休眠,大家专心观看军队厮杀
		try {
			Thread.sleep(50);
		} catch (InterruptedException e) {
			e.printStackTrace();
		}
		
		System.out.println("正当双方激战正酣,半路杀出了个程咬金");
		
		Thread  mrCheng = new KeyPersonThread();
		mrCheng.setName("程咬金");
		
		System.out.println("程咬金的理想就是结束战争,使百姓安居乐业!");
		
		//停止军队作战
		//停止线程的方法
		armyTaskOfSuiDynasty.keepRunning = false;
		armyTaskOfRevolt.keepRunning = false;
		
		try {
			Thread.sleep(2000);
		} catch (InterruptedException e) {
			e.printStackTrace();
		}
		
		/*
		 * 历史大戏留给关键人物
		 */
		mrCheng.start();
		
		//万众瞩目,所有线程等待程先生完成历史使命
		try {
			/*
			 * 这里的join参数如果设为1毫秒,则若KeyPersonThread中人物攻击次数很多,也就是1毫秒之内mrCheng线程无法执行完,
				则main线程会启动,与mrCheng线程并行执行。此时会出现执行完System.out.println("谢谢观看隋唐演义,再见!");
				后程咬金仍然在攻击的情况
			 */
			mrCheng.join(1);
		} catch (InterruptedException e) {
			e.printStackTrace();
		}
		
		System.out.println("战争结束,人民安居乐业,程先生实现了积极的人生梦想,为人民作出了贡献!");
		System.out.println("谢谢观看隋唐演义,再见!");
		
	}
	
	public static void main(String[] args) {
		new Stage().start();

	}

}

猜你喜欢

转载自blog.csdn.net/lyj434786736lyj/article/details/81126587
今日推荐