java动态代理_Java动态代理
java動態代理
代理是一種設計模式。 當我們想添加或修改現有類的某些功能時,我們創建并使用代理對象。 使用代理對象而不是原始對象。 通常,代理對象具有與原始對象相同的方法,并且在Java代理類中,通常會extend原始類。 代理具有原始對象的句柄,并可以在該對象上調用方法。
這樣,代理類可以以便捷的方式實現許多事情:
- 在方法開始和停止時記錄
- 對參數進行額外檢查
- 嘲笑原始類的行為
- 實現對昂貴資源的懶惰訪問
無需修改該類的原始代碼。 (以上列表并不廣泛,僅是示例。)
在實際應用中,代理類不會直接實現功能。 遵循單責任原則,代理類僅進行代理,并且實際的行為修改在處理程序中實現。 當調用代理對象而不是原始對象時,代理將決定是否必須調用原始方法或某些處理程序。 處理程序可以執行其任務,也可以調用原始方法。
即使代理模式不僅適用于在運行時創建代理對象和代理Cass的情況,但這在Java中也是一個特別有趣的話題。 在本文中,我將重點介紹這些代理。
這是一個高級主題,因為它需要使用反射類,或者字節代碼操作或編譯動態生成的Java代碼。 或所有這些。 要使新類在運行時還不能用作字節碼,將需要生成字節碼,并需要一個用于加載字節碼的類加載器。 要創建字節碼,可以使用cglib或bytebuddy或內置的Java編譯器。
當我們考慮代理類及其調用的處理程序時,我們可以理解為什么在這種情況下責任分離很重要。 代理類是在運行時生成的,但是可以將代理類調用的處理程序編碼為常規源代碼,并沿著整個程序的代碼進行編譯(編譯時)。
最簡單的方法是使用java.lang.reflect.Proxy類,它是JDK的一部分。 該類可以創建一個代理類或直接創建它的一個實例。 Java內置代理的使用很容易。 您需要做的就是實現一個java.lang.InvocationHandler以便代理對象可以調用它。 InvocationHandler接口非常簡單。 它僅包含一個方法: invoke() 。 invoke() ,參數包含被代理的原始對象,被調用的方法(作為反射Method對象)和原始參數的對象數組。 示例代碼演示了用法:
package proxy;import java.lang.reflect.InvocationHandler; import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; import java.lang.reflect.Proxy;public class JdkProxyDemo {interface If {void originalMethod(String s);}static class Original implements If {public void originalMethod(String s) {System.out.println(s);}}static class Handler implements InvocationHandler {private final If original;public Handler(If original) {this.original = original;}public Object invoke(Object proxy, Method method, Object[] args)throws IllegalAccessException, IllegalArgumentException,InvocationTargetException {System.out.println("BEFORE");method.invoke(original, args);System.out.println("AFTER");return null;}}public static void main(String[] args){Original original = new Original();Handler handler = new Handler(original);If f = (If) Proxy.newProxyInstance(If.class.getClassLoader(),new Class[] { If.class },handler);f.originalMethod("Hallo");}}如果處理程序想要在原始對象上調用原始方法,則它必須有權訪問它。 Java代理實現未提供此功能。 您必須自己在代碼中將此參數傳遞給處理程序實例。 (請注意,有一個通常稱為proxy的對象作為參數傳遞給調用處理程序。這是Java反射動態生成的代理對象,而不是我們要代理的對象。)這樣,您絕對可以使用單獨的對象每個原始類的處理程序對象,或者使用某種共享對象,這些共享對象恰好知道某種方式(如果有任何要調用的方法)來調用哪個原始對象。
作為一種特殊情況,您可以創建一個調用處理程序和一個沒有任何原始對象的接口的代理。 甚至不需要任何類來實現源代碼中的接口。 動態創建的代理類將實現該接口。
如果要代理的類未實現接口,該怎么辦? 在這種情況下,您必須使用其他代理實現。 我們將在下周討論一下。
翻譯自: https://www.javacodegeeks.com/2016/01/java-dynamic-proxy.html
java動態代理
總結
以上是生活随笔為你收集整理的java动态代理_Java动态代理的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 查看linux dns配置(查看linu
- 下一篇: 安卓模拟器助手下载(安卓模拟器助手)