搜索引擎的网站网站建设免
搜索引擎的网站,网站建设免,淄博桓台学校网站建设方案,浙江省网站建设公司概念#xff1a;Java线程安全问题#xff0c;本质上是在多线程环境下#xff0c;由于线程调度的不确定性#xff0c;导致程序的执行结果与预期不符。
线程安全问题的产生通常可以归结为以下三个核心原因#xff1a; 原子性问题 (Atomicity) 一个看似简单的操作#xff0…概念Java线程安全问题本质上是在多线程环境下由于线程调度的不确定性导致程序的执行结果与预期不符。线程安全问题的产生通常可以归结为以下三个核心原因原子性问题 (Atomicity)一个看似简单的操作如count在底层实际上包含了读取、修改、写入三个步骤。如果这些步骤没有作为一个不可分割的整体即原子操作来执行就可能被其他线程打断。例如两个线程同时对一个变量进行自增可能因为操作交错导致最终结果只增加了一次。可见性问题 (Visibility)根据Java内存模型JMM每个线程都有自己的工作内存类似于CPU缓存保存了主内存中共享变量的副本。一个线程对变量的修改可能只更新到了自己的工作内存中而没有及时刷新回主内存导致其他线程无法看到最新的值。有序性问题 (Ordering)为了优化性能编译器或处理器可能会对指令的执行顺序进行重排Instruction Reordering。虽然在单线程下这不会有问题但在多线程环境下这种重排可能导致一个线程看到的操作顺序与代码编写的顺序不一致从而引发错误。这里主要介绍12两者以及对应解决方法1.使用synchronized关键字它可以保证代码块或方法的原子性和可见性。同一时刻只有一个线程能进入被synchronized修饰的代码区域其他线程必须等待。(原子操作简单来说原子操作就是指一个操作在执行过程中不会被线程调度机制打断)2.使用volatile关键字它主要用于保证变量的可见性和有序性禁止指令重排但不保证操作的原子性。下面以两个程序展示用法【1】synchronized添加synchronized关键字后同步代码块执行后输出结果为20000若不加synchronized锁结果偏小package Thread_Learning; /** * author jinhuang * date 2026/2/5 9:59 * description */ public class ThreadDemo1 extends Thread{ static int count0; static Object lockobjnew Object(); Override public void run() { for (int i 0; i 10000; i) { //同步代码块 synchronized(lockobj){ count; } } } public static void main(String[] args) { ThreadDemo1 t1new ThreadDemo1(); ThreadDemo1 t2new ThreadDemo1(); t1.start(); t2.start(); try { t1.join(); t2.join(); } catch (InterruptedException e) { throw new RuntimeException(e); } System.out.println(count); } }【2】volatile// 具备可见性当一个线程修改之后另一个线程可以立马更新// 被这个词修饰的变量在每次使用时都会更新 查看堆内存的数据是否更改若没有volatile关键字无法正常执行完A程序package Thread_Learning; /** * author jinhuang * date 2026/2/5 10:06 * description */ class ThreadDemo3 extends Thread{ ThreadDemo2 td2; Override public void run() { System.out.println(线程B启动); td2.isflagtrue; System.out.println(线程B执行完成); } } public class ThreadDemo2 extends Thread{ volatile boolean isflag; Override public void run() { System.out.println(线程A启动); while (true){ if(isflag){ break; } } System.out.println(线程A执行完成); } public static void main(String[] args) { ThreadDemo2 t2new ThreadDemo2(); ThreadDemo3 t3new ThreadDemo3(); t3.td2t2; t2.start(); t3.start(); } }