【问题标题】:Parallel execution of multi-threaded program in JavaJava中多线程程序的并行执行
【发布时间】:2017-09-28 02:49:31
【问题描述】:

我想使用多线程方法编写一个程序,其中每个线程执行一些 IO 操作,每个 IO 操作需要 100 毫秒才能完成。我的问题是我想这样设计我的问题,即一旦线程调用 IO 操作并进入等待状态,其余线程应该开始执行。

这是我最初的实验:

public class TestThread {
    public static void main(String args[]) throws InterruptedException {
        List<String> list = new ArrayList<>();
        ExecutorService executorService = Executors.newFixedThreadPool(10);
for(int i = 0; i < 50; i++) {
            Future<String> future = executorService.submit(() -> {
                System.out.println(Thread.currentThread().getId());
                return getValue();
               //here instead of calling getValue(), thread will call some IO operation
//each IO call is indepndent of each other
            });
            list.add(future.get());
        }
       }
    static String getValue() throws InterruptedException {
        if(Thread.currentThread().getId() == 11)
        Thread.sleep(10000);
        return "some value for the thread " + Thread.currentThread().getId();
    }
}

观察到的情况如下: 12 号线程一直等到 11 号线程完成执行。我想要的是,一旦 11 号线程进入睡眠状态(在实际问题中它将进入 IO 等待),12 号线程应该开始执行。 请帮我设计这个问题。

【问题讨论】:

  • 什么?请尝试重申您的问题。
  • 你有一个固定的线程池。当然,它会等待。如果线程池小于线程数,就会阻塞。

标签: java multithreading threadpool threadpoolexecutor


【解决方案1】:

12 号线程一直等到 11 号线程完成执行

这可能是因为您将每个任务添加到一个循环中,您可能认为它会以异步方式触发并忘记,但是您通过调用 @987654321 有效地阻止了连续任务的启动@ 和循环结束。

future.get() 处于阻塞状态,因此线程 11 阻止了线程 12 的启动。

我提出这个设计,是为了避免挡住自己

import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.ListenableFuture;
import com.google.common.util.concurrent.ListeningExecutorService;
import com.google.common.util.concurrent.MoreExecutors;
import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;

public class TestThread {

    public static List<Integer> execute(ExecutorService executorService, Callable<Integer> callable, int calls)
        throws ExecutionException, InterruptedException {
        ListeningExecutorService listeningExecutorService = MoreExecutors.listeningDecorator(executorService);

        List<ListenableFuture<Integer>> futures = new ArrayList<>();

        for (int i = 0; i < calls; i++) {
            futures.add(listeningExecutorService.submit(callable));
        }

        return Futures.allAsList(futures).get();
    }
}

我建议,如果 IO 调用是相互独立的,那么为什么要鼓励它们相互等待呢?为什么他们会生成任何类型的组合列表?

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2022-10-13
    • 1970-01-01
    • 2017-08-17
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多