java-简单计算在多线程中比在单线程中花费更长的时间
我试图理解如何利用多线程。我编写了一个简单的程序,它使用两种方式将java-简单计算在多线程中比在单线程中花费更长的时间,java,multithreading,performance,Java,Multithreading,Performance,我试图理解如何利用多线程。我编写了一个简单的程序,它使用两种方式将I的值递增400000倍:单线程方式(0到400000)和多线程方式(在我的例子中,是4倍:0到100000),线程数等于Runtime.getRuntime().availableProcessor() 我对我测量的结果感到惊讶:单线程方式的速度明显更快,有时快3倍。这是我的密码: public class Main { public static int LOOPS = 100000; private stat
I
的值递增400000倍:单线程方式(0到400000)和多线程方式(在我的例子中,是4倍:0到100000),线程数等于Runtime.getRuntime().availableProcessor()
我对我测量的结果感到惊讶:单线程方式的速度明显更快,有时快3倍。这是我的密码:
public class Main {
public static int LOOPS = 100000;
private static ExecutorService executor=null;
public static void main(String[] args) throws InterruptedException, ExecutionException {
int procNb = Runtime.getRuntime().availableProcessors();
long startTime;
long endTime;
executor = Executors.newFixedThreadPool(procNb);
ArrayList<Calculation> c = new ArrayList<Calculation>();
for (int i=0;i<procNb;i++){
c.add(new Calculation());
}
// Make parallel computations (4 in my case)
startTime = System.currentTimeMillis();
queryAll(c);
endTime = System.currentTimeMillis();
System.out.println("Computation time using " + procNb + " threads : " + (endTime - startTime) + "ms");
startTime = System.currentTimeMillis();
for (int i =0;i<procNb*LOOPS;i++)
{
}
endTime = System.currentTimeMillis();
System.out.println("Computation time using main thread : " + (endTime - startTime) + "ms");
}
public static List<Integer> queryAll(List<Calculation> queries) throws InterruptedException, ExecutionException {
List<Future<Integer>> futures = executor.invokeAll(queries);
List<Integer> aggregatedResults = new ArrayList<Integer>();
for (Future<Integer> future : futures) {
aggregatedResults.add(future.get());
}
return aggregatedResults;
}
}
class Calculation implements Callable<Integer> {
@Override
public Integer call() {
int i;
for (i=0;i<Main.LOOPS;i++){
}
return i;
}
}
公共类主{
公共静态int循环=100000;
私有静态执行器服务执行器=null;
公共静态void main(字符串[]args)引发InterruptedException、ExecutionException{
int procNb=Runtime.getRuntime().availableProcessors();
长启动时间;
长时间;
executor=Executors.newFixedThreadPool(procNb);
ArrayList c=新的ArrayList();
对于(int i=0;i一个加法可能需要一个cpu周期,因此,如果您的cpu以3GHz运行,则为0.3纳秒。执行400k次,则会变为120k纳秒或0.1毫秒。因此,与您试图测量的操作相比,您的测量更受启动线程、线程切换、JIT编译等开销的影响
您还需要考虑编译器的优化:如果您将空循环放在一个方法中并多次运行该方法,您将注意到它在一段时间后的0毫秒内运行。因为编译器确定该循环不执行任何操作,并将其完全优化
我建议您使用专门的库进行微观基准测试,例如
另请参见:您不认为您在多线程方面做得太多了吗?创建未来,将未来添加到列表中?多线程总是比单线程好也不是强制性的。我猜创建多线程所需的时间比增加值要长。当然多线程有开销。您需要一个足够大的问题来获得多线程ti线程优势。它还取决于平台、硬件(多核)和使用的实现(Java8 Streams可以大量使用多核)。此外,为了提高使用多线程的速度,一个线程的计算不能依赖于另一个线程的计算结果,也不能被另一个线程的计算结果阻止。感谢您的回答。即使我将循环数乘以10,结果也是一样的。我想强调我的“for”也非常重要循环是空的,编译器优化了它的计算…而我的基准测试是有偏差的!