何时并行执行任务是矫枉过正



我有一段java代码,它从xml构造一个对象,根据对象大小需要几纳秒到几毫秒。有时我必须循环调用该方法 1-2 次,有时调用 70-80 次才能构造对象列表。

我尝试并行构造对象,但有时它花费的时间是顺序的两倍,其他时间的一半。现在我的问题是,是否有任何指南或性能比较指标来指导何时应该使用多任务处理以及何时只是矫枉过正?

我使用的示例代码是:

    List<Callable<Integer>> tasks = new ArrayList<Callable<Integer>>();
    for (final Integer object : list) {
        Callable<Integer> c = new Callable<Integer>() {
            @Override
            public Integer call() throws Exception {
                    return test.m1(object);
            }
        };
        tasks.add(c);
    }
    List<Future<Integer>> results = EXEC.invokeAll(tasks);
    for (Future<Integer> fr : results) {
        fr.get();
    }

看看Doug Lea的文章"何时使用并行流"。

粗略估计(在十倍以内)是并行计算开始有意义时 100 微秒的顺序执行。尽管需要考虑的因素还有很多。

简短回答:当您没有性能或 IO 阻塞问题时,这是矫枉过正的。

有关并行性能的几个因素是:

  • 任务之间需要多少沟通/协调。 有关具有最少协调的示例,请参阅令人尴尬的并行。
  • 创建并行处理的结构需要时间。 例如,OSX 线程大约需要 90 微秒才能创建,因此您至少需要节省那么多(如果您创建一个)。
  • 并行处理不会加快顺序分数的速度。 如果任务需要一个小时,并且只有 75% 可以并行处理,那么您将无法在不到 15 分钟的时间内完成任务。参见阿姆达尔定律。

最新更新