Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/362.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_Exception_Thread Safety - Fatal编程技术网

Java 确保变量只设置一次

Java 确保变量只设置一次,java,exception,thread-safety,Java,Exception,Thread Safety,我需要确保一件物品只卖一次。 这也必须在多个线程上确保 检查buyer变量是否不为空就足够了吗?因此,在我看来,第二个调用方将收到一个AlreadyBoughtException public synchronized void buy(Buyer buyer) throws AlreadyBoughtException { if (this.buyer != null) { throw new AlreadyBoughtException(); } S

我需要确保一件物品只卖一次。 这也必须在多个线程上确保

检查
buyer
变量是否不为空就足够了吗?因此,在我看来,第二个调用方将收到一个
AlreadyBoughtException

public synchronized void buy(Buyer buyer) throws AlreadyBoughtException {
    if (this.buyer != null) {
        throw new AlreadyBoughtException();
    }

    System.out.println(buyer + " bought article " + identifier);

    this.buyer = buyer;
    this.sold = true;
}

这是线程安全的吗?我是否可以假设,当同时(完全相同的时间)调用
buy
方法时,没有可能无法购买文章?

只要
buyer
不能通过非同步方法设置,您的代码就是线程安全的


JVM将确保同步方法不会发生“完全相同的时间”-一个调用方将被视为第一个调用方,而另一个调用方必须等到第一个调用完成后才能继续。

只要不能通过非同步方法设置
,您的代码就是线程安全的


JVM将确保同步方法不会发生“完全相同的时间”——一个调用方将被视为第一个调用方,另一个必须等到第一次调用完成后才能继续。

您的方法是同步的这一事实使其安全-只要这是您更新买家的唯一方式。

您的方法是同步的这一事实使其安全-只要这是您更新买家的唯一方式买方。

是的,这很好(当然,除非您是通过其他方法访问买方字段)

两个试图同时执行此方法的线程将无法执行此操作:只有一个线程能够获得锁并初始化买方。然后,另一个线程将执行它,并看到初始化的买方,因为该方法是同步的。

是的,这很好(当然,除非您是从另一个方法访问买方字段)

两个试图同时执行此方法的线程将无法执行此操作:只有一个线程能够获得锁并初始化买方。然后,另一个线程将执行它,并查看初始化的买方,因为该方法是同步的。

您可以

this.buyer
易变变量

您可以

this.buyer

volatile variable

您的代码是正确的,但是使用AtomicRefreference可以实现更好的性能和更少的线程争用。我将检查
this.sell==true
。我不明白为什么要让买家复杂化。举个例子,我还尝试了其他方法。您的代码是正确的,但使用AtomicReference可以实现更好的性能和更少的线程争用。我会检查
this.sell==true
。我不明白为什么要把买家复杂化。举个例子,我也试过别的东西。两者都做有意义吗?同步setter和使用volatile?不,如果您也是同步的,则不需要volatile,因为volatile所做的一切都是同步的,等等。Volatile在这里也不够,因为你会有几个比赛条件,使用Volatile但不同步实际上是危险的。@Tim B我同意你的观点,如果使用Volatile,就不需要同步(这就是我所说的答案)。但不会有任何竞争条件,因为在函数的第二行中访问了volatile变量。内存障碍将使线程可以获得此文件的最大更新值。你完全错了。需要同步。否则,两个线程都可以检查
buyer
是否为空,通过检查,然后都将新值写入
buyer
…以允许项目销售两次。同意。因为它设定了买家的价值,这可能会让其他线程站出来并在竞争中领先。两者都做有意义吗?同步setter和使用volatile?不,如果您也是同步的,则不需要volatile,因为volatile所做的一切都是同步的,等等。Volatile在这里也不够,因为你会有几个比赛条件,使用Volatile但不同步实际上是危险的。@Tim B我同意你的观点,如果使用Volatile,就不需要同步(这就是我所说的答案)。但不会有任何竞争条件,因为在函数的第二行中访问了volatile变量。内存障碍将使线程可以获得此文件的最大更新值。你完全错了。需要同步。否则,两个线程都可以检查
buyer
是否为空,通过检查,然后都将新值写入
buyer
…以允许项目销售两次。同意。因为它设定了买家稍后的价值,这可能会让其他线程站出来,并在比赛中领先。