并发编程①概述
1、概述
并发编程涉及知识点
- 进程与线程
- 并发与并行
- 同步与异步
- Java 并发工具、并发问题及解决方案
基础知识
- 接触过 Java Web、JDBC 开发、Web 服务器(最好有分布式框架)
- 基于 JDK 8,了解函数式编程、lambda 表达式
- 了解 slf4j 打印日志
相关依赖
1.8
1.8
org.projectlombok
lombok
1.18.10
ch.qos.logback
logback-classic
1.2.3
logback 配置
<?xml version="1.0" encoding="UTF-8"?>
%date{HH:mm:ss} [%t] %logger - %m%n
2、初识并发编程
2.1、程序、进程、线程
2.1.1、相关概念
程序(procedure)
- 程序由指令和数据组成,是静态的。
- 指令加载到 CPU 才能执行,数据加载到内存才能读写。
- 指令执行过程中需要用到磁盘、网络等设备。
进程(progress)
- 进程可视为程序的一个实例,是动态的(可理解为运行中的程序)
- 进程用于加载指令、管理内存和 I/O
- 当一个指令被执行,将程序从磁盘加载到内存,此时开启了一个进程。
- 程序可运行一个或多个实例进程(如 QQ音乐、记事本)
线程(thread)
- 线程相当于指令流。
- 线程将指令以一定的顺序交给 CPU 执行。
2.1.2、进程 vs 线程
在 Java 中,进程是资源分配的最小单位,线程是最小调度单位。
- 进程基本上相互独立,线程存在于进程内
(一个进程由多个线程组成) - 进程拥有共享的资源,如内存空间等,供其内部的线程共享。
- 在 Windows 中,进程作为线程的容器,自身是不活动的。
通信
- 进程间通信(复杂)
- 同一台计算机:IPC(Inter-process communication)
- 不同计算机:通过网络并遵守共同的协议,例如 HTTP
- 线程通信(简单):线程共享进程的内存(例:多个线程可以访问同一个共享变量)
上下文切换(context switch):内核在 CPU 上对进程(线程)进行切换,即任务切换
一般情况下,线程上下文切换成本比进程低。
2.2、并发、并行
理解
- 并发(concurrent):同一时间应对事情(deal with)
- 并行(parallel):同一时间实际做事情(do)
concurrent
简单来说,并发就是线程轮流使用 CPU。
- 在单核 CPU 下,线程是串行执行的。
- 操作系统的任务调度器,将 CPU 时间片分给不同程序使用。
- CPU 在线程间的切换非常快,使人感觉是同时运行的(Windows 时间片最小约 15ms)。
总结:宏观并发,微观串行。
parallel
- 在多核 CPU 下,每个核都可以调度运行线程,线程可以并行执行。
- 通常线程数会远大于核数,因此并行和并发是同时存在的。
总结:宏观并行,微观串行。
2.3、同步、异步
从程序调用方的角度
- 同步(synchronization):需要等待结果返回才能继续运行。
- 异步(asynchronization):不需要等待结果返回,就能继续运行。
多线程可以使方法异步执行
- 开启一个线程用于处理比较耗时的操作,避免阻塞主线程。
- 应用举例:Tomcat 中的 异步 Servlet、UI 编程中的异步。