Java 我应该在这个方法中使用lock.lock():吗?
我编写了这个方法,其目的是通知线程正在离开 特定代码块 一条线代表一辆离开桥的汽车,以便其他汽车可以穿过桥 该桥可供一定数量的车辆通行(通行能力有限),且只能单向通行Java 我应该在这个方法中使用lock.lock():吗?,java,Java,我编写了这个方法,其目的是通知线程正在离开 特定代码块 一条线代表一辆离开桥的汽车,以便其他汽车可以穿过桥 该桥可供一定数量的车辆通行(通行能力有限),且只能单向通行 public void getout(int diection){ // release the lock semaphore.release(); try{ lock.lock(); //access to shared data
public void getout(int diection){
// release the lock
semaphore.release();
try{
lock.lock(); //access to shared data
if(direction == Car.NORTH)
nNordTraversing--; //decreasing traversing threads
else
nSudTraversing--;
bridgeCond.signal();
}finally{
lock.unlock();
}
}
我的问题是:我应该使用lock.lock()吗;或者只是胡说八道
提前感谢因为我们没有完整的代码(信号量是什么?),这个答案部分基于猜测
如果您的问题与递增和递减操作有关,那么您应该知道这些操作实际上不是原子操作
因此,是的,如果有其他线程访问这些变量,则需要保护它们,以确保没有其他线程可以读取它们,或者更糟糕的是,尝试执行相同的操作,因为两个并行增量可能只会导致一个有效变量
但是由于锁定是有代价的,您也可以将变量封装在代码段中。模拟线程不会调用requirement
getout
,只有队列前面的线程才会调用,因此调用getout
的方法应该同步,因为不是所有线程(car)可以在队列的前面
我还认为您正在使用信号量
作为调用方法中的保护锁
如果在您的实现中,
getout
被多个方法调用,那么是的,您需要同步,并且您的代码是正确的。好吧,我假设nNordTraversing和nSudTraversing是共享数据。因为++和-,不是原子操作,所以在更改之前锁定它们是很有意义的。否则,可能会发生以下情况:
- 读取变量nNordTraversing(例如7)
- 另一个线程被调度并完成其getout方法,它更改了变量(例如7-->6)
- 计划返回时,更改变量,但在另一个线程更改之前读取的旧数据(例如7-->8)上
- 其他线程的更改被重写,计数不再一致(例如,现在是8,但应该是7)
这就是所谓的丢失更新问题。这里对锁的要求取决于其他线程正在执行的操作。他们是否试图读取/修改您同时递减的变量?nOrdTraversing和nSudTraversing是共享数据,因此我需要保护它们以避免不一致。我试图在不使用同步构造的情况下设计getout方法,但我不允许使用同步构造…假设我的代码正确吗?是的,那么你的代码是正确的,你也正确地释放了finally块中的锁。你的建议听起来很有趣..鉴于我的限制(不使用同步构造)为了使用AtomicLong,我应该如何修改代码?谢谢