java动态语言_java动态类型语言支持(三)
invokedynamic指令
在前面java動態類型語言支持(一)(二)中我們有提到invokedynamic指令和java.lang.invoke包中的MethodHandle機制,在某種程度上他們的作用是一樣的,都是為了解決原有4條invoke*指令方法分派規則固話在虛擬機之中的問題,把如何查找目標方法的決定權從虛擬機轉嫁到具體用戶代碼中,讓yoghurt有更高的自由度。
每一處含有invokedynamic指令的位置都稱作“動態調用點”,這條指令的第一個參數不再是代表方法符號引用的CONSTANT_Method_info常量,而是變為JDK新加入的CONSTANT_InvokeDynamic_info常量,從這個新常量中可以得到三項信息:引導方法(Bootstrap Method,此方法存放在新增的BootstrapMethods屬性中)、方法類型(MethodType)和名稱。引導方法是固有的參數,并且返回值是java.lang.invoke.Callsite對象,這個代表真正要執行的目標方法調用。根據CONSTANT_InvokeDynamic_info常量中提供的信息,虛擬機可以找到并執行應到方法,從而獲得一個Callsite對象,最終調用要執行的目標方法。
掌控方法分派規則
invokedynamic指令與前面4條“invoke*”指令最大差別就是他的分派邏輯不是由虛擬機決定的,而是與程序員決定的。我們看如下代碼:
我們思考在TODO處填入適當代碼(不能修改其他地方的代碼)實現調用祖父類的thinking方法。。
在java中我們可以通過super關鍵字很方便的調用到父類中的方法,如果要訪問祖父類的方法在JDK1.7以前我們使用純粹的java語言很難實現這個問題,原因在于Son類的thinking()方法中無法獲取一個實際類型是GrandFather的對象引用,而invokevirtual指令的分派邏輯就是按照方法接收者的實際類型進行分派,這個邏輯是固化在虛擬機中的,程序員無法改變。在JDK1.7以后我們可以使用如下方式解決這個問題,代碼如下:
總結
以上是生活随笔為你收集整理的java动态语言_java动态类型语言支持(三)的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: ​&#820
- 下一篇: java如何解析json_java 中解