线程安全问题是多线程所涉及到的最重要的,也是最复杂的问题
public class ThreadDemo14 {
static class Counter{
public int count = 0;
public void increase(){
count++;
}
}
public static void main(String[] args) throws InterruptedException {
Counter counter = new Counter();
Thread t1 = new Thread(){
@Override
public void run(){
for (int i = 0; i < 50000; i++) {
counter.increase();
}
}
};
t1.start();
Thread t2 = new Thread(){
@Override
public void run(){
for (int i = 0; i < 50000; i++) {
counter.increase();
}
}
};
t2.start();
t1.join();
t2.join();
// 两个线程各自自增5000次,最终预期结果,应该是10w
System.out.println(counter.count);
}
}
注意:
运行结果:
多运行几次你会发现,结果并不是10w,而且每次运行的结果都不一样
上述现象:则是线程不安全
线程不安全: 多线程并发执行某个代码时,产生了逻辑上的错误,就是"线程不安全"
和线程不安全对应,线程安全就是 多线程并发执行某个代码,没有逻辑上的错误,就是"线程安全"
思考: 为啥会出现上述情况???
原因:
画图表示:
上述代码的执行结果在范围 [5w,10w] 之间
极端情况下,
t1 和 t2 每次++ 都是纯并行的,结果就是 5w
t1 和 t2 每次++ 都是纯串行的,结果就是 10w
实际情况,一般不会这么极端,调度过程中有时候是并行,有时候是串行(多少次并行,多少次串行,这个不清楚),因此导致最终的结果是在 [5w,10w] 之间
1.抢占式执行 — (这个没法解决,操作系统内核解决)
2.自增操作非原子 — (这个有办法,可以给自增操作加上锁) 适用范围最广
3.多个线程同时修改同一个变量 — (这个不一定有办法解决,得看具体的需求)
转下篇:锁
版权说明 : 本文为转载文章, 版权归原作者所有 版权申明
原文链接 : https://blog.csdn.net/m0_47988201/article/details/121339038
内容来源于网络,如有侵权,请联系作者删除!