进程的概念
- 进程是指可执行程序并存放在计算机存储器的一个指令序列,它是一个动态执行的过程;
- 线程是比进程还要小的运行单位,一个进程包含多个线程;
- 线程可以看作一个子程序;
- 线程调度的先后次序是随机的。
线程的创建(两种方法)
- 创建一个
Thread
类,或者一个Thread
子类的对象; - 创建一个实现
Runnable
接口的类的对象。
new MyThread().start() //方法一,通过创建Thread子类的对象创建进程
new Thread(new MyRunnable()).start() //方法二,通过Runnable接口类传入Thread类构造函数,构造Thread对象,此方法更为常用,更适合需要继承另一个父类的情况
Thread
类中的常用方法
方法 | 功能 |
---|---|
public void run() |
线程相关的代码写在该方法中,一般需要重写 |
public void start() |
启动线程的方法 |
public static void sleep(long m) |
线程休眠m毫秒的方法 |
public void join() |
优先执行调用join() 方法的线程,抢占资源 |
创建一个实现Runnable
接口的类的对象
只有一个方法
run();
;Runnable
是Java中用以实现线程的接口;任何实现线程功能的类都必须实现该接口;
使用
Runnable
接口创建线程的原因- Java不支持多继承,如果继承
Thread
类的同时还需要继承别的类就没法实现了,因此通过接口的形式实现继承; - 不打算重写
Thread
类的其他方法。
- Java不支持多继承,如果继承
Runnable
接口实现类的创建和使用示例代码如下:
public static void main(String[] args){
PrintRunnable td = new PrintRunnable();
Thread td1=new Thread(td);
td1.start();
}
public class PrintRunnable implements Runnable{
@Override
public void run() {
System.out.println(Thread.currentThread().getName()
+"线程正在执行!");
}
}
- 使用
Runnable
接口实现类的时候需要先实例化接口实现类的对象,再去实例化一个Thread
类的对象来运行实现类定义的线程。
线程的状态
- 新建状态(New)
- 可运行状态(Runnable)(就绪状态)
- 正在运行状态(Running)
- 阻塞(Blocked)
- 终止(Dead)
线程的生命周期
sleep方法应用
Thread
类的方法;
public static void sleep(long millis)
- 作用:在指定的毫秒数内让正在执行的线程休眠(暂停执行);
- 参数为休眠的时间,单位是毫秒。
join方法应用
Thread
类的方法;
public final void join()
- 作用:等待调用该方法的线程结束后才能执行;
public final void join(long millis)
- 作用:等待该线程终止的最长时间为millis毫秒;
- 抢占CPU使用权,迫使其他线程放弃CPU使用权。
线程优先级
Java为线程类提供了10个优先级;
优先级可以用整数1-10表示,超过范围会抛出异常;
主线程默认优先级5;
数字越大,表示优先级越高;
优先级常量:
- MAX_PRIORITY:线程的最高优先级10;
- MIN_PRIORITY:线程的最低优先级1;
- NORM_PRIORITY:线程的默认优先级5(与主线程相同)。
优先级相关的方法:
方法 | 说明 |
---|---|
public int getPriority() |
获取线程优先级的方法 |
public void setPriority(int newPriority) |
设置线程优先级的方法 |
多线程运行问题
- 各个线程是通过竞争CPU时间而获得运行机会的;
- 各线程什么时候得到CPU时间,占用多久,是不可预测的;
- 一个正在运行着的线程在什么地方被暂停是不确定的。
线程同步问题
以取款为例,说明为什么要引入线程同步这个概念
- 为了保证在存款或取款的时候,不允许其他线程对账户余额进行操作;
- 需要将
Bank
对象进行锁定; - 使用关键字
synchronized
实现,可以确保共享对象在同一个时刻只能被一个线程访问,进一步保证执行完整性。
synchronized
关键字用在- 成员方法
- 静态方法
- 语句块
public synchronized void saveAccount(){} //成员方法
public static synchronized void saveAccount(){} //静态方法
synchronized (obj){...} //语句块,obj指的是需要被锁定的对象,{...}是指作用语句块,即作用范围
进程间通信
- wait()方法:中断方法的执行,使线程等待;
- notify()方法:唤醒处于等待的某个线程,使其结束等待;
- notifyAll()方法:唤醒所有处于等待的线程,使它们结束等待;
- 以生产者消费者的例子可以很好地说明通信需求的原因。