为什么下面的代码片段在第二次通过时打印 true ?不应该是一个新实例吗?
import java.util.function.Supplier;
public class Foo {
public static void main(String[] args) throws Exception {
Supplier<Long> old = () -> System.nanoTime();
for (int i = 0; i < 3; i++) {
/* false true true
Supplier<Long> foo = System::nanoTime;*/
Supplier<Long> foo = () -> System.nanoTime();
/* false false false
Supplier<Long> foo = new Supplier<Long>() {
@Override
public Long get() {
return System.nanoTime();
}
};
//*/
System.out.printf("%s %s %s%n", foo == old, foo, old);
old = foo;
}
}
}
false Foo$$Lambda$2/122883338@1ddc4ec2 Foo$$Lambda$1/1534030866@133314b
true Foo$$Lambda$2/122883338@1ddc4ec2 Foo$$Lambda$2/122883338@1ddc4ec2
true Foo$$Lambda$2/122883338@1ddc4ec2 Foo$$Lambda$2/122883338@1ddc4ec2
看看这个article http://www.infoq.com/articles/Java-8-Lambdas-A-Peek-Under-the-Hood关于 lambda 的实现方式。
本质上编译器把你的两个System.nanoTime()
进入类中的以下静态方法:
static Long lambda$1() {
return System.nanoTime();
}
static Long lambda$2() {
return System.nanoTime();
}
然后创建对每个目标类型的常量引用Supplier<Long>
使用LambdaMetaFactory https://docs.oracle.com/javase/8/docs/api/java/lang/invoke/LambdaMetafactory.html。坦率地说,我很失望 Java 编译器没有意识到 lambda 主体是相同的并且只创建一个实例。如果 Java 编译器足够聪明,每一行都应该打印true
!
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)