基础概念:
- 进程与线程
进程是操作系统分配资源的基本单位,进程是cpu调度的基本单位。
同一进程下的线程共享进程中的一些资源,线程也有自己独立的存储空间。
- 多线程
多线程是指的,再单个的进程中同时存在多个线程
存在多个线程,可以类比再一家店里同时存在多个伙计,分别负责不同的职责。让服务可以更加快捷和丝滑
但是引入多线程,多个线程同时管理同一份资源,会带来一致性的问题。这和单体架构过度道分布式架构出现的问题很类似。
- 串行、并行、并发
串行:同一个cpu,按照顺序执行代码。排队执行
并行:多核cpu,同时执行多个程序片段
并发:单核cpu再多个程序之间快速切换(和高并发不是一个意思)
- 同步和异步,阻塞和非阻塞
同步和异步,执行程序后被调用者是否会主动反馈信息
阻塞和非阻塞,执行某个功能后,调用者是否需要一直等待结果反馈
创建线程的方式
- 继承Thread类,重写run方法
- 实现Runnabble接口,重新run方法
【可以用匿名内部类,或lambda方式】
,因为new Thread的构造可以接收一个Runnable实例, - 实现Callable接口,重写call方法,配合FutureTask
【获取返回值】
,因为new Thread的构造可以接收一个FutureTask实例,而FutureTask(Future Task)则需要一个Callable实例。
所有的创建方式,最终都是要实现一个Runnable接口。
线程的状态
- 操作系统层面的5种状态:new-ready-running-terminated,在running过程中可以通过方法调用,让线程处于waiting状态
- java中的线程的6种状态:
new
-runnable(reday+running)
-Terminated
,在runnable状态下,可以调用wait()让线程进入waiting
状态,调用sleep()或join()让程序进入timed_waiting
状态,synchronized没有拿到锁的时候进入blocked
状态
当一个线程被new出来之后,没有调用start()方法,则该线程是
new
状态
当一个线程在运行过程中,则该线程是runnable
状态
当一个线程没有拿到锁的时候,线程的状态是blocked
状态
当线程主动调用wait方法时,线程进入waiting
状态
当线程调用sleep(),或join()方法时,sleep必须带参数,join可以不带参数(直接timed_waitting到调用线程结束),线程进入timed_waiting
状态
当线程结束后,查看状态的状态,此时为terminated
状态
线程api
– | 方法 |
---|---|
static | Thread currentThread() 获取当前线程 |
String | getName() 获取当前线程的名称,用来标识和排错. |
static void | yield() 让当前线程从运行状态转变为就绪状态. |
static void | sleep(long millis)让线程休眠 |
static void | sleep(long millis)让线程休眠 |
void | join() 让线程先执行一段时间或到结束,取决于是否带参数 |
void | setDaemon(boolean on) 标记线程为守护线程,JVM推出前会保证所有非守护线程结束 |
void | notify(),notifyAll() 需要使用锁对象去唤醒 |
线程中存在等待池和锁池,等待池中的线程处于等待唤醒,或自己醒的状态,锁池的线程则是在等待锁释放,释放后抢锁执行程序。
- 线程结束
Interrput
方法
isInterrupted() 查看interrut标记,默认interrupt为false
interrupt() 打断线程状态
interrupted() 返回interrupt状态,并归位为false
打断waiting
和timed_waiting
状态从而对线程的状态进行控制,执行不同的代码块。