日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

使用cglib创建代理对象

發(fā)布時間:2023/12/3 编程问答 21 豆豆
生活随笔 收集整理的這篇文章主要介紹了 使用cglib创建代理对象 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

在上一篇文章中,我討論了基于標(biāo)準(zhǔn)Java的代理對象。 當(dāng)您要在實現(xiàn)接口的對象上具有方法調(diào)用處理程序時,可以使用這些方法。 Java反射代理的創(chuàng)建要求您具有一個實現(xiàn)接口的對象。 我們要代理的對象已經(jīng)失控,它沒有實現(xiàn)我們要從處理程序調(diào)用的接口,而我們?nèi)匀幌M麚碛写怼?

什么時候需要不帶接口的對象的代理?

這是很常見的情況。 如果有的話,我們有一個JPA實現(xiàn),例如Hibernate,它實現(xiàn)了記錄的延遲加載。 例如,審核日志記錄存儲在一個表中,并且每個記錄(第一個記錄除外)都引用了上一項。 就像是

class LinkedAuditLogRecord {LinkedAuditLogRecord previous;AuditLogRecord actualRecord; }

通過JPA加載記錄將返回一個對象LinkedAuditLogRecord ,該對象包含以前的記錄作為對象,依此類推,直到第一個在名為previos的字段中可能為null記錄為止。 (這不是實際的代碼。)任何JPA實現(xiàn)從一開始就抓取并加載整個表到我們感興趣的記錄都是一個非常糟糕的實現(xiàn)。 相反,持久層僅加載實際記錄,并創(chuàng)建一個擴展LinkedAuditLogRecord的代理對象,而這就是previous字段的內(nèi)容。 實際字段通常是私有字段,如果我們的代碼嘗試訪問上一條記錄,則代理對象將在該時間加載它。 簡而言之,這是延遲加載。

但是,JPA實現(xiàn)如何為未實現(xiàn)接口的類的對象創(chuàng)建代理? Java反射代理實現(xiàn)無法做到這一點,因此JPA實現(xiàn)使用了不同的東西。 他們通常使用的是cglib。

什么是cglib

Cglib是一個開放源代碼庫,能夠在Java運行時創(chuàng)建和加載內(nèi)存中的類文件。 為此,它使用Java字節(jié)碼生成庫'asm',這是一個非常低級的字節(jié)碼創(chuàng)建工具。 我不會在本文中深入探討。

如何使用cglib

使用cglib創(chuàng)建代理對象幾乎與使用JDK反射代理API一樣簡單。 我使用cglib創(chuàng)建了與上周文章相同的代碼:

package proxy;import net.sf.cglib.proxy.Enhancer; import net.sf.cglib.proxy.MethodInterceptor; import net.sf.cglib.proxy.MethodProxy;import java.lang.reflect.Method;public class CglibProxyDemo {static class Original {public void originalMethod(String s) {System.out.println(s);}}static class Handler implements MethodInterceptor {private final Original original;public Handler(Original original) {this.original = original;}public Object intercept(Object o, Method method, Object[] args, MethodProxy methodProxy) throws Throwable {System.out.println("BEFORE");method.invoke(original, args);System.out.println("AFTER");return null;}}public static void main(String[] args){Original original = new Original();MethodInterceptor handler = new Handler(original);Original f = (Original) Enhancer.create(Original.class,handler);f.originalMethod("Hallo");} }

區(qū)別在于類的名稱略有不同,并且我們沒有接口。

代理類擴展原始類也很重要,因此在創(chuàng)建代理對象時,它將調(diào)用原始類的構(gòu)造函數(shù)。 如果這是資源匱乏的話,我們可能會有一些問題。 但是,這是我們不能回避的事情。 如果我們想為一個已經(jīng)存在的類提供一個代理對象,那么我們應(yīng)該有一個接口,或者我們必須擴展原始類,否則我們就不能使用代理對象代替原始類。

翻譯自: https://www.javacodegeeks.com/2016/01/creating-proxy-object-using-cglib.html

總結(jié)

以上是生活随笔為你收集整理的使用cglib创建代理对象的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。