验证preso中关于java8lambdas性能的语句
请从34英尺到40英尺观看: 它基本上声称,这两者之间存在着显著的性能差异验证preso中关于java8lambdas性能的语句,java,performance,lambda,Java,Performance,Lambda,请从34英尺到40英尺观看: 它基本上声称,这两者之间存在着显著的性能差异 public class _14 { final String pattern; public _14(String pattern) { this.pattern = pattern; } public List<String> allMatchingElements(final List<String> elements) {
public class _14 {
final String pattern;
public _14(String pattern) {
this.pattern = pattern;
}
public List<String> allMatchingElements(final List<String> elements) {
return elements.stream()
.filter(e -> e.contains(pattern))
.collect(toList());
}
}
public class\u 14{
最终字符串模式;
公共14(字符串模式){
这个模式=模式;
}
公共列表所有匹配元素(最终列表元素){
返回元素。stream()
.filter(e->e.contains(模式))
.collect(toList());
}
}
及
public class\u 14{
最终字符串模式;
公共14(字符串模式){
这个模式=模式;
}
公共列表所有匹配元素(最终列表元素){
最终字符串模式=this.pattern;
返回元素。stream()
.filter(e->e.contains(模式))
.collect(toList());
}
}
执行lambda捕获“拥有”lambda的实例(根据presenter为有状态)和lambda捕获局部变量(根据presenter为无状态)之间是否真的存在很大的性能差异
或者,重要的区别只是捕获(实例或局部变量)lambda(有状态)和非捕获lambda(无状态)之间的区别?正如本演示(幻灯片#32)中所述:。您的怀疑是有道理的 lambda表达式的对象是否是无状态的并不取决于目标方法是否为static。更糟糕的是,演示者关注的是一个未指定的、特定于编译器的实现细节 捕获
此
的lambda表达式可以编译为实例方法或静态
方法,该方法接收对象作为参数。AFAIR,早期版本的javac
使用后一种形式,因此使用这样的编译器,您甚至不会在视频中看到这样的代码更改
您可以通过将代码重写为以下内容来模拟这种行为:
public List<String> allMatchingElements(final List<String> elements) {
final _14 arg = this;
return elements.stream()
.filter(e -> e.contains(arg.pattern))
.collect(toList());
}
公开列出所有匹配元素(最终列表元素){
最终_14arg=此;
返回元素。stream()
.filter(e->e.contains(参数模式))
.collect(toList());
}
现在,这个lambda表达式不捕获this
,而是一个局部变量arg
,它包含作为第一个参数传递给合成静态
方法的同一个对象,但是应该很明显,与调用合成实例方法的this
捕获lambda没有区别
因此,在该演示文稿中所做的更改将影响生成的实例是捕获此
实例还是捕获模式
字符串,这不会改变lambda表达式的捕获性质以及当前JRE实现将在每个捕获过程中创建新实例的事实。但是无论如何,对于大多数用例来说,性能影响可以忽略不计
如果可以,您应该避免捕获此
的唯一情况是,假设lambda表达式的实例可能具有更长的生存期,因为捕获此
可能会阻止其垃圾收集
对于该演示的用例中的临时对象,无需担心。在当前实现中,您将使用所示的流操作创建六个临时对象实例,但演示者将重点放在为lambda表达式创建的单个临时实例上,这可能被视为一个具有讽刺意味的转折点
public List<String> allMatchingElements(final List<String> elements) {
final _14 arg = this;
return elements.stream()
.filter(e -> e.contains(arg.pattern))
.collect(toList());
}