Java线程一

89 阅读3分钟

持续创作,加速成长!这是我参与「掘金日新计划 · 6 月更文挑战」的第13天,点击查看活动详情

进程是操作系统分配资源的单位,线程是调度的基本单位,线程之间共享进程资源。

利用多线程技术可以使系统同时运行多个程序块,缩短出程序响应的时间,提高计算机资源的利用率,达到多任务处理的目的。

线程的五种状态:1、新建状态(New),2、可运行(Runnable),3、运行状态(Running),4、阻塞状态(Blocked);,5、死亡状态(Dead)。

线程状态

新建状态

线程对象被创建后,就进入了新建状态,此时线程尚未启动。

可运行状态

线程对象被创建后,调用该对象的start()方法,从而来启动该线程。启动之后,线程处于可运行状态,随时可能被CPU调度执行。

运行状态

当线程获取了CPU时间片,就处于运行转态,执行程序代码。

阻塞状态

当线程由于某种原因放弃了CPU的使用权就会暂停运行,直到线程进入可运行状态才有机会转到运行状态,一般情况下,阻塞有下面三种情况:

  1. 等待阻塞:调用运行状态的线程的wait()方法,JVM会把该线程放入等待队列中。
  2. 同步阻塞:运行状态的线程在获取synchronized同步锁的时候如果锁被其它线程所占用,就会获取锁失败,它会进入同步阻塞状态。
  3. 其他阻塞:调用了运行状态线程的sleep()方法或者join()方法时,线程会进入阻塞状态。

死亡状态

线程执行完了或者因异常退出,从而结束了线程的生命周期。

使用线程

继承 Thread 类

创建自定义类并继承 Thread 类。然后重新run()方法编写业务代码。

class ThreadTest extends Thread{
    @Override
    public void run() {
        System.out.println(Thread.currentThread().getName());
    }
}

启动线程需要使用start()方法,而不是run()方法。

new ThreadTest().start();//Thread-0
new ThreadTest().start();//Thread-1
new ThreadTest().run();//main

通过start()方法才能启动线程,从而抢占CPU资源,当线程被调度的时候会自动执行run()方法,而当我们直接调用run()方法的时候,仅仅是当做普通对象执行。

实现 Runnable 接口

创建自定义类并实现 Runnable 接口。然后重新run()方法编写业务代码。

class RunnableTest implements Runnable{
    @Override
    public void run() {
        System.out.println(Thread.currentThread().getName());
    }
}

RunnableTest对象并不能直接使用,还需要创建Thread对象,然后当RunnableTest对象注入到Thread对象中,最后调用start()开启线程。

new Thread(new RunnableTest()).start();//Thread-0
new Thread(new RunnableTest()).start();//Thread-1
new RunnableTest().run();//main

由于Java不支持多重继承,如果使用方式一继承Thread创建线程,就无法继承其他类,所以一般有限选择实现Runnable接口。