gpt4 book ai didi

java - 使用和不使用 volatile 的实现

转载 作者:行者123 更新时间:2023-11-30 08:07:51 24 4
gpt4 key购买 nike

我正在运行以下代码:

import java.util.*;

public class Common_variable extends Thread{
private boolean running = true;

public void run()
{
while(running)
{
try {
System.out.println("Hello");
Thread.sleep(100);
} catch (InterruptedException ex) {
System.out.println(ex);
}
}
}

public void shutdown()
{
running = false;
}
}

public class Thread_demo{

public static void main(String args[])
{
Common_variable x = new Common_variable();
x.start();

Scanner in = new Scanner(System.in);
in.nextLine();

x.shutdown();
}
}

现在,我在这里有些疑问。当我们执行“Common_variable x = new Common_variable();”时,创建了新的线程,这意味着分离堆栈。此时,堆中也创建了一个对象x。我的疑问是:

是否只有一个“运行中”变量的副本,或者新线程的堆栈中也有一个?如果是,那么两个线程如何能够相互通信并更新“running”的值。如果不是,并且两者都从同一内存位置访问,那么如果我们将变量 running 声明为 volatile 会有什么不同。

请澄清我的理解哪里不对。

最佳答案

这与线程堆栈无关。 running 是对象的字段,因此存储在堆中。

但是由于多核机器上的性能优化,每个核心都可以在其缓存中拥有该值的副本:访问缓存比访问主内存更快。

如果没有 volatile,当主线程将标志设置为 false 时,无法保证其他线程会看到该更改:缓存的值不会写入主内存,线程也不会重新读取- 从主内存中读取它。

volatile 保证每次对变量的更改都写入主内存,并且每次更改后的变量读取都从主内存重新读取。

也就是说,您应该更喜欢 AtomicBoolean 而不是 volatile 变量。在那种情况下,你甚至应该根本不喜欢任何变量:每个线程都有一个中断标志,你可以通过 interrupting the thread 来改变它。 .这种内在机制的优点是一旦线程被中断,线程就不会继续 hibernate :它会通过抛出 InterruptedException 立即退出 sleep() 方法,这将允许您立即停止线程。

关于java - 使用和不使用 volatile 的实现,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/33454057/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com