在现场运行多个线程并等待所有线程完成,方便和安全hashMap

时间:2016-12-14 00:48:32

标签: java arrays multithreading optimization

我刚开始学习线程背后的概念而且我遇到了问题。

我有一个N Strings数组,其中N是可变的,但总是<= 5。 我有另一个容量为N的空数组。

现在,我必须对每个字符串one by one进行一些复杂的计算,每个结果都在空数组中,与刚检查的字符串在同一索引上。

当一切都结束时,将分析结果数组并保留最长的结果。所有这一切发生的线程都是主线程。

计算花了很多时间,所以我在想是否值得打开N新主题,并一起评估所有这些。

值得一提的是,计算涉及在HashMap<String, customObject>上查找字符串,这与所有字符串相同。因此,对于线程,他们将一起访问它。他们不会编辑它,只是寻找值。地图可以更改,但在执行时永远不会更改,因为它会在代码的后面的主线程中从其他部分更改。

示例:

//Current approach

HashMap<String, Object> m = new HashMap<>(); //filled with 10^6 values

String[] data = new String[3];
Object[] results = new String[3];

results[0] = complexCalculationsAndSearcOnHashMap(data[0]); 
results[1] = similarComplexCalculationsAndSearcOnHashMap(data[1]);
results[2] = otherComplexCalculationsAndSearcOnHashMap(data[2]);

//Now every complex calculation has to wait until the last one ended before starting. But the only thing that actually should have to wait is this next line:

Object finalResult = longest(results);

所以我的问题是,我应该构建3个线程并将复杂的计算放在run方法中吗?方便,还是让整个线程概念错了?这在应用程序中造成了瓶颈,需要很长时间才能完成。

线程示例:

HashMap<String, Object> m = new HashMap<>(); //filled with 10^6 values

    String[] data = new String[3];
    Object[] results = new String[3];

    Thread t0 = new Thread(){

    public void run(){
      results[0] = complexCalculationsAndSearcOnHashMap(data[0]);
    }
};

//Thread t1, t2..
//t0.start(), t1.start()...

 Object finalResult = longest(results);

如果上一个答案是肯定的,那么如何让最后一行等待所有3个线程完成,而他们独立于另一个运行我是否通过循环加入所有3个?

最后但并非最不重要的是,安全以这种方式使用HashMap吗? 或者我应该切换到另一个与线程更好的集合对象? 我已经阅读了几个关于此的想法,似乎没有人同意。 它会慢吗? 我不能失去任何优化,除非此时非常必要。

修改

应该指出,“他们需要很长时间才能完成”不应该被视为理所当然。虽然有97%的时间N功能确实需要很长时间才能完成,但它们几乎可以瞬间发生。 我不知道这是否有所作为。

**编辑2:**

我不仅要问如何运行所有4并等待它们完成,我还需要知道在这种情况下是否正确的做法,或者它是否会改变一件事,我还需要了解如果可以这样使用hashMap。

**有关守则的详情**

  • 所有这些都发生在同一个对象中,没有使用静态字段。
  • HashMap早已在另一个对象中初始化。
  • HashMap可以在同一个线程上更改,但在另一个对象中。因此,当其他3个线程运行时,它不会发生。
  • 这是应用程序使用更多线程的唯一时间。

1 个答案:

答案 0 :(得分:3)

您可以使用简单的方法为每个“计算”创建一个线程

    Thread[] workers = new Thread[count];
    for (int i = 0; i < count; i++) {
        final int index = i;
        //create thread to calculate i-th value
        workers[i] = new Thread(new Runnable() {
            @Override
            public void run() {
                results[index] = complexCalculationsAndSearcOnHashMap(data[index]);
            }
        });
        workers[i].start();
    }
    for (int i = 0; i < count; i++) {
        //wait until threads execution is finished
        workers[i].join();
    }

    //Test output
    System.out.println(Arrays.toString(results));

如果您的计算函数依赖于索引...您可以使用索引选择相应的函数或创建外部循环的线程。