Android中使用Java的动态代理
同事写一个功能的时候,使用了Java的动态代理,虽然我不赞同他在实现那个功能时使用这项技术,但是不能忽略动态代理在Android中的作用的。
比如很多插件化框架就是以动态代理为原理的。Android插件化原理解析——Hook机制之动态代理
所以这里简单介绍下java代理相关的知识。
1.Java的代理模式
【Android中使用Java的动态代理】定义:为其他对象提供一种代理以控制对这个对象的访问说白了就是在一个对象不好修改时,可以通过new一个新的代理对象对他进行控制,并且可以很容易的加入一些新的方法和特性。
Java的代理技术一般分为三种,静态代理、动态代理及Cglib代理。
2.静态代理 静态代理比较简单,看下下面的代码就很好理解了。
//定义一个接口
public interface Interface {
void doSomething();
void somethingElse(String args);
}
//定义一个被代理的类
public class RealObject implements Interface {@Override
public void doSomething() {
System.out.println("doSomething");
}@Override
public void somethingElse(String args) {
System.out.println("somethingElse" + args);
}
}
//新的代理的类
public class SimpleProxy implements Interface {
//被代理的类作为成员变量
private Interface proxied;
//构造方法中传入
public SimpleProxy(Interface proxied) {
this.proxied = proxied;
}//实现接口
@Override
public void doSomething() {
System.out.println("SimpleProxy doSomething");
proxied.doSomething();
}@Override
public void somethingElse(String args) {
System.out.println("SimpleProxy somethingElse" + args);
proxied.somethingElse(args);
}
}
//测试一下
public class SimpleProxyDemo {public static void consumer(Interface iface) {
iface.doSomething();
iface.somethingElse(":jyu");
}public static void main(String[] args) {
consumer(new RealObject());
consumer(new SimpleProxy(new RealObject()));
}
}
输出:
doSomething
somethingElse:jyu
SimpleProxy doSomething
doSomething
SimpleProxy somethingElse:jyu
somethingElse:jyu
动态代理 动态代理也叫做JDK代理、接口代理。不需要实现目标对象的接口。生成代理对象,使用的是Java的API,动态的在内存中构件代理对象(这需要我们指定创建代理对象/目标对象的接口的类型)。
看下下面的例子。还是使用上面的Interface接口,和RealObject类。
//实现InvocationHandler接口
public class DynamicProxyHandler implements InvocationHandler {private Object proxied;
public DynamicProxyHandler(Object proxied) {
this.proxied = proxied;
}//覆写invoke方法
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
System.out.println("*** proxy:"
+ proxy.getClass() + ",\nmethod:"
+ method + ",\nargs:" + args);
if (args != null) {
for (Object arg : args) {
System.out.println("" + arg);
}
}
return method.invoke(proxied, args);
}
}
//测试一下
public class SimpleDynamicProxy {public static void consumer(Interface iface) {
iface.doSomething();
iface.somethingElse(" jyu");
}public static void main(String[] args) {
RealObject real = new RealObject();
consumer(real);
Interface proxy = (Interface) Proxy.newProxyInstance(
Interface.class.getClassLoader(),
new Class[]{Interface.class},
new DynamicProxyHandler(real));
consumer(proxy);
}
}
//输出:
doSomething
somethingElse jyu
*** proxy:class com.sun.proxy.$Proxy0,
method:public abstract void proxy.Interface.doSomething(),
args:null
doSomething
*** proxy:class com.sun.proxy.$Proxy0,
method:public abstract void proxy.Interface.somethingElse(java.lang.String),
args:[Ljava.lang.Object;
@355da254
jyu
somethingElse jyu
PS:《java编程思想》中给咱们留的作业:使用动态代理来编写一个系统以实现事务,其中,代理在被代理的调用执行成功时(不抛出异常)执行提交,而在其执行失败时执行回滚。你的提交和回滚都针对一个外部的文本文件,该文件不在Java异常的控制控制范围之内。你必须注意操作的原子性
3.Cglib代理 cglib在android中是不能使用的,因此咱们这里先不讨论这项技术了。有兴趣的同学可以看看类似的文章。
将cglib动态代理思想带入Android开发
参考资料
- 【Java基础】动态代理实现AOP之控制事务
- java设计模式-代理模式(Proxy)
推荐阅读
- 热闹中的孤独
- android第三方框架(五)ButterKnife
- Shell-Bash变量与运算符
- JS中的各种宽高度定义及其应用
- 2021-02-17|2021-02-17 小儿按摩膻中穴-舒缓咳嗽
- 深入理解Go之generate
- 由浅入深理解AOP
- 异地恋中,逐渐适应一个人到底意味着什么()
- 【译】20个更有效地使用谷歌搜索的技巧
- 我眼中的佛系经纪人