代理

代理类型

 Java的代理分为静态代理和动态代理。Java的代理都是基于接口实现的。

静态代理的局限性:只能代理某一类型接口的实例。不能代理任意接口任意方法的操作。

动态代理灵活性很大,在任意时候任意地方都可以使用代理功能,前提是该对象有接口。

 Java 动态代理机制的出现,使得 Java 开发人员不用手工编写代理类,只要简单地指定一组接口及委托类对象,便能动态地获得代理类。代理类会负责将所有的方法调用分派到委托对象上反射执行,在分派执行的过程中,开发人员还可以按需调整委托类对象及其功能,这是一套非常灵活有弹性的代理框架。

1.要了解 Java 动态代理的机制,首先需要了解以下相关的类或接口:

 java.lang.reflect.Proxy:这是 Java 动态代理机制的主类,它提供了一组静态方法来为一组接口动态地生成代理类及其对象。

重点方法:该方法用于为指定类装载器、一组接口及调用处理器生成动态代理类实例

1
static Object newProxyInstance(ClassLoader loader, Class[] interfaces, InvocationHandler h)

java.lang.reflect.InvocationHandler:这是调用处理器接口,它自定义了一个 invoke 方法,用于集中处理在动态代理类对象上的方法调用,通常在该方法中实现对委托类的代理访问。

核心方法

InvocationHandler():该方法用于为指定类装载器、一组接口及调用处理器生成动态代理类实例。该方法负责集中处理动态代理类上的所有方法调用。第一个参数既是代理类实例,第二个参数是被调用的方法对象 第三个参数是调用参数。调用处理器根据这三个参数进行预处理或分派到委托类实例上发射执行。

代码实现动态代理

Test类:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
package com.静态代理;

import com.动态代理.DynamicMapper;

public class Test {

public static void main(String[] args) {
// TODO Auto-generated method stub

//创建被代理对象
StudentMapper sm = new StudentMapper();

//创建被代理对象
UserMapper um = new UserMapper();

//创建代理对象
DynamicMapper staticMapper = new DynamicMapper();

//代理对象不能转成被代理对象,接收的时候,必须用实现的接口进行接收
IMapper im = (IMapper) staticMapper.bindObj(sm);

String val = im.eat("abc");
System.out.println("val:"+val);

}

}

DynamicMapper类:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
package com.动态代理;

import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;

public class DynamicMapper {

// 提供方法为被代理对象进行动然代理,代理完成之后 需要将别代理对象返回
public Object bindObj(Object obj) {

return Proxy.newProxyInstance(obj.getClass().getClassLoader(), obj.getClass().getInterfaces(),
new InvocationHandler() {

@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {

System.out.println("====做饭===");

//回调被代理 对象的业务逻辑,args:目标方法参数信息 result:目标方法返回值
Object result = method.invoke(obj,args);

System.out.println("===收拾===");
return result;
}
});

}

}

StudentMapper类:

1
2
3
4
5
6
7
8
9
10
11
12
package com.静态代理;

public class StudentMapper implements IMapper {

@Override
public String eat(String name) {

System.out.println("===StudentMapper====");
return "StudentMapper--eat";
}

}

IMapper接口:

1
2
3
4
5
6
7
package com.静态代理;

public interface IMapper {

public String eat(String name);

}

-------------本文结束感谢您的阅读-------------