Java中的多线程基准测试

时间:2011-01-20 00:07:15

标签: java exception-handling

我正在做一个科学公平的项目,我在其中测试了多少额外的处理核心提高了计算速度。这是我迄今为止编写的多核基准,但存在问题。 "线程#.join();"所有行都会抛出错误。有人可以帮忙修复这个吗?请记住,我是初学者,所以你能用非常简单的术语解释如何解决它或通过将修复后的代码放在你的回复中给我看。这就是我所拥有的:

import java.util.Calendar;
import java.text.SimpleDateFormat;
import java.util.Scanner;
import java.text.*;
import java.util.concurrent.*;

public class SciFair 
{

    /**
     * Numa Robertson
     * 1/13/11
     * Science Fair 2011
     */

    public static String now(String dateFormat) {
        Calendar cal = Calendar.getInstance();
        SimpleDateFormat sdf = new SimpleDateFormat(dateFormat);
        return sdf.format(cal.getTime());
    }

    public static void main(String[] args) {
        Scanner dataIn = new Scanner(System.in);
        DecimalFormat timeInSeconds = new DecimalFormat("##.###");

        System.out.println("Are you ready to begin the benchmark? ");
        String response = dataIn.nextLine();
        double endNum = 0;

        if(response.equals("Yes") || response.equals("yes") || response.equals("Ok") || response.equals("ok")) {

            System.out.println("Benchmark starting at " + SciFair.now("H:mm:ss:SSS") + ".");

            String startTimeHours = SciFair.now("H");
            String startTimeMinutes = SciFair.now("mm");
            String startTimeSeconds = SciFair.now("ss");
            String startTimeMilliseconds = SciFair.now("SSS");
            double startTimeHoursNumFormat = Double.valueOf(startTimeHours.trim()).doubleValue();
            double startTimeMinutesNumFormat = Double.valueOf(startTimeMinutes.trim()).doubleValue();
            double startTimeSecondsNumFormat = Double.valueOf(startTimeSeconds.trim()).doubleValue();
            double startTimeMillisecondsNumFormat = Double.valueOf(startTimeMilliseconds.trim()).doubleValue();
            double startHoursInSeconds = (startTimeHoursNumFormat * 3600);
            double startMinutesInSeconds = (startTimeMinutesNumFormat * 60);
            double startMillisecondsInSeconds = (startTimeMillisecondsNumFormat / 1000);
            double startTotalSeconds = (startHoursInSeconds + startMinutesInSeconds + startTimeSecondsNumFormat + startMillisecondsInSeconds);

            Thread thread1 = new Thread() {
                public void run() {
                    double endNum = 0;
                    double num = 5832544225416546445465465465465465448412168546725.2655236355335649499923164684654345649874181221173246189579162421579584572121334216957951462175918894199993642446445548521652158975;

                    for(double numberRun = 0; numberRun <= 1666666660; numberRun++) {
                        endNum = endNum+((num * 58445246411658545558.458561435435385465146445641894984984651321616548946132131654984 + 26564.6351648941654984156 / 321654984616321654654984365.3216548974165416484 + 216541648165141654.23164584961321316546844651 * 65616484316541486541.1654484646546576746862468546576248645814668585145181 / 111.3216516543464545795479884754424759845 * 3467247954975472171276545789595.4721756147541715715157145715145714514748717521 / 31654688498445132154.3215449848489461531654 * 61654984132165465484464131321145644684.3164846434654648446546546465456465465414321165118547521569845258547566352544 / 32136546465434654654484843131.3164484151515121211554464547951126758178571454164175415417584175664) / 2431276251975915431326725157958456157321624621765419.4321672175951247316726451751487465462645754579517232172757497516373127651975167516715);    
                    }
                }
            };


            Thread thread2 = new Thread() {
                public void run() {
                    double endNum = 0;
                    double num = 5832544225416546445465465465465465448412168546725.2655236355335649499923164684654345649874181221173246189579162421579584572121334216957951462175918894199993642446445548521652158975;

                    for(double numberRun = 0; numberRun <= 1666666660; numberRun++) {
                        endNum = endNum+((num * 58445246411658545558.458561435435385465146445641894984984651321616548946132131654984 + 26564.6351648941654984156 / 321654984616321654654984365.3216548974165416484 + 216541648165141654.23164584961321316546844651 * 65616484316541486541.1654484646546576746862468546576248645814668585145181 / 111.3216516543464545795479884754424759845 * 3467247954975472171276545789595.4721756147541715715157145715145714514748717521 / 31654688498445132154.3215449848489461531654 * 61654984132165465484464131321145644684.3164846434654648446546546465456465465414321165118547521569845258547566352544 / 32136546465434654654484843131.3164484151515121211554464547951126758178571454164175415417584175664) / 2431276251975915431326725157958456157321624621765419.4321672175951247316726451751487465462645754579517232172757497516373127651975167516715);    
                    }
                }
            };

            //Snip out a bunch of copy/paste thread implementations



            thread1.start();
            thread2.start();
            thread3.start();
            thread4.start();
            thread5.start();
            thread6.start();

            thread1.join();
            thread2.join();
            thread3.join();
            thread4.join();
            thread5.join();
            thread6.join();


            String endTimeHours = SciFair.now("H");
            String endTimeMinutes = SciFair.now("mm");
            String endTimeSeconds = SciFair.now("ss");
            String endTimeMilliseconds = SciFair.now("SSS");
            double endTimeHoursNumFormat = Double.valueOf(endTimeHours.trim()).doubleValue();
            double endTimeMinutesNumFormat = Double.valueOf(endTimeMinutes.trim()).doubleValue();
            double endTimeSecondsNumFormat = Double.valueOf(endTimeSeconds.trim()).doubleValue();
            double endTimeMillisecondsNumFormat = Double.valueOf(endTimeMilliseconds.trim()).doubleValue();
            double endHoursInSeconds = (endTimeHoursNumFormat * 3600);
            double endMinutesInSeconds = (endTimeMinutesNumFormat * 60);
            double endMillisecondsInSeconds = (endTimeMillisecondsNumFormat / 1000);
            double endTotalSeconds = (endHoursInSeconds + endMinutesInSeconds + endTimeSecondsNumFormat + endMillisecondsInSeconds);

            double elapsedTime = (endTotalSeconds - startTotalSeconds);

            System.out.println("\nThe benchmark is complete at " + SciFair.now("H:mm:ss:SSS") + ", and the end result is " + endNum + ".");
            System.out.println("\nThe benchmark was run in " + timeInSeconds.format(elapsedTime) + " seconds.");
        } else {
            System.out.println("\nPlease restart the program when you are ready to benchmark.");
        }
    }
}

2 个答案:

答案 0 :(得分:1)

问题是Thread#join()抛出了一个已检查的异常,编译器希望您处理该异常。检查异常通常通过声明您的方法/函数可以抛出异常或捕获异常来处理。

在您的特定情况下,由于您只是编写一个简单的基准测试应用程序,最简单的解决方案是仅指示您的代码可能抛出异常。

public static void main(String[] args) throws InterruptedException {

处理异常的一个例子是这样的:

try {
    thread1.join();
    thread2.join();
    thread3.join();
    thread4.join();
    thread5.join();
    thread6.join();
} catch (InterruptedException e) {
    Thread.currentThread().interrupt(); //This is a best practice for handling the InterruptedException only
    logger.log("The thread has been interrupted and should now exit quickly and cleanly. Processing may be incomplete.");
}

答案 1 :(得分:0)

我建议你使用ExecutorService。我希望你会看到它使管理线程变得更容易。

public static void main(String[] args) throws InterruptedException {
int threads = 6;

System.out.println("Benchmark starting at " + new Date());
long start = System.nanoTime();
ExecutorService es = Executors.newCachedThreadPool();
for (int i = 0; i < threads; i++)
    es.submit(new Runnable() {
        public void run() {
            // place your benchmark code here
        }
    });
es.shutdown();
es.awaitTermination(60, TimeUnit.SECONDS);
long time = System.nanoTime() - start;

System.out.printf("%nThe benchmark is complete at " + new Date() + "%nThe benchmark was run in %.3f seconds.%n", time / 1e9);
}

我认为你的编译错误是你没有处理InterruptedException。没有必要捕获InterruptedException作为a)它不应该发生b)除了记录它你不能做任何事情。