如何获得方法的执行时间? 是否有Timer实用程序类来计时任务所需的时间等?

在谷歌上的大多数搜索都返回调度线程和任务的计时器的结果,这不是我想要的。


当前回答

对于java 8+,另一种可能的解决方案(更通用,函数风格,没有方面)可能是创建一些实用程序方法,将代码作为参数接受

public static <T> T timed (String description, Consumer<String> out, Supplier<T> code) {
    final LocalDateTime start = LocalDateTime.now ();
    T res = code.get ();
    final long execTime = Duration.between (start, LocalDateTime.now ()).toMillis ();
    out.accept (String.format ("%s: %d ms", description, execTime));
    return res;
}

调用代码可以是这样的smth:

public static void main (String[] args) throws InterruptedException {
    timed ("Simple example", System.out::println, Timing::myCode);
}

public static Object myCode () {
    try {
        Thread.sleep (1500);
    } catch (InterruptedException e) {
        e.printStackTrace ();
    }
    return null;
}

其他回答

总有一些过时的方法:

long startTime = System.nanoTime();
methodToTime();
long endTime = System.nanoTime();

long duration = (endTime - startTime);  //divide by 1000000 to get milliseconds.

下面是打印好的字符串,格式化后的秒数,类似于谷歌搜索所需的时间:

        long startTime = System.nanoTime();
        //  ... methodToTime();
        long endTime = System.nanoTime();
        long duration = (endTime - startTime);
        long seconds = (duration / 1000) % 60;
        // formatedSeconds = (0.xy seconds)
        String formatedSeconds = String.format("(0.%d seconds)", seconds);
        System.out.println("formatedSeconds = "+ formatedSeconds);
        // i.e actual formatedSeconds = (0.52 seconds)

纯Java SE代码,不需要添加依赖项,使用TimeTracedExecuter:

public static void main(String[] args) {

    Integer square = new TimeTracedExecutor<>(Main::calculateSquare)
                .executeWithInput("calculate square of num",5,logger);

}
public static int calculateSquare(int num){
    return num*num;
}

会产生这样的结果:

信息:计算num的平方需要3毫秒

自定义可重用类:TimeTracedExecutor

import java.text.NumberFormat;
import java.time.Duration;
import java.time.Instant;
import java.util.function.Function;
import java.util.logging.Logger;

public class TimeTracedExecutor<T,R> {
    Function<T,R> methodToExecute;

    public TimeTracedExecutor(Function<T, R> methodToExecute) {
        this.methodToExecute = methodToExecute;
    }

    public R executeWithInput(String taskDescription, T t, Logger logger){
        Instant start = Instant.now();
        R r= methodToExecute.apply(t);
        Instant finish = Instant.now();
        String format = "It took %s milliseconds to "+taskDescription;
        String elapsedTime = NumberFormat.getNumberInstance().format(Duration.between(start, finish).toMillis());
        logger.info(String.format(format, elapsedTime));
        return r;
    }
}

在我的机器上进行性能测量

System.nanoTime(): 750ns System.currentTimeMillis(): 18ns

如前所述,System.nanoTime()被认为是度量经过的时间。只要注意在循环中使用的代价就可以了。

我实现了一个简单的定时器,我认为它真的很有用:

public class Timer{
    private static long start_time;

    public static double tic(){
        return start_time = System.nanoTime();
    }

    public static double toc(){
        return (System.nanoTime()-start_time)/1000000000.0;
    }

}

这样你就可以计算一个或多个动作的时间:

Timer.tic();
// Code 1
System.out.println("Code 1 runtime: "+Timer.toc()+" seconds.");
// Code 2
System.out.println("(Code 1 + Code 2) runtime: "+Timer.toc()+"seconds");
Timer.tic();
// Code 3
System.out.println("Code 3 runtime: "+Timer.toc()+" seconds.");