Java 中枚举值的线程安全比较

Thread-safe comparison of an enum value in Java

这是我当前的代码。我想了解如果 getState() 已经同步,是否需要将 isObjectActive() 包装在同步块中?

private final Object lock = new Object();
@GuardedBy("lock")
private EventTypes state;

@GuardedBy("lock")
public void setState(final EventTypes state) {
    synchronized (lock) {
        this.state = state;
    }
}

@GuardedBy("lock")
@VisibleForTesting
public EventTypes getState() {
    synchronized (lock) {
        return state;
    }
}

@GuardedBy("lock")
public boolean isObjectActive() {
    synchronized (lock) {
        return getState() == EventTypes.ACTIVE;
    }
}

[Do] I need to wrap isObjectActive() in a the synchronized block...?

没有

同步不是针对方法,而是针对数据。在上面显示的示例中,您可以从 isObjectActive() 中删除 synchronized 块,因为该函数不直接访问 state 变量,并且它调用的唯一其他函数 在访问 state 时是否使用同步。

@Thomas 在他对你的问题留下的评论中提出了一个很好的观点:如果其他线程的操作可以改变状态,你可能应该考虑 isObjectActive() 调用的结果意味着什么在调用者有机会对结果采取行动之前的对象:

MyType mt = ...;

if (mt.isObjectActive()) {
    // This is broken because there's no guarantee that mt still will be "active"
    // by the time doSomething...() gets called.
    //
    doSomethingThatOnlyMakesSenseWhen_mt_IsActive(...);
}