Java动态代理

1.首先,什么是代理(中介)

目标对象/被代理对象 ------- 房主:真正有租房子方法的人

代理对象 -------------------- 黑中介:有租房子的方法(负责调用房主的租房子方法)

执行代理对象方法的对象 ---- 租房的人

流程:我们要租房----->中介(租房的方法)------>房主(租房的方法)

抽象:调用对象----->代理对象------>目标对象


使用代理的好处:可以在执行目标对象方法的前后执行自己的加工或其它逻辑。类似黑中介在原租房费上要再加钱,本来目标方法返回值房价是1000,黑中介可以返回值房价+300,就是1300了。


2.动态代理

动态代理:刚刚上图中的代理对象不需要手动编写了,不需要一一编写与目标对象相同的方法,这个过程,在运行时的内存中动态生成代理对象。------字节码对象级别的代理对象

动态代理的API:

在jdk的API中存在一个Proxy中存在一个生成动态代理的的方法newProxyInstance

static Object

newProxyInstance(ClassLoader loader, Class<?>[] interfaces, InvocationHandler h)

返回值:Object就是代理对象

参数:loader:代表与目标对象相同的类加载器-------目标对                                     象.getClass().getClassLoader()

interfaces:代表与目标对象实现的所有的接口字节码对象数组

h:具体的代理的操作,InvocationHandler接口

注意:JDK的Proxy方式实现的动态代理 目标对象必须有接口 没有接口不能实现jdk版动态代理

举个使用的例子:

目标接口:

public interface TargetInterface {

	public void method1();
	public String method2();
	public int method3(int x);
}

目标对象Target.java:

public class Target implements TargetInterface{
	@Override
 public void method1() {
System.out.println("method1 running...");}@Overridepublic String method2() {System.out.println("method2 running...");return "method2";}@Overridepublic int method3(int x) {return x;}}

使用ProxyTest.java:
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;

import org.junit.Test;

public class ProxyTest {

	@Test
	public void test1(){
		//获得动态的代理对象----在运行时 在内存中动态的为Target创建一个虚拟的代理对象
		//objProxy是代理对象 根据参数确定到底是谁的代理对象
		TargetInterface objProxy = (TargetInterface) Proxy.newProxyInstance(
				Target.class.getClassLoader(), //与目标对象相同的类加载器
				new Class[]{TargetInterface.class}, //接口
				new InvocationHandler() {
					//invoke 代表的是执行代理对象的方法
					@Override
					//method:代表目标对象的方法字节码对象
					//args:代表目标对象的响应的方法的参数
					public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
						System.out.println("目标方法前的逻辑");
						//执行目标对象的方法
						Object invoke = method.invoke(new Target(), args);
						System.out.println("目标方法后的逻辑");
						return invoke;
					}
				}
			);
		
		objProxy.method1();
		String method2 = objProxy.method2();
		System.out.println(method2);
		
	}
	
}


原文地址:https://www.cnblogs.com/chz-blogs/p/9380930.html