简体   繁体   English

invokedynamic和隐式方法

[英]invokedynamic and implicit methods

As I understand from reading this post about the new invokedynamic bytecode instruction in JDK 7, it makes it possible to call methods on the objects which are not statically defined in the object's class and have those method calls be resolved to some concrete static methods in some other class by intercepting the method call target resolution (the post gives an example). 正如我在阅读这篇关于JDK 7中新的invokedynamic字节码指令的帖子所理解的那样,它可以调用对象类中没有静态定义的对象上的方法,并将这些方法调用解析为某些具体的静态方法。其他类通过拦截方法调用目标分辨率(帖子给出一个例子)。

Does this mean that Java 7 classes can have implicit methods like Scala has? 这是否意味着Java 7类可以使用Scala之类的隐式方法? If not how is implicit method resolution in Scala different from the invokedynamic method resolution? 如果不是,Scala中的隐式方法解析与invokedynamic方法解析有何不同?

It is completely unrelated. 这完全不相关。 Implicits in scala are fully resolved at compile time . scala中的Implicits编译时完全解析 The compiler inserts something that you could as well have written yourself. 编译器会插入您自己编写的内容。 If it cannot do that, at compile time, there is an error. 如果它不能这样做,在编译时,就会出错。 InvokeDynamic is about finding the method at runtime and failing at runtime if it cannot be found. InvokeDynamic是在运行时查找方法,如果找不到则在运行时失败。

Specifically, if you write in scala xm() where there is no method m in type x, it will look for an implicit conversion, that is a function, say f, which is in scope (you could call f at this point), which is marked as implicit , which will accept x as a parameter, and whose result type has a method m (there are a lot more details in the rules, but this is the essence). 具体来说,如果你在scala xm()中写入x类型中没有方法m,它将寻找一个隐式转换,即一个函数,比如f,它在范围内(你可以在此时调用f),标记为隐式的 ,它将接受x作为参数,其结果类型具有方法m (规则中有更多细节,但这是本质)。 If it finds such a method, then it will replace xm() by the properly typed f(x).m() . 如果找到这样的方法,那么它将用正确类型的f(x).m()替换xm() f(x).m() It could just as well have been written that way in the code, and it would have to in java. 它也可以在代码中以这种方式编写,并且必须在java中编写。 If no such function f can be found, then there is a compile time error. 如果找不到这样的函数f,则存在编译时错误。

It happens just the same way if you call g(x) and x is not of the right type to be passed to g . 如果你调用g(x)并且x不是要传递给g的正确类型,它的发生方式也是一样的。 If there is a function f such that f(x) has the proper type, then it will replace the code by g(f(x)) . 如果有一个函数f使得f(x)具有正确的类型,那么它将用g(f(x))代替代码。 Again, you could have written that yourself in plain scala, and again, if there is no such method, it will not compile. 再一次,你可以用普通的scala写自己,再说一次,如果没有这样的方法,它就不会编译。

Dynamic is about not worrying too much at compile time whether there is an m method in x , and looking for one at runtime. 动态是在编译时不要过于担心x是否有m方法,并且在运行时查找一个方法。 This is how a dynamic language like JRuby or Groovy typically works. 这就像JRuby或Groovy这样的动态语言通常如何工作。 There is something related in scala, trait Dynamic (marked experimental). scala中有一些相关的东西,特性动态(标记实验)。

The invokedynamic bytecode will help speed up dynamic languages on the JVM. invokedynamic字节码将有助于加速JVM上的动态语言。 It will also speed up accesses to structural types in Scala. 它还将加速对Scala中结构类型的访问。 The alternative to invokedynamic (and only option prior to JDK 7) is reflection, which is really slow. invokedynamic(以及JDK 7之前的唯一选项)的替代方法是反射,这非常慢。

Java-the-language is statically typed, and doesn't have features that use invokedynamic (apart from explicit reflective method calls using java.lang.invoke.MethodHandle , according to this question ). Java-the-language是静态类型的,并且没有使用invokedynamic的功能(除了使用java.lang.invoke.MethodHandle的显式反射方法调用,根据这个问题 )。

Scala implicits are actually statically resolved, and thus unrelated to invokedynamic. Scala implicits实际上是静态解析的,因此与invokedynamic无关。 For details about how it works, see Daniel Sobral's excellent expose: Where does Scala look for implicits? 有关它如何工作的详细信息,请参阅Daniel Sobral的优秀曝光: Scala在哪里寻找暗示?

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM