当前位置: 首页 > 知识库问答 >
问题:

java中的executor服务不是并行提交任务的吗?

江新
2023-03-14

我在玩java多线程代码。我创建了一个具有固定线程池的executor服务。我正在提交两个任务顺序。我试图用线程使第一个任务变得很长。我在想这两个任务将并行运行。然而,当我运行程序时,程序会等待一段时间,然后输出一个B,这意味着编译器首先完成了第一个任务,然后才执行第二个任务。事实上,我在期待,因为第二个任务是一个短任务,它会在第一个任务之前完成。有什么解释吗?

 public static void main(String[] args) {
    ExecutorService executor = Executors.newFixedThreadPool(10);
    Map<String, String> map = new HashMap<>();
    ReadWriteLock lock = new ReentrantReadWriteLock();
    executor.submit(() -> {
        lock.writeLock().lock();
        try {
            Thread.sleep(10000);
            map.put("boo", "mar");
            System.out.println("A");
        } catch (InterruptedException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } finally {
            lock.writeLock().unlock();
        }
    });

    executor.submit(() -> {
        lock.writeLock().lock();
        try {
            Thread.sleep(1);
            map.put("foo", "bar");
            System.out.println("B");
        } catch (InterruptedException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } finally {
            lock.writeLock().unlock();
        }
    });

    executor.shutdown();
}

共有1个答案

荣波
2023-03-14

在第一个线程Hibernate之前,您正在“锁定”writeLock。所以锁实际上是锁了10秒钟…然后就解锁了。第二个线程等待了10秒来获取锁。

事件顺序:

Thread 1: Starts
Thread 2: Starts

Thread 1: Acquire Lock and wait for 10 seconds.
Thread 2: Try to acquire lock (ends up waiting 10 seconds because it is already acquired by Thread 1).

Thread 1: Prints Data.
Thread 1: Unlocks lock.

Thread 2: Acquires lock.
Thread 2: Prints data.
Thread 2: Unlocks lock.

尝试如下所示(它只在必要时才获得锁。例如:在执行写操作或修改映射时):

public static void main(String[] args) {
        ExecutorService executor = Executors.newFixedThreadPool(10);
        Map<String, String> map = new HashMap<>();
        ReadWriteLock lock = new ReentrantReadWriteLock();
        executor.submit(() -> {
            try {
                Thread.sleep(10000);

                lock.writeLock().lock();
                map.put("boo", "mar");
                lock.writeLock().unlock();

                System.out.println("A");
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        });

        executor.submit(() -> {
            try {
                Thread.sleep(1);

                lock.writeLock().lock();
                map.put("foo", "bar");
                lock.writeLock().unlock();

                System.out.println("B");
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        });

        executor.shutdown();
    }
 类似资料:
  • 假设我有几个任务要在Java中并行运行。每个任务要么返回成功,要么返回失败。每个任务都有一个相关的截止日期。如果任务未在截止日期前完成,它将被中断(所有任务都可中断)并返回失败。 如果其中一个任务失败(即返回失败),我们将中断所有仍在运行的其他任务。 我们应该等到所有任务都完成,最后如果所有任务都返回成功,则返回成功;如果至少有一个任务返回失败,则返回失败。 你将如何实施它?我将使用util。同时

  • 我刚开始学习Java多线程。我从这个简单的代码开始,但是似乎从未实现。 我希望“任务执行”结果应该被打印出来,但我得到了一个空控制台。 下面是我的简单类:

  • 我正在尝试将一个任务提交给Java的ExecutorService。它要么需要一个Callable,它允许抛出异常,要么需要一个Runnable。我的用例是愚蠢的:我想安排一个抛出异常的任务,但它是一个无效的方法。因此,我不能使用Callable或Runnable,因为方法定义与我的用例不匹配。我还想让我的异常从提交后收到的Future传播。有什么想法吗?

  • 所以我使用executorservice创建了一个线程池。 我试图访问线程池队列中的任务数。我看到没有办法得到它。我知道有一些方法来获取线程池执行器中的队列大小,但是我如何使用执行器服务对象来实现这一点。 就像我说的,如果我创建了一个像这样的线程池执行器,我可以得到队列信息 我知道我可以使用tpExecutor。队列size()获取线程池队列中的任务数。但目前我已经使用Executor服务声明了我

  • 我正在使用sping-boot,我有这样一个用例,我想将列表的每个元素提交给执行器服务(线程池大小=4)。但是在每个必须处理的元素之间,我想要1秒钟的延迟。 Thread.sleep(1000)不工作,因为执行程序一睡觉就启动另一个线程。 编辑:这是我的process()方法,我在最后尝试使用sleep,但没有成功。

  • 问题内容: 我有一些我想在JS中做的资源密集型任务。对于这个问题,让我们假设它们是一些繁重的计算,而不是系统访问。现在,我想同时运行任务A,B和C,并在完成后执行一些功能D。 该异步库为此提供了一个很好的脚手架: 如果我正在做的只是计算,那么它将仍然同步运行(除非库将任务本身放在不同的线程上,我希望情况并非如此)。我如何使它实际上是平行的?异步代码通常不阻止调用者的事情是什么(使用NodeJS时)