高并发的基础概念

时间:2021-07-08 18:01:22

一、高并发的常用概念

1.1 同步(Synchronous)和异步(Asynchronous)

高并发的基础概念

很明显,同步调用会等待方法的返回,异步调用会瞬间返回,但是异步调用瞬间返回并不代表你的任务就完成了,他会在后台起个线程继续进行任务。


1.2 并发(Concurrency)和并行(Parallelism)

高并发的基础概念
并行则是两个任务同时进行,而并发呢,则是一会做一个任务一会又切换做另一个任务


1.3 临界区

临界区用来表示一种公共资源或者说是共享数据,可以被多个线程使用,但是每一次,只能有一个线程使用它,一旦临界区资源被占用,其他线程要想使用这个资源,就必须等待


1.4 阻塞(Blocking)和非阻塞(Non-Blocking)

阻塞和非阻塞通常形容多线程间的相互影响


1.5 死锁(Deadlock)、饥饿(Starvation)、活锁(LiveLock)

死锁:是指两个或两个以上的进程在执行过程中,由于竞争资源或者由于彼此通信而造成的一种阻塞的现象,若无外力作用,它们都将无法推进下去。此时称系统处于死锁状态或系统产生了死锁,这些永远在互相等待的进程称为死锁进程


1.5.1 java 多线程死锁

如果出现死锁,可以使用JDK自带的命令行工具

jsp 
jstack 

饥饿:指某一个或者多个线程因为种种原因无法获得所需要的资源,导致一直无法执行


活锁:指事物1可以使用资源,但它让其他事物先使用资源;事物2可以使用资源,但它也让其他事物先使用资源,于是两者一直谦让,都无法使用资源


1.6 并发级别

并发级别:阻塞和非阻塞(非阻塞分为无障碍、无锁、无等待)


1.6.1 阻塞

当一个线程进入临界区后,其他线程必须等待


1.6.2 无饥饿

因为线程有优先级别,导致低优先级始终都不能执行到。如果使用队列,FIFO,则能保证被执行


1.6.3 无障碍

无障碍是一种最弱的非阻塞调度


1.6.4 无锁

与无障碍相比,无障碍并不保证有竞争时一定能完成操作,因为如果它发现每次操作都会产生冲突,那它则会不停地尝试。如果临界区内的线程互相干扰,则会导致所有的线程会卡死在临界区,那么系统性能则会有很大的影响。而无锁增加了一个新的条件,保证每次竞争有一个线程可以胜出,则解决了无障碍的问题。至少保证了所有线程都顺利执行下去。


1.6.5 无等待(Wait-Free)

一种典型的无等待结构就是 RCU(Read-Copy-Updat). 所有的读线程都是无等待的。写数据,先在副本上修改。然后再写回主数据。


1.7 原子性(Atomicity)

原子性是指一个操作不可再分(不能中断)


1.8可见性(Visibility)

可见性是指当一个线程修改了某一个共享变量的值,其他线程是否能够立即知道这个修改值。


Happen-Before规则

JSR-133使用happen-before的概念来指定两个操作之间的执行顺序。由于这两个操作可以在一个线程之内,也可以是在不同线程之间。因此,JMM可以通过happen-before关系向程序员提供跨线程的内存可见性保证(如果A线程的写操作a与B线程的读操作b之间存在happen-before关系,尽管a操作和b操作在不同的线程中执行,但JMM向程序员保证a操作将对b操作可见)


• volatile规则:volatile变量的写,先发生于读,这保证了volatile变量的可见性
• 锁规则:解锁(unlock)必然发生在随后的加锁(lock)前
• 传递性:A先于B,B先于C,那么A必然先于C
• 线程的start()方法先于它的每一个动作
• 线程的所有操作先于线程的终结(Thread.join())
• 线程的中断(interrupt())先于被中断线程的代码
• 对象的构造函数执行结束先于finalize()方法


参考

  1. 《实战java高并发程序设计》