初探AOP

大家好,我是IT修真院深圳分院第12期的JAVA学员,一枚正直纯洁善良的java程序员。

今天给大家分享一下,修真院官网Java任务3,深度思考中的知识点—Spring Aop?

1.背景介绍

1、什么是AOP

1)在OOP(面向对象编程)中,正是这种分散在各处且与对象核心功能无关的代码(横切代码)的存在,使得模块复用难度增加。  2)AOP则将封装好的对象剖开,找出其中对多个对象产生影响的公共行为,并将其封装为一个可重用的模块,这个模块被命名为“切面”(Aspect) 3)切面将那些与业务无关,却被业务模块共同调用的逻辑提取并封装起来,减少了系统中的重复代码,降低了模块间的耦合度,同时提高了系统的可维护性、提高了开发的效率和程序的可复用性。      

2、AOP与OOP的区别

1)AOP可以说是OOP(面向对象编程)的补充和完善。OOP引入封装、继承、多态等概念来建立一种对象层次结构,用于模拟公共行为的一个集合。   2)不过OOP允许开发者定义纵向的关系,但并不适合定义横向的关系   3)例如日志功能。日志代码往往横向地散布在所有对象层次中,而与它对应的对象的核心功能毫无关系。对于其他类型的代码,如安全性、异常处理和透明的持续性也都是如此,这种散布在各处的无关的代码被称为横切(cross cutting)。 4)在OOP设计中,它导致了大量代码的重复,而不利于各个模块的重用。 

3、AOP的思想

1) AOP的核心思想是帮助我们在扩展功能(方法)时可以不依靠修改源代码来实现。 2)其采取横向抽取机制,规避了传统面向对象中纵向继承体系的重复性高耦合代码。

2.知识剖析

 1、为什么要使用aop               1)为了方便,用了aop能让你少写很多代码               2)为了更清晰的逻辑,可以让你的业务逻辑去关注自己本身的业务,而不去想一些其他的事情,这些其他的事情包括:安全,事物,日志等。               3)为了降低之前传统面向对象中采用纵向继承体系增强方法导致的耦合度过高的问题:               4)提高了代码的复用性 

2、浅析AOP思想的发展及原理

 发展:修改源代码————采用OOP纵向继承体系————采用AOP横向织入    实现原理:通过动态代理创建代理对象来实现,默认使用Java动态代理来创建AOP代理,当需要代理的类不是代理接口的时候,Spring会切换为使用CGLIB代理  

3、aop专业术语

1.通知(Advice):通知定义了切面是什么以及何时使用;里面就是增强方法的逻辑,分为前置增强,后置增强,环绕增强,最终增强,异常增强。   2.连接点(JoinPoint):连接点是在应用执行过程中能够插入切面的一个点。这个点可以是调用方法时,抛出异常时,甚至修改一个字段时。切面代码可以利用这些点插入到应用的正常流程中,并添加新的行为。  3.切入点(Pointcut)*:切点有助于缩小切面所通知的连接点的范围。(何处)  

4.切面(Aspect)*:切面是通知和切点的结合。通知和切点定义了切面的全部内容——它是什么,在何时何处完成其功能。  5.目标(target):被增强的方法所在的那个类,也就是真正的业务逻辑,他可以在毫不知情的情况下,被织入切面。而自己专注于业务本身的逻辑。  6.代理(proxy):目标类被增强后产生的代理类 

7.织入(weaving):把增强应用到目标类的过程  8:引入(Introduction) 引入允许我们向现有的类添加新方法或属性,从而无需修改这些现有类的情况下,让他们具有新的行为和状态   

4、通知类型介绍

 (1)Before:在目标方法被调用之前做增强处理,@Before只需要指定切入点表达式即可  (2)AfterReturning:在目标方法正常完成后做增强,@AfterReturning除了指定切入点表达式后,还可以指定一个返回值形参名returning,代表目标方法的返回值  (3)AfterThrowing:主要用来处理程序中未处理的异常,@AfterThrowing除了指定切入点表达式后,还可以指定一个throwing的返回值形参名,可以通过该形参名 来访问目标方法中所抛出的异常对象 

   (4)After:在目标方法完成之后做增强,无论目标方法时候成功完成。@After可以指定一个切入点表达式     (5)Around:环绕通知,在目标方法完成前后做增强处理,环绕通知是最重要的通知类型,像事务,日志等都是环绕通知,注意编程中核心是一个ProceedingJoinPoint 

3、常见问题 

1、实现AOP的方式有哪些? 2、实现增强的方法有那些? 3、在确定好需要增强的方法之后,切入点的定位是如何完成的   4、使用@Aspect对SSM进行切入,统计运行时间。  

4.解决方案

            1):实现AOP的方式有哪些?             在sring里面进行aop操作,使用aspectJ(AspectJ是一种扩展Java)来实现。aspectJ本身是一个单独的面向切面的框架,里面定义了AOP语法,不是spring的一部分,和spring协同完成springAOP的操作,使用aspectJ来实现springAOP的操作有两种方式             1:继承的类的方式(不推荐)             2:基于aspectJ的xml文件             3.基于aspectJ注解

 2):实现增强的方法有那些?             织入             引入  

            3):在确定好需要增强的方法之后,切入点的定位是如何完成的              可以用execution表达式来解决(常用)             也可以用xml配置,使用RegexpMethodPointcutAdvisor,来定义切点。             1.execution(* com.aop.add(..))             2.匹配所有save开头的方法:execution(* save*(..))

            4):使用@Aspect对SSM进行切入,统计运行时间。             在编码实战的时候讲讲。

5.编码实战

基于xml配置文件配置

需要创建aop对象,设置切入点、增强类、方法等。

基于注解方式配置文件

 

注意这里尽可能使用闭合标签,不要使用,否则无法正常切入

这里上传一个简单的基于注解方式的aop demo

<pre class="has">
applicationContext.xml

 

  1. xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"

  2. xmlns:context="http://www.springframework.org/schema/context"

  3. xmlns:aop="http://www.springframework.org/schema/aop"

  4. xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd">

UserService.java

 

  1. package anno;

  2.  
  3. import org.springframework.stereotype.Service;

  4.  
  5. @Service

  6. public class UserService {

  7.  
  8. public void add(){

  9. System.out.println("UserService add()");

  10. }

  11.  
  12. public boolean delete(){

  13. System.out.println("UserService delete()");

  14. return true;

  15. }

  16.  
  17. public void edit(){

  18. System.out.println("UserService edit()");

  19. int i = 5/0;

  20. }

  21.  
  22.  
  23. }

Operator.java

 

  1. package anno;

  2.  
  3. import org.aspectj.lang.JoinPoint;

  4. import org.aspectj.lang.ProceedingJoinPoint;

  5. import org.aspectj.lang.annotation.*;

  6. import org.springframework.stereotype.Component;

  7.  
  8.  
  9. @Component

  10. @Aspect

  11. public class Operator {

  12.  
  13. @Pointcut("execution(* anno..*.*(..))")

  14. public void pointCut(){}

  15.  
  16. @Before("pointCut()")

  17. public void doBefore(JoinPoint joinPoint){

  18. System.out.println("AOP Before Advice...");

  19. }

  20.  
  21. @After("pointCut()")

  22. public void doAfter(JoinPoint joinPoint){

  23. System.out.println("AOP After Advice...");

  24. }

  25.  
  26. @AfterReturning(pointcut="pointCut()",returning="returnVal")

  27. public void afterReturn(JoinPoint joinPoint,Object returnVal){

  28. System.out.println("AOP AfterReturning Advice:" + returnVal);

  29. }

  30.  
  31. @AfterThrowing(pointcut="pointCut()",throwing="error")

  32. public void afterThrowing(JoinPoint joinPoint,Throwable error){

  33. System.out.println("AOP AfterThrowing Advice..." + error);

  34. System.out.println("AfterThrowing...");

  35. }

  36.  
  37. @Around("pointCut()")

  38. public void around(ProceedingJoinPoint pjp){

  39. System.out.println("AOP Aronud before...");

  40. try {

  41. pjp.proceed();

  42. } catch (Throwable e) {

  43. e.printStackTrace();

  44. }

  45. System.out.println("AOP Aronud after...");

  46. }

  47.  
  48. }

  49.  
Test.java

 

  1. package anno;

  2.  
  3. import org.springframework.context.ApplicationContext;

  4. import org.springframework.context.support.ClassPathXmlApplicationContext;

  5.  
  6. public class Test {

  7. public static void main(String[] args) {

  8. ApplicationContext ctx = new ClassPathXmlApplicationContext("classpath:applicationContext.xml");

  9. UserService userService = (UserService) ctx.getBean("userService");

  10. userService.add();

  11. }

  12. }

运行结果

扩展思考

  1、 基于注解与基于配置文件的优缺点.             优点:             注解能减少配置的工作,而且配置信息和JAVA代码放在一起,有助于增强程序的内聚性。相对于XML配置文件进行配置文件和程序文件的切换,用注解方式,能提高开发的连贯性,和提成开发效率。             缺点:             程序复杂的话,还是使用xml配置文件的方式,这样可读性和可维护性比较强。

7.    参考文献

8.    更多讨论

  1、 基于注解与基于配置文件的优缺点有哪些?             优点:             注解能减少配置的工作,而且配置信息和JAVA代码放在一起,有助于增强程序的内聚性。相对于XML配置文件进行配置文件和程序文件的切换,用注解方式,能提高开发的连贯性,和提成开发效率。             缺点:             程序复杂的话,还是使用xml配置文件的方式,这样可读性和可维护性比较强。

2、实现AOP的方式有哪些?             在sring里面进行aop操作,使用aspectJ(AspectJ是一种扩展Java)来实现。aspectJ本身是一个单独的面向切面的框架,里面定义了AOP语法,不是spring的一部分,和spring协同完成springAOP的操作,使用aspectJ来实现springAOP的操作有两种方式             1:继承的类的方式(不推荐)             2:基于aspectJ的xml文件             3.基于aspectJ注解

3、实现增强的方法有那些?             织入             引入

两种方式

今天的分享就到这里啦,欢迎大家点赞、转发、留言、拍砖~

技能树.IT修真院“我们相信人人都可以成为一个工程师,现在开始,找个师兄,带你入门,掌控自己学习的节奏,学习的路上不再迷茫”。

这里是技能树.IT修真院,成千上万的师兄在这里找到了自己的学习路线,学习透明化,成长可见化,师兄1对1免费指导。快来与我一起学习吧~我的邀请码:,或者你可以直接点击此链接:

视频地址:

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐


摘要: 原创出处 https://www.bysocket.com 「公众号:泥瓦匠BYSocket 」欢迎关注和转载,保留摘要,谢谢! 目录 连接 连接池产生原因 连接池实现原理 小结 TEMPERANCE:Eat not to dullness;drink not to elevation.节制
摘要: 原创出处 https://www.bysocket.com 「公众号:泥瓦匠BYSocket 」欢迎关注和转载,保留摘要,谢谢! 一个优秀的工程师和一个普通的工程师的区别,不是满天飞的架构图,他的功底体现在所写的每一行代码上。-- 毕玄 1. 命名风格 【书摘】类名用 UpperCamelC
今天犯了个错:“接口变动,伤筋动骨,除非你确定只有你一个人在用”。哪怕只是throw了一个新的Exception。哈哈,这是我犯的错误。一、接口和抽象类类,即一个对象。先抽象类,就是抽象出类的基础部分,即抽象基类(抽象类)。官方定义让人费解,但是记忆方法是也不错的 —包含抽象方法的类叫做抽象类。接口
Writer :BYSocket(泥沙砖瓦浆木匠)微 博:BYSocket豆 瓣:BYSocketFaceBook:BYSocketTwitter :BYSocket一、引子文件,作为常见的数据源。关于操作文件的字节流就是 —FileInputStream&amp;FileOutputStream。
作者:泥沙砖瓦浆木匠网站:http://blog.csdn.net/jeffli1993个人签名:打算起手不凡写出鸿篇巨作的人,往往坚持不了完成第一章节。交流QQ群:【编程之美 365234583】http://qm.qq.com/cgi-bin/qm/qr?k=FhFAoaWwjP29_Aonqz
本文目录 线程与多线程 线程的运行与创建 线程的状态 1 线程与多线程 线程是什么? 线程(Thread)是一个对象(Object)。用来干什么?Java 线程(也称 JVM 线程)是 Java 进程内允许多个同时进行的任务。该进程内并发的任务成为线程(Thread),一个进程里至少一个线程。 Ja
Writer :BYSocket(泥沙砖瓦浆木匠)微 博:BYSocket豆 瓣:BYSocketFaceBook:BYSocketTwitter :BYSocket在面向对象编程中,编程人员应该在意“资源”。比如?1String hello = &quot;hello&quot;; 在代码中,我们
摘要: 原创出处 https://www.bysocket.com 「公众号:泥瓦匠BYSocket 」欢迎关注和转载,保留摘要,谢谢! 这是泥瓦匠的第103篇原创 《程序兵法:Java String 源码的排序算法(一)》 文章工程:* JDK 1.8* 工程名:algorithm-core-le
摘要: 原创出处 https://www.bysocket.com 「公众号:泥瓦匠BYSocket 」欢迎关注和转载,保留摘要,谢谢! 目录 一、父子类变量名相同会咋样? 有个小故事,今天群里面有个人问下面如图输出什么? 我回答:60。但这是错的,答案结果是 40 。我知错能改,然后说了下父子类变
作者:泥瓦匠 出处:https://www.bysocket.com/2021-10-26/mac-create-files-from-the-root-directory.html Mac 操作系统挺适合开发者进行写代码,最近碰到了一个问题,问题是如何在 macOS 根目录创建文件夹。不同的 ma
作者:李强强上一篇,泥瓦匠基础地讲了下Java I/O : Bit Operation 位运算。这一讲,泥瓦匠带你走进Java中的进制详解。一、引子在Java世界里,99%的工作都是处理这高层。那么二进制,字节码这些会在哪里用到呢?自问自答:在跨平台的时候,就凸显神功了。比如说文件读写,数据通信,还
1 线程中断 1.1 什么是线程中断? 线程中断是线程的标志位属性。而不是真正终止线程,和线程的状态无关。线程中断过程表示一个运行中的线程,通过其他线程调用了该线程的 方法,使得该线程中断标志位属性改变。 深入思考下,线程中断不是去中断了线程,恰恰是用来通知该线程应该被中断了。具体是一个标志位属性,
Writer:BYSocket(泥沙砖瓦浆木匠)微博:BYSocket豆瓣:BYSocketReprint it anywhere u want需求 项目在设计表的时候,要处理并发多的一些数据,类似订单号不能重复,要保持唯一。原本以为来个时间戳,精确到毫秒应该不错了。后来觉得是错了,测试环境下很多一
纯技术交流群 每日推荐 - 技术干货推送 跟着泥瓦匠,一起问答交流 扫一扫,我邀请你入群 纯技术交流群 每日推荐 - 技术干货推送 跟着泥瓦匠,一起问答交流 扫一扫,我邀请你入群 加微信:bysocket01
Writer:BYSocket(泥沙砖瓦浆木匠)微博:BYSocket豆瓣:BYSocketReprint it anywhere u want.文章Points:1、介绍RESTful架构风格2、Spring配置CXF3、三层初设计,实现WebService接口层4、撰写HTTPClient 客户
Writer :BYSocket(泥沙砖瓦浆木匠)什么是回调?今天傻傻地截了张图问了下,然后被陈大牛回答道“就一个回调…”。此时千万个草泥马飞奔而过(逃哈哈,看着源码,享受着这种回调在代码上的作用,真是美哉。不妨总结总结。一、什么是回调回调,回调。要先有调用,才有调用者和被调用者之间的回调。所以在百
Writer :BYSocket(泥沙砖瓦浆木匠)一、什么大小端?大小端在计算机业界,Endian表示数据在存储器中的存放顺序。百度百科如下叙述之:大端模式,是指数据的高字节保存在内存的低地址中,而数据的低字节保存在内存的高地址中,这样的存储模式有点儿类似于把数据当作字符串顺序处理:地址由小向大增加
What is a programming language? Before introducing compilation and decompilation, let&#39;s briefly introduce the Programming Language. Programming la
Writer :BYSocket(泥沙砖瓦浆木匠)微 博:BYSocket豆 瓣:BYSocketFaceBook:BYSocketTwitter :BYSocket泥瓦匠喜欢Java,文章总是扯扯Java。 I/O 基础,就是二进制,也就是Bit。一、Bit与二进制什么是Bit(位)呢?位是CPU
Writer:BYSocket(泥沙砖瓦浆木匠)微博:BYSocket豆瓣:BYSocket一、前言 泥瓦匠最近被项目搞的天昏地暗。发现有些要给自己一些目标,关于技术的目标:专注很重要。专注Java 基础 + H5(学习) 其他操作系统,算法,数据结构当成课外书博览。有时候,就是那样你越是专注方面越