具有非最终函数参数的Java Lambda表达式 [英] Java Lambda Expression with Non-final Function Paramter
问题描述
我试图通过使用Runnable接口包装我需要的任何函数来简单地计时一个函数.
I am trying to simply time a function by using the Runnable interface to wrap around whichever function I need.
private static double time(Runnable runnable) { // returns how long runnable took
long startTime = System.nanoTime();
runnable.run();
return (System.nanoTime() - startTime) / 1000000000.0;
}
然后我可以简单地执行以下操作:
then I could simply do the following:
double durationOfFunctionA = time(Driver::functionA); // functionA belongs in class Driver
但是,如果我有一个带有参数的函数,则必须将其修改为:
however, if I have a function that takes a parameter, it must be modified to:
double durationOfFunctionB = time(() -> functionB(someParameter));
我遇到的问题是'someParameter'必须是final或有效的final.有没有解决此问题的方法?我已经看到了forEach的循环,但是我需要将此参数从1、10、100->指数化直到满足条件.代码是这样的:
The problem I am having is that 'someParameter' must be final or effectively final. Is there any workaround this problem? I have seen loops with forEach, but I need this parameter to be exponential from 1, 10, 100 -> until a condition is met. The code is this:
public static void main(String[] args) {
double timer = 0;
int size = 1;
while(timer <= 10) {
timer = time(() -> functionB(size));
size *= 10;
}
}
我需要functionB接受一个参数,因为我想测试它的复杂性/big-O.我担心我没有以正确的方式编码/使用lambda表达式.如果有人可以帮助解决此问题或找到其他解决方案,将不胜感激.
I require functionB to take in a parameter because I want to test the complexity/big-O of it. I am worried that I am not coding/using lambda expressions the correct way. If someone can help solve this problem or find another solution, that would be appreciated.
作为旁注,我确实知道我不必使用Runnable接口使其变得如此复杂,我只需在while循环中进行计时即可.但是,我只是想看看是否可以做这样的事情,所以我可以只输入一些要测试的功能,也可以输入语法糖.
As a side note, I do know that I don't have to make this so complex with a Runnable interface, I can just do the timing right in the while loop. However, I just wanted to see if it were possible to do such a thing both so I could just input some function to test, and as syntactic sugar.
推荐答案
您可以像这样简单地将变量值复制到单独的最终变量中:
You can simply copy the variable value to separate final variable like this:
double timer = 0;
int size = 0;
while(true) {
final finalSize = size;
timer = time(() -> functionB(finalSize));
size *= 10;
}
此外,我可以建议您为要计时的功能的各种参数制作更多的计时功能. 这是您的操作方法:
Also, I can advice you to make some more timing functions for various amount of parameters for functions you want to time. Here how you can do it:
public class Test {
public static void main(final String[] args) {
int ttt = 0;
time(ttt, Test::func);
time(ttt, ttt, Test::func);
}
public static void func(int i) {
}
public static void func(int i, int j) {
}
public static <T> double time(T arg, Consumer<T> func) {
long startTime = System.nanoTime();
func.accept(arg);
return (System.nanoTime() - startTime) / 1000000000.0;
}
public static <T1, T2> double time(T1 arg1, T2 arg2, BiConsumer<T1, T2> func) {
long startTime = System.nanoTime();
func.accept(arg1, arg2);
return (System.nanoTime() - startTime) / 1000000000.0;
}
}
这篇关于具有非最终函数参数的Java Lambda表达式的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!