用于模拟数据的Java多线程

时间:2016-03-16 19:50:53

标签: java multithreading statistics analytics simulation

因此,我目前正在创建数据分析和预测程序,出于测试目的,我正在模拟大量数据(在10,000 - 1,000,000范围内)“试验”。数据是理论游戏的模拟匹配。每场比赛都有轮次。该程序的基本psudocode是这样的:

main(){
    data = create(100000);
    saveToFile(data);
}

Data create(){
    Data returnData = new Data(playTestMatch());
}

Match playTestMatch(){


    List<Round> rounds = new List<Round>();

    while(!GameFinished){
        rounds.add(playTestRound());
    }

    Match returnMatch = new Match(rounds);
}


Round playTestRound(){
    //Do round stuff
}

现在,我想知道我是否可以在多个线程上处理这些回合的模拟以加速该过程。我不熟悉多线程背后的理论,所以有人请帮助我完成这个,或者向我解释为什么这不起作用(不会加快这个过程)。谢谢!

2 个答案:

答案 0 :(得分:0)

如果您的代码是线程安全的,并且您可以将任务拆分为不相互依赖的离散块,那么它相对容易。使完成工作的类Callable并将工作块添加到List中,然后使用ExecutorService,如下所示:

ArrayList<Simulation> SL=new ArrayList<Simulation>();
for(int i=0; i<chunks; i++)
    SL.add(new Simulation(i);
ExecutorService executor=Executors.newFixedThreadPool(nthreads);//how many threads
List<Future<Result>> results=null;
try {
     results = executor.invokeAll(SL);
    } catch (InterruptedException e) {
      e.printStackTrace();
    }
executor.shutdown();
for(Future<Result> result:results)
  result.print();

因此,Simulation是可调用的并返回一个Result,结果是一个List,当使用模拟的ArrayList调用executor.invokeAll时,它将被填充。获得结果后,您可以打印它们或其他任何内容。可能最好将nthreads设置为等于您可用的核心数。

答案 1 :(得分:0)

如果您不熟悉Java多线程,这个解释起初可能看起来有点难以理解,但我会尝试让它看起来尽可能简单。

基本上我认为,无论何时拥有大型数据集,使用多个线程同时运行操作都会显着加快流程速度,这与使用单线程方法相反,但当然也有例外。

你需要考虑三件事:

  1. 创建主题

  2. 管理主题

  3. 通过主线程

  4. 传达/分享每个线程计算的结果

    创建线程: 可以手动创建线程类来创建线程,也可以使用Executors类。 我更喜欢Executors类来创建线程,因为它允许您创建线程池并为您执行线程管理。也就是说,它允许您重用线程池中空闲的现有线程,从而减少应用程序的内存占用。 您还必须查看ExecutorService Interface,因为您将使用它来激发您的任务。

    管理线程: Executors / Executors服务可以自动管理线程,所以如果你使用它,你就不必担心线程管理了。

    沟通:这是整个过程的关键部分。在这里,您必须详细考虑应用程序的线程安全性。

    我建议使用两个队列来完成这项工作,一个读取队列来读取数据并写入队列来写入数据。

    但是,如果您使用的是简单的arraylist,请确保通过将arraylist封装在同步块中来同步代码以确保线程安全

    synchronized(arrayList){
     // do stuff
    

    }