Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/332.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/multithreading/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 为什么这些同步方法总是给我不同的输出?_Java_Multithreading_Concurrency_Thread Safety_Java Threads - Fatal编程技术网

Java 为什么这些同步方法总是给我不同的输出?

Java 为什么这些同步方法总是给我不同的输出?,java,multithreading,concurrency,thread-safety,java-threads,Java,Multithreading,Concurrency,Thread Safety,Java Threads,我需要有权访问相同数据的线程同时执行,而不会相互干扰,因此我一直在尝试使用同步方法,而不是使用Thread.join()。问题是,我看不到任何变化,它一直给我相同的结果,我在使用它们之前。我甚至不知道我到底做错了什么 方法应该阻止其他同步方法在完成之前执行,对吗?希望你能告诉我发生了什么事 公共类线程同步{ 公共静态void main(字符串[]args)引发InterruptedException{ //如果执行得当 //输出不能不是0 while(true){ ChangeValue计数器=

我需要有权访问相同数据的线程同时执行,而不会相互干扰,因此我一直在尝试使用同步方法,而不是使用
Thread.join()。问题是,我看不到任何变化,它一直给我相同的结果,我在使用它们之前。我甚至不知道我到底做错了什么
方法应该阻止其他同步方法在完成之前执行,对吗?希望你能告诉我发生了什么事

公共类线程同步{
公共静态void main(字符串[]args)引发InterruptedException{
//如果执行得当
//输出不能不是0
while(true){
ChangeValue计数器=新的ChangeValue();
螺纹t=新螺纹(计数器,“向上”);
螺纹t2=新螺纹(反向“向下”);
线程t3=新线程(计数器,“打印”);
t、 start();
t2.start();
t3.start();
}
}
}
类线程扩展线程{
线程(ChangeValue对象、字符串动作){
计数器=obj;
行动=行动;
}
@凌驾
公开募捐{
开关(动作){
case(“up”):counter.up();break;
case(“down”):counter.down();break;
case(“print”):counter.print();break;
}
}
可变值计数器;
弦作用;
}
类更改值{
public synchronized void up(){value++;}
public synchronized void down(){value--;}
public synchronized void print(){System.out.println(value);}
公共int值=0;
}

同步只是确保方法不会同时执行。但是,它不保证任何执行命令

您需要确保在其他线程终止之前不执行
print()
。这可以通过连接螺纹来实现。为此,执行

t.join();
t2.join();
在启动打印线程之前或在执行其逻辑之前

请注意,同步仍然是合理的,因为它确保以原子方式执行递增和递减操作。也就是说,在执行
count++
时,读取、递增和写入
count
是同时执行的 (另见:)。因此,它可以防止以下执行顺序:

  • [线程“向上”]:加载
    count
    0
  • [线程“向下”]:加载
    count
    0
  • [线程“向上”]:递增
    计数
    1
  • [线程“向下”]:递减
    计数
    -1
  • [线程“向上”]:使用值
    1存储
    count
  • [线程“向下”]:使用值存储
    计数
    -1

(这是数据库术语中的“丢失更新”)

synchronized
防止线程同时访问字段,但当然它不能保证线程的执行顺序。
例如,如果纯粹出于偶然,首先执行“向上”线程,“打印”线程,最后执行“向下”线程,则输出将为1,即使在所有线程完成后计数器值为0。

您在问题中写道:问题是,我看不到任何更改,它会一直给我与使用[threads]之前相同的结果你期望得到什么样的“结果”?所以我不能假装同步方法像连接线程一样工作。现在我明白了,谢谢,现在我可以做一个更好的测试,看看它是如何工作的。:)