代理模式
- 定义:
由于某些原因需要给某对象提供一个代理以控制对该对象的访问。这时,访问对象不适合或者不能直接引用目标对象,代理对象作为访问对象和目标对象之间的中介。 - 代理模式就是设置一个中间代理来控制访问原目标对象,可以在原代码逻辑前后增加一些逻辑,以达到增强原对象的功能和简化访问方式。
- 实际应用
我们需要在低层模块中访问高层模块中的对象,这时候无法直接访问到,所有就可以例如代理来实现
静态代理
- 这种代理方式需要代理对象和目标对象实现一样的接口。
- 特点
- 冗余。由于代理对象要实现与目标对象一致的接口,会产生过多的代理类。
- 不易维护。一旦接口增加方法,目标对象与代理对象都要进行修改。
- 静态代理在编译时就已经实现,编译完成后代理类是一个实际的class文件
- 接口
public interface IUserDao {
public void save();
}
public class UserDao implements IUserDao{
@Override
public void save() {
System.out.println("保存数据");
}
}
public class UserDaoProxy implements IUserDao{
private IUserDao target;
public UserDaoProxy(IUserDao target) {
this.target = target;
}
@Override
public void save() {
System.out.println("开启事务");
target.save();
System.out.println("提交事务");
}
}
public class StaticUserProxy {
@Test
public void testStaticProxy(){
IUserDao target = new UserDao();
UserDaoProxy proxy = new UserDaoProxy(target);
proxy.save();
}
}
开启事务
保存数据
提交事务
动态代理
- 利用了JDK API,动态地在内存中构建代理对象,从而实现对目标对象的代理功能。动态代理又被称为JDK代理或接口代理。
- 特点
- 动态代理对象不需要实现接口,但是要求目标对象必须实现接口,否则不能使用动态代理。
- 动态代理是在运行时动态生成的,即编译完成后没有实际的class文件,而是在运行时动态生成类字节码,并加载到JVM中
- 动态代理对象
public class ProxyFactory {
private Object object;
public ProxyFactory(Object object) {
this.object = object;
}
public Object getProxyInstance() {
return Proxy.newProxyInstance(object.getClass().getClassLoader(), object.getClass().getInterfaces(),
(proxy, method, args) -> {
System.out.println("开启事务");
Object returnValue = method.invoke(object,args);
System.out.println("提交事务");
return null;
}
);
}
}
public class TestProxy {
@Test
public void testDynamicProxy (){
IUserDao target = new UserDao();
IUserDao proxy = (IUserDao) new ProxyFactory(target).getProxyInstance();
proxy.save();
}
}
kotlin中的动态代理by
class JumpProxy constructor(provider: IIProvider) : IIProvider by provider
JumpProxy(JumpProvider()).gotoMainActivity()
参考资料