JUC 核心前置:Java 内存模型与多线程核心八股
1. 介绍Java的内存模型(JMM)
JMM是多线程并发问题的一套规则,也就是在规定是多线程的环境下,线程怎们访问变量才会步出错这里要处理可见性、原子性、有序性

可见性:若线程A从CPU共享变量里拿到变量到自己的工作内存里修改变量后还没来得及把变量放回共享变量里,那么线程B在此时就看不到变量的更新,此时就要用volatitle关键字来约束、让整个流程结束后才能让其他线程访问这个变量
原子性:若线程AB同时执行i++这个操作,首先i++是先读i再加1再放回原本变量,当线程A已经把i=10更新为i =11了,可能线程B才把i更新为11这样结果就会出错,所以就需要synchronized 或lock锁来让只有一个线程结束后另一个线程才能操作,且中间不会被打断,提供了互斥访问
有序性:就是可能代码执行顺序有问题,在单线程时,我们常常初始化一个对象A,再把这个对象的引用给变量a。可在多线程时,为了编译速度,编译器或者cpu可能会改变你的代码执行顺序,可能会优先给变量a赋值A的引用,但A还没初始化好时,线程B就访问a,由于A还没有初始化完全就会报错,synchronized或者lock锁就会构建一个锁屏障来防止这个重排序的发生,保证正确
所以JMM的核心思路就是:定义主内存(共享变量)和工作内存,只有把变量从主内存拿到工作内存才能修改变量,修改后再放回主内存
然后再通过synchronized和volatile关键字、lock锁这样的方式,来控制加载时机、写回时机、不合理的重排序保证多线成共享变量时的正确交互
2.Java多线程是什么?需要注意什么
Java多线程是值在同一个Java程序里运行多个线程、这些线程共享变量、方法区等资源,比如一个线程输入、一个线程后台下载文件、就可以提提高程序运行的效率

1.线程之间的通信:要避免一个线程还没有准备好,另一个线程就来访问这个线程的变量,可以用wait()或notify()方法来控制访问的时机
2.线程数据安全问题:比如两个线程同时加1,那么变量应该加2,可能结果只加了1,就需要用synchronizes、volatitle关键字来,控制线程执行的时机,保证数据安全
3.线程的创建和销毁:线程频繁的创建和销毁很浪费系统资源、可以在线程池里提前准备多个线程以应用,减少资源的消耗
3.Java的线程和操作系统的线程一样吗
Java的线程底层是pthread_create创建的,和操作系统的是一样的、都是一对一的线程模式

再说一下Java多线程的注意点:可见性、原子性、有序性
4.保证数据一致性的方法有哪些?
事务管理、锁机制、版本控制
事务管理:来保证一组数据库操作要么全部成功,要么就全部失败回滚,通过ACID(原子性、隔离性、持久性、一致性)属性,数据库数据可以保证一致性
锁机制:通过锁机制来保证对共享资源的互斥访问,在java中可以利用synchronized和其他锁机制来控制并发访问,从而导致并发操作导致数据不一致
版本控制:通过乐观锁机制实现并发修改时的冲突检测,允许基于最新版本号的修改生效,否则拒绝覆盖并要求重试或解决冲突,从而避免旧版本修改覆盖新版本数据,保证并发场景下的数据一致性