java中使用cglib和asm實現基於子類(java簡單類)實現的動態代理實例+基於接口實現動態代理

動態代理的作用:在不改變源碼的情況下增強方法;
舉個例子,在進行簡單的jdbc操作的時候,你想做到每執行一次sql語句就打印一句話,作爲日誌.
說明:本例子是基於子類(任何一個java普通類)的動態代理,(當然也有基於接口的動態代理模式了)[點擊這裏連接到](https://blog.csdn.net/weixin_45127611/article/details/104523192);
首先定義簡單類,定義一個簡單的功能吧:
public class Producter{
	@Override
	public Float saleProduct(Float money) {
		System.out.println("賣了"+money);
		return money;
	}
	}

好,類出來了,現在給你出個問題,你怎麼能夠在不改變源碼的情況下,讓每次執行這個方法之前打印一行字,或者是改變money參數的倍數等簡單操作??
這些問題用JDK官方提供的 Proxy 類,就沒有辦法解決了,因爲這個java類沒有實現任何的接口,只是一個java的簡單類;但是這也是有辦法增強的,不過要用到三方jar包(cglib和asm)少一不可
在這裏插入圖片描述
接下來是類代碼:

public class TestCglib {
	//要代理的對象
		private static IProduct target = new ProductImpl();
		
		public TestCglib(IProduct target){
			this.target = target;
		}
		
		
		public IProduct getlLoggingProxy(){
			IProduct proxy = null;
			//代理對象由哪一個類加載器負責加載
			Class loader = target.getClass();
			//代理對象的類型,即其中有哪些方法
			MethodInterceptor met = new MethodInterceptor() {
				@Override
				public Object intercept(Object arg0, Method arg1, Object[] arg2, MethodProxy arg3) throws Throwable {
					Object returnValue = null;
					if("saleProduct".equals(arg1.getName())) {
						Float money = (float) (0.8*(Float)arg2[0]);
						returnValue = arg1.invoke(target, money);
					}
					return returnValue;
				}
			};
			return proxy = (IProduct)Enhancer.create(loader,met);
		}
		
			public static void main(String[] args) {
				TestCglib tc = new TestCglib(new ProductImpl());
				IProduct pr = tc.getlLoggingProxy();
				pr.saleProduct(1000f);
				/*
				IProduct proxy = (IProduct)Enhancer.create(target.getClass(),
						new MethodInterceptor() {
					@Override
					public Object intercept(Object arg0, Method arg1, Object[] arg2, MethodProxy arg3) throws Throwable {
						Object returnValue = null;
						if("saleProduct".equals(arg1.getName())) {
							Float money = (float) (0.8*(Float)arg2[0]);
							returnValue = arg1.invoke(target, money);
						}
						return returnValue;
					}
				});
				proxy.saleProduct(1000f);
				*/
			}
		
}

兩種方法運行的結果都是:

賣了800.0

寫到最後:用這種方式的(基於子類的動態代理)中,無需被代理類有什麼特殊的要求只需要是一個java的簡單類就行了,然後用到了這個類的生命;

還有一種基於接口的動態代理:jdk自帶的動態代理
https://blog.csdn.net/weixin_45127611/article/details/104523192

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章