我可以将一个方法作为java中另一个方法的参数传递吗?

我试图测量几种方法的执行时间。 所以我想要制作一个方法,而不是多次复制相同的代码。

这是我的代码:

private void MeasureExecutionTime(Method m) { startTime = System.nanoTime(); try { m(); } finally { endTime = System.nanoTime(); } elapsedTime = endTime - startTime; System.out.println("This takes " + elapsedTime + " ns."); } 

假设我有myMethod() ,我如何使用MeasureExecutionTime()来测量myMethod的执行时间?

方法不是Java中的第一类对象,因此它们不能作为参数传递。 你可以在一个烦人的类中使用wrap你的方法调用,例如Runnable接口:

 private void MeasureExecutionTime(Runnable r) { r.run(); } ... MeasureExecutionTime(new Runnable() { public void run() { m(); } }); 

最简单的方法是传递一个接口。 所以像

 public interface CommonFuncs { public void execute(); ... more functions } 

然后在你可以拥有将CommonFuncs作为参数的方法。 这些方法的实现可以调用execute方法。

我同意@hvgotcodes,但是,有可能,虽然你没有像m()那样调用它,但是使用invoke (这意味着你可能应该传递另一个或两个参数……)。

您处于正确的路径中,您需要传递Method对象,执行该方法的目标对象及其所需的参数,然后将其调用到try catch中,例如:

 private void MeasureExecutionTime(Method m, Object target, Object args) throws IllegalArgumentException, IllegalAccessException, InvocationTargetException { long startTime = System.nanoTime(); long endTime; try { m.invoke(target, args); } finally { endTime = System.nanoTime(); } long elapsedTime = endTime - startTime; System.out.println("This takes " + elapsedTime + " ns."); } 

我有一个对象调用计数器,基本上看起来像这样:

 private long count; private long errors; private long duration; private long errorDuration; 

有两个“时间”方法用于返回某些方法和其他无效方法。

 public  T time(ReturningRunnable runnable) { long start = currentTimeMillis(); T result = null; try { result = runnable.run(); } catch (Throwable ex) { errorDuration += currentTimeMillis() - start; errors++; throw runtime(ex); } duration += currentTimeMillis() - start; count++; return result; } public void time(Runnable runnable) { time(new RunnableRunner(runnable)); } 

我选择将exception重新抛出为运行时exception(因为我不是检查exception的粉丝),但你也可以使自定义MyRunnable接口抛出exception,然后捕获并重新抛出它们。 以下是上述用法:

 counter.time(new Runnable() { @Override public void run() { // Do something }); 

或者,在返回值的情况下:

 return counter.time(new ReturningRunnable() { @Override public Integer run() { return 1; // You get the idea }); 

我喜欢这个,因为我的计数器对象可以通过JMX暴露并注入我需要的任何地方。 你可以用反思做你所问的,但我认为那会很混乱(恕我直言)。

你可以这样做:

 private void MeasureExecutionTime(Method m) { startTime = System.nanoTime(); try { m.invoke(classObj, args); } finally { int endTime = System.nanoTime(); } elapsedTime = endTime - startTime; System.out.println("This takes " + elapsedTime + " ns."); }