我正在尝试检查使用什么调用动态 http://blog.headius.com/2008/09/first-taste-of-invokedynamic.html
public class HelloWorld {
public static void main(String[] args) {
GreetingLambda lamda=()->System.out.println("Hello");
lamda.greet();
GreetingLambda lamda2=()->System.out.println("Hello");
lamda2.greet();
}
}
interface GreetingLambda{
void greet();
}
相同的字节码
public class HelloWorld {
/* compiled from HelloWorld.java */
/* inner class */
/* public final static Lookup */
public HelloWorld() {
/* L2 */
0 aload_0; /* this */
1 invokespecial 8; /* java.lang.Object() */
4 return;
}
void print(GreetingLambda arg0) {
/* L5 */
0 aload_1; /* l */
1 invokeinterface 16 1; /* void greet() */
/* L6 */
6 return;
}
public static void main(java.lang.String[] args) {
/* L10 */
0 invokedynamic 27; /* GreetingLambda greet() */
3 nop;
4 nop;
5 astore_1; /* lamda */
/* L11 */
6 aload_1; /* lamda */
7 invokeinterface 16 1; /* void greet() */
/* L12 */
12 invokedynamic 28; /* GreetingLambda greet() */
15 nop;
16 nop;
17 astore_2; /* lamda2 */
/* L13 */
18 aload_2; /* lamda2 */
19 invokeinterface 16 1; /* void greet() */
/* L17 */
24 return;
}
private static void lambda$0() {
/* L10 */
0 getstatic 34; /* java.lang.System.out */
3 ldc 40; /* "Hello" */
5 invokevirtual 42; /* void println(java.lang.String arg0) */
8 return;
}
private static void lambda$1() {
/* L12 */
0 getstatic 34; /* java.lang.System.out */
3 ldc 40; /* "Hello" */
5 invokevirtual 42; /* void println(java.lang.String arg0) */
8 return;
}
}
对lambda表达式的调用正在被 invokedynamic 取代。但是我无法理解使用这种方法有什么好处。
它与从下面的代码生成的invokeinterface有什么不同,因为它也在进行运行时检查。
List<String> a = new ArrayList<String>() ;
答案 0 :(得分:2)
对于第一个问题:
简单地说:invokedynamic经过精心设计(因此花了很长时间才能将它变成Java);其中一个副作用是:性能非常高效。
有关详细信息,请参阅here。引自那里:
invokedynamic还通过支持动态更改的呼叫站点目标(动态站点目标,更具体地说,动态呼叫站点是invokedynamic指令)使动态语言实现者受益。此外,由于JVM内部支持invokedynamic,因此JIT编译器可以更好地优化该指令。
所以,长话短说:至少在理论上,当你可以编写使用invokedynamic的代码而不是某些&#34;旧学校&#34;解决同样问题的方法,新的invokedynamic解决方案有一定的机会更快&#34;。如下所示:与创建匿名内部类的旧式方法相比,使用invokedynamic更快,并使用它。
答案 1 :(得分:2)
您引用的同一篇博客还有更多关于jruby优化的文章。例如here,Charles Nutter正在讨论invokedynamic的优点。
简而言之,它是一种优化,它允许jvm缓存和优化本来会混乱的方法句柄查找和间接。另一个优点是生成的代码对热点优化器更友好,这意味着许多使用java字节码的优化现在也适用于使用invokedynamic的jruby和其他jvm语言。
该功能专门添加到jvm以支持动态语言,其中绑定方法句柄的确切代码在运行时才知道(与静态语言不同)。