Android AOP简介及AspectJ的应用

3、分层架构如MVP,每一层之间也是纵向关联在一起的。**

一般OOP开发的时候,我们更多关注的是对象Object本身的功能,对象之间的功能和联系往往不会考虑的那么详细。

切面,也叫横向,它所嵌入的地方往往之间并不需要强关联。比如app中各个业务模块之间就属于一种横向的关系。

使用切面的好处:

**1、用标签标注切入点,这里的标签我们使用注解(Annotation)完成,由标签引导完成具体功能;

2、解耦。为什么说解耦呢?用打印Log举例,app中可能存在不同的Log框架来实现。如果同一使用Log标签切入,那么在处理Log标签的地方可以统一Log框架。**

OOP和AOP往往是搭配使用,功能互补。

OOP中散落着各种功能,而AOP则是将涉及到众多模块的某一类功能进行统一管理。

AOP实现方式

=================================================================

1. JDK动态代理

通过实现InvocationHandler接口,可以实现对一个类的动态代理,通过动态代理,我们可以生成代理类从而在代理类方法中,在执行被代理类方法前后,添加自己的实现内容,从而实现Aop。

2. 动态字节码生成

在运行期,目标类加载后,动态构建字节码文件生成目标类的子类,将切面逻辑加入到子类中,没有接口也可以织入,但扩展类的实例方法为final时,则无法进行织入。如:Cglib。

3. 自定义类加载器

在运行期,目标加载前,将切面逻辑加到目标字节码里。如:Javassist。

4. ASM

ASM可以在编译期直接修改编译出的字节码文件,也可以像Javassit一样,在运行期,类文件加载前,去修改字节码。两者的区别在于,一个将所有需要AOP的类都事先修改了,一个在运行时需要才去修改。

5. AspectJ

和ASM一样,Aspectj有静态编译和动态编译的优点,供程序员选择。另外Aspectj其编码更为简洁,是Android开发中,实现AOP的首选。

6. APT

自定义一个AbstractProcessor,在编译期去解析编译的类,并且根据需求生成一个实现了特定接口的子类(代理类),和JDK动态代理不同的是,APT的代理类是在编译期生成的。

Android中的AOP

======================================================================

  1. APT

典型应用:Dagger2、BUtterKnife、ARouter;

  1. AspectJ

功能插入,如日志、权限、埋点等;

  1. Javassist

应用场景:热更新

在这里插入图片描述

AspectJ实现原理

=====================================================================

参考:AspectJ框架实现原理

AspectJ实例

===================================================================

我们实现一个网络状态检测的AOP。

定义annotation:

@Target(ElementType.METHOD)

@Retention(RetentionPolicy.RUNTIME)

public @interface CheckNetwork {

}

切入:

@CheckNetwork()

private void checkNetwork() {

LogUtil.i(“AnnotationFragment”, “检测完毕”);

}

处理切入点:

@Aspect

public class CheckNetworkAspect {

private static final String TAG = CheckNetworkAspect.class.getSimpleName();

/**

  • 找到处理的切点

    • *(…) “**”表示是任意包名 “…”表示任意类型任意多个参数

*/

@Pointcut(“execution(@la.xiong.androidquick.demo.features.function.annotation.aspect.CheckNetwork * *(…))”)

public void executionCheckNetwork() {

}

/**

  • 处理切面

  • @param joinPoint

  • @return

*/

@Around(“executionCheckNetwork()”)

public Object checkPermission(ProceedingJoinPoint joinPoint) throws Throwable {

MethodSignature signature = (MethodSignature) joinPoint.getSignature();

CheckNetwork annotation = signature.getMethod().getAnnotation(CheckNetwork.class);

if (annotation != null) {

Context context = AspectUtils.getContext(joinPoint.getThis());

if (NetworkUtils.isConnected()) {

Toast.makeText(context, “当前网络正常”, Toast.LENGTH_SHORT).show();

} else {

Toast.makeText(context, “此时没有网络连接”, Toast.LENGTH_SHORT).show();

}

return joinPoint.proceed();

}

return null;

}

}

  • 3
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值