Java线程问题
我正在上Java课程。我们现在进入线程。这是我第一次体验多线程,所以如果问题非常愚蠢,请原谅:) 我有以下计划:Java线程问题,java,Java,我正在上Java课程。我们现在进入线程。这是我第一次体验多线程,所以如果问题非常愚蠢,请原谅:) 我有以下计划: public class Foo extends Thread { private int x = 2; public static void main(String[]args) { new Foo().fun(); } Foo () { x = 5; start(); } pub
public class Foo extends Thread {
private int x = 2;
public static void main(String[]args) {
new Foo().fun();
}
Foo () {
x = 5;
start();
}
public void fun() {
x = x - 1;
System.out.println(x);
}
public void run() {
x = x * 2;
}
}
当我运行程序时,我得到4作为输出。上述程序的输出是否始终为4?是,它将始终为4。我看不出它没有理由不是
4
您只运行fun()
,从不运行run()
阅读是的,它将始终是4。我看不出它没有理由不是
4
您只运行fun()
,从不运行run()
阅读它并不总是4 如果Foo run()方法在主线程运行fun()之前执行,则它将是9 如果Foo run()方法在main运行fun()时执行,则它将为8
如果main()在Foo启动之前完成,它将是4,但并不总是4 如果Foo run()方法在主线程运行fun()之前执行,则它将是9 如果Foo run()方法在main运行fun()时执行,则它将为8
如果main()在Foo启动之前完成,则它将是4,但并不总是如此。因为在调用
start()
方法时,从主线程调用fun
和从thread.start调用run
之间存在竞争条件,这将改变x
的值
但是,实际上,如果没有适当的同步,就无法保证输出是什么,与调用fun
和run
的顺序无关。因为同步确保了线程更改的可见性,所以即使run
将在调用fun
之前完成,输出也可以是4。不,不总是这样。因为在调用start()
方法时,从主线程调用fun
和从thread.start调用run
之间存在竞争条件,这将改变x
的值
但是,实际上,如果没有适当的同步,就无法保证输出是什么,与调用fun
和run
的顺序无关。因为同步可以确保线程更改的可见性,所以即使在调用fun
之前run
将完成,输出也可以是4。正如您所说,您正在学习多线程,您必须知道,您永远无法预测不同线程的执行顺序
这是一个非常简单的程序,其中主线程几乎总是首先完成,但要记住的重要一点是,在复杂的多线程场景中,您永远无法确定。事实上,在一个线程不依赖于另一个线程的执行的情况下,您选择了多线程方法
顺便说一句,请尝试以这种方式更改构造函数:
Foo () {
x = 5;
start();
Thread.sleep(2 * 1000);
}
您可能会得到不同的结果。正如您所说,您正在学习多线程,您必须知道,您永远无法预测不同线程的执行顺序
这是一个非常简单的程序,其中主线程几乎总是首先完成,但要记住的重要一点是,在复杂的多线程场景中,您永远无法确定。事实上,在一个线程不依赖于另一个线程的执行的情况下,您选择了多线程方法
顺便说一句,请尝试以这种方式更改构造函数:
Foo () {
x = 5;
start();
Thread.sleep(2 * 1000);
}
您可能会得到不同的结果。是正确的,但需要注意。Java有一些变量值的缓存。如果变量未设置为volatile或未使用原子值,则可能会获取缓存的值,而不是最新的值。是正确的,但需要注意。Java有一些变量值的缓存。如果变量未设置为volatile或未使用原子值,则可能会获取缓存的值,而不是最新的值。但构造函数正在调用start,该函数调用run。实例化线程
,没有什么特殊的操作,只需像常规类一样调用new
。您引用的Javadoc也给出了一个例子。但是构造函数调用start调用run。要实例化线程
,没有什么特别的事情要做,只需像普通类一样调用new
。您引用的Javadoc也展示了一个例子。谢谢你能解释一下“8作为输出”部分吗?我明白了。如果x=x*2发生在x=5之后但在打印之前。我说得对吗?值得注意的是,由于线程是在构造函数中启动的,因此线程可以将x
视为5、2或0(或者在fun()启动后启动4)Peter,你能详细说明一下吗?如果run
在fun
的第一行之前读取x
,并在fun
的两行之间将其双精度写回x
,那么输出将是5*2=10.5。谢谢你能解释一下“8作为输出”部分吗?我明白了。如果x=x*2发生在x=5之后但在打印之前。我说得对吗?值得注意的是,由于线程是在构造函数中启动的,因此线程可以将x
视为5、2或0(或者在fun()启动后启动4)Peter,您能详细说明一下吗?如果run
在fun
的第一行之前读取x
,并将其双精度写回x
在fun
的两行之间,那么输出将是5*2=10。谢谢您的先生。这个网站太快了:)谢谢你的先生。这个网站太快了:)我的文本有这个在练习中,但没有作业。我的文本有这个在练习中,但没有作业。