线程状态
* 新生状态:用new关键字和thread类或其子类建立一个线程对象后,该线程对象就处于新生状态,处于新生状态的
* 线程拥有自己的内存空间,通过调用start方法进入就绪状态
* 就绪状态:处于就绪状态的线程已经具备了运行条件,但还没有分配到cpu,处于线程就绪队列,等待系统为其分配cpu,
* 等待系统为其分配cpu,等待状态并不是执行状态,当系统选定一个等待执行的Thread对象后,他就会从等待执行状态
* 执行状态,系统挑选的动作称之为cpu调度,一旦获得cpu,线程就进入运行状态并自动调用自己的run方法;
* 运行状态: 在运行状态的线程执行自己run方法的代码,直到调用其他方法而终止,或等待某资源而阻塞或完成任务而死亡
* ,如果在给定的时间内没有执行结束,就会被系统给换下来回到等待执行状态;
* 阻塞状态:
* 处于运行状态的线程在某些情况下,如执行了sleep睡眠方法,或等待I/O设备等资源,将让出cpu并暂时停止自己的运行
* 进入阻塞状态,在阻塞状态的线程不能进入就绪队列,只有当引起阻塞的原因消除时,如睡眠时间已到,或等待的I/O设备空闲下来
* ,线程便转入就绪状态,重新到就绪队列中排队等待,被系统选中后从原来的位置开始继续运行
* 死亡状态:
* 死亡状态时线程生命周期中的最后一个阶段,线程死亡的原因有两个,一个是正常运行的状态完成了它的全部工作
* 另一个是线程被强制性的终止,如通过stop或destroy方法来终止一个线程(不推荐使用这两个方法,前者会产生异常,后者是强制终止
* ,不会释放锁)
停止线程:
* 1.自然终止:线程体常执行完毕;
* 外部干涉:
* 1.线程内中定义线程体中使用的标志;
* 2.线程体使用该标志;
* 3.提供对外的方法改变该标志
package Tread;
public class Thread06 {
public static void main(String[] args) {
Study s = new Study();
new Thread(s).start();
for (int i = 0; i < 1000; i++) {
if (i == 50) {
s.setFlag(false);
}
System.out.println("main" + "-----------" + i);
}
}
}
class Study implements Runnable {
private boolean flag = true;
@Override
public void run() {
while (flag) {
System.out.println("Thread stop.....");
}
}
public boolean isFlag() {
return flag;
}
public void setFlag(boolean flag) {
this.flag = flag;
}
}
阻塞线程(一)
1.join:合并线程,下图代码阻塞了main方法;
package Tread;
public class JoinDemo implements Runnable {
public static void main(String[] args) throws InterruptedException {
JoinDemo j = new JoinDemo();
Thread t = new Thread(j);
t.start();
for (int i = 0; i < 1000; i++) {
if (50 == i) {
t.join();
}
System.out.println("main...." + i);
}
}
@Override
public void run() {
for (int i = 0; i < 1000; i++) {
System.out.println("join...." + i);
}
}
}
* 2.yield:暂停自己的线程,让出cpu的调度:静态方法,
package Tread;
public class YieldDemo implements Runnable {
public static void main(String[] args) throws InterruptedException {
YieldDemo j = new YieldDemo();
Thread t = new Thread(j);
t.start();
for (int i = 0; i < 1000; i++) {
if (i % 20 == 0) {
Thread.yield();
}
System.out.println("main...." + i);
}
}
@Override
public void run() {
for (int i = 0; i < 1000; i++) {
System.out.println("yiled" + "...." + i);
}
}
}
, 3.sleep:线程休眠时不会释放锁 经常用于两种情况:与时间相关的:倒计时 模拟网络延时
package Tread;
public class SleepDemo {
public static void main(String[] args) throws InterruptedException {
int num = 10;
while (true) {
Thread.sleep(1000);
System.out.println(num--);
if (num < 0) {
break;
}
}
}
}
模拟倒计时
package Tread;
import java.text.SimpleDateFormat;
import java.util.Date;
public class SleepDemo01 {
public static void main(String[] args) throws InterruptedException {
Date endtime = new Date(System.currentTimeMillis() + 10 * 1000);
long end = endtime.getTime();
while (true) {
Thread.sleep(1000);
System.out.println(new SimpleDateFormat("mm:ss").format(endtime));
endtime = new Date(endtime.getTime() - 1000);
if (end - 10000 > endtime.getTime()) {
break;
}
}
}
}
模拟网络延时
public class Demo {
public static void main(String[] args) {
Web12306 wb = new Web12306();
Thread t1 = new Thread(wb, "黄牛");
Thread t2 = new Thread(wb, "黄牛2");
Thread t3 = new Thread(wb, "工程师");
t1.start();
t2.start();
t3.start();
}
}
class Web12306 implements Runnable {
int num = 10;
private boolean flag = true;
@Override
public void run() {
while(true) {
if (num <= 0) {
break;
}
try {
Thread.sleep(500);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println(Thread.currentThread().getName() + "抢到了" + num-- + "票");
}
}