多线程
基本概念
程序概念
一些列代码指令的集合统称 ,应用,软件等等 都属于程序。
程序运行必须依托于进程而存在,进程负责分配资源,依赖线程来运行。
单核心配置
运行 - msconfig - 引导 - 高级选项 - 处理器个数为 1
进程定义
进行中应用程序中属于资源分配的基本单位 。
应用程序执行的实例,拥有独立的内存空间和CPU资源。
线程定义
线程是包含在进程之中的, 一个进程至少有一个线程,否则将无法运行,线程是CPU调度运算的基本单位。
线程是CPU调度和分派的基本单位,应用程序运算是最小单位。
多线程
-
一个进程中同时运行了多个线程,用来完成不同的工作,则称之为"多线程"。
-
单核CPU下,多个线程交替占用CPU资源,而非真正的并行执行。
线程开辟和线程执行
线程不是越多越好,要 结合实际的硬件环境来决定。
在单核心CPU下,多个线程是轮流交替执行的,以windows操作系统为例,多个线程随机轮流交替执行,每个线程最多执行20ms,然后继续切换下一个线程,而非并行执行,因为切换的频率非常快,所以我们感知不到这个过程,宏观上是同时执行的,实际上,是轮流交替执行的。
并发并行
并发:同时发生,轮流交替执行;宏观上同时执行,微观轮流交替执行。
并行:严格意义上的同时执行,相当于一个请求生成一个线程。
主线程
main方法为程序的入口,底层由main线程负责执行,由JVM自动调用执行。
Thread类
-
java.lang.Thread 线程类
-
优先级越高执行的概率越高。
属性
最高的优先级是10
最低的优先级是1
默认的优先级是5
构造方法
// 无参
Thread()
// 传入一个Runnable接口的实现类
Thread(Runnable target)
// 传入一个Runnable接口的实现类,再传入线程的名称
Thread(Runnable target, String name)
// 传入一个String类型的作为线程的名字
Thread(String name)
方法
getName()
作用:获取线程名称
参数:无
返回值:String类,
示例:
// 获取当前Thread类对象(线程对象)
Thread thread = Thread.currentThread();
// 打印线程名称
System.out.println("当前线程对象 " + thread); // Thread[main,5,main]
// 获取当前线程对象名称
String name = thread.getName();
System.out.println("当前线程名称 " + name); // main
currentThread()
作用:(静态方法)获取当前线程对象
参数:无
返回值:Thread类型,线程对象
示例:
// 获取当前Thread类对象(线程对象)
Thread thread = Thread.currentThread();
// 打印线程名称
System.out.println("当前线程对象 " + thread); // Thread[main,5,main]
setName(String name)
作用:设置线程名称
参数:String类型
返回值:无
示例:
// 获取当前Thread类对象(线程对象)
Thread thread = Thread.currentThread();
// 打印线程名称
System.out.println("当前线程对象 " + thread); // Thread[main,5,main]
// 获取当前线程对象名称
String name = thread.getName();
System.out.println("当前线程名称 " + name); // main
// 设置当前线程名称
thread.setName("主线程");
start()
作用:开启线程,向CPU提示自己准备就绪,可以被执行。
参数:无
返回值:无
示例:
// 创建 自定义线程对象
MyThread myThread1 = new MyThread();
MyThread myThread2 = new MyThread();
// 设置线程名称
myThread1.setName("线程A");
myThread2.setName("线程B");
// 启动线程
myThread1.start();
myThread2.start();
sleep()
作用:休眠进程,进入阻塞状态。
参数:long 类型的 毫秒数
返回值:无
示例:
public class MyThread extends Thread{
@Override
public void run() { // 运行
// 自定义线程执行的代码
// 遍历当前线程的名称
for (int i = 0;i<=20;i++){
try {
// 方法重写,因为父类run方法没有声明任何异常 所以子类也不能声明任何异常
// 不能通过 throws xxx 的形式在方法上声明异常,只能捕获处理异常。
// 线程睡眠,进入阻塞状态
Thread.sleep(3000); // 休眠3秒钟 到达时间 自动继续执行
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println(Thread.currentThread().getName() + "执行, 第" + i + "次");
}
// 线程执行完毕
System.out.println("线程执行完毕");
// 线程挂了
}
}
setPriority()
作用:设置线程的优先级,默认为5,范围1-10。从1~10,1最低,10最高,默认为5,优先级高的线程只是获得CPU资源的概率较大,并不一定能够保证优先执行;