2

在下面的课程中,我使用的是 singleThreadScheduledExecutor。我的问题是,我是否需要围绕对 dummyInt 和 dummyBoolean 的访问进行同步?

import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.TimeUnit;

public class Playground {

    /**
     * @param args
     */
    public static void main(String[] args) {
        startThread();

    }

    private static void startThread() {
        ScheduledExecutorService timer = Executors
                .newSingleThreadScheduledExecutor();
        Runnable r = new Runnable() {
            int dummyInt = 0;
            boolean dummyBoolean = false;

            @Override
            public void run() {
                dummyInt = dummyInt + 1;

                if (dummyBoolean) {
                    dummyBoolean= false;
                } else {
                    dummyBoolean= true;
                }

            }

        };

        timer.scheduleAtFixedRate(r, 0, 100, TimeUnit.MILLISECONDS);

    }

}
4

6 回答 6

3

不,你没有。只有一个线程访问这些值,因此不需要同步。

于 2010-03-07T17:06:59.463 回答
2

使用该机制启动的每个线程都将拥有自己定义和实例化的“可运行”子类的实例。因此,不可能有争执。

于 2010-03-07T17:07:24.780 回答
1

你需要吗?不,只有一个线程会访问当前实现中的变量,所以它是线程安全的。

会影响性能吗?嗯,是的,但没有你想象的那么多。现代 JIT 编译器很高兴地发现在当前使用中同步是不必要的,并且几乎消除了编译代码的所有开销——但是会留下一点开销来检查单线程访问的假设是否仍然存在有效的。当然,还有 JITting 的开销。

不同步会不会很痛苦?好吧,很可能,如果实现发生了变化并且不再保持单线程访问的假设 - 并且进行更改的开发人员忽略了他们更改的后果。

但实际上,在这种情况下,这可能会发生吗?也许不是 - 所有代码都包含在一个非常小的区域中......

我可能会留下某种评论来记录假设。如果我在项目中的其他任何地方使用JCIP 注释,我什至可以将该类注释为 @NotThreadSafe。可以在 Brian Goetz 的Java Concurrency In Practice一书中找到有关使用这些注释的讨论,注释源代码和 jar 文件可从该书的网站下载。

于 2010-03-10T17:16:58.440 回答
0

你不必成功synchronized

于 2010-03-07T18:00:05.187 回答
-1

不,但它可能不会受到伤害。由于您使用的是newSingleThreadScheduledExecutor,它承诺

任务保证按顺序执行,并且在任何给定时间不会有超过一个任务处于活动状态。

但是如果你改变了执行者,让 Runnable 退出以便其他人可以调用它,或者在外部检查值,那么你会希望你同步它。

于 2010-03-07T17:09:55.053 回答
-2
dummyInt = dummyInt + 1;

该语句实际上是 3 个单独的操作:

  1. 读取 dummyInt 的值
  2. 添加 1
  3. 将值写回 dummyInt

所以是的,你确实需要同步这个。一个线程可以读取该值,然后另一个线程执行所有三个操作,并且当第一个线程完成时,该值仅增加 1(我希望这是有道理的:P)。dummyBoolean类似。您在 if 语句中读取它并写入新值。

编辑

很抱歉没有正确阅读问题。根据javadoc,这不需要同步。

于 2010-03-07T17:03:48.397 回答