概述

Spring通过以下策略降低Java开发复杂性

  • 基于POJO的轻量级和最小侵入性编程;

    • 侵入式让用户代码产生对框架的依赖,这些代码不能在框架外使用,不利于代码的复用。但侵入式可以使用户跟框架更好的结合,更容易更充分的利用框架提供的功能。
    • 非侵入式的代码则没有过多的依赖,可以很方便的迁移到其他地方。但是与用户代码互动的方式可能就比较复杂。
  • 通过依赖注入(DI)和面向接口实现松耦合;
  • 基于切面和惯例进行声明式编程;
  • 通过面向切面(AOP)和模板减少样板式代码。

传统开发

依赖
A: new B
B类
var student = new Student();
student.setName("比尔");
student.setAge(15);
student.setId(27);

简化Java开发

不再依赖
交给容器new
递给A
A
B类
IoC容器

依赖注入

使用DI,代码会变得异常简单且易理解和测试。在传统的开发中,需要调用对象时,通常由调用者来创建被调用者的实例,即对象是由调用者主动new出来的;在spring中,则交给IoC容器new,这个控制指的就是对象的new过程。

自动注入

@Component
public class CDPlayer implements MediaPlayer{private CompactDisc compactDisc;@Autowired  // 依赖注入@BlankCDpublic void setCompactDisc(CompactDisc compactDisc) {this.compactDisc = compactDisc;}@Autowired. // 依赖注入@BlankCDpublic CDPlayer(CompactDisc compactDisc) {this.compactDisc = compactDisc;}public void play() { compactDisc.play();}
}

装配(wiring)

创建应用组建之间协作的行为称为装配。Spring通过它的配置,能够了解这些组成部分是如何装配起来的,从而在不修改所依赖的类的情况下,修改依赖关系。

XML文件装配

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"><bean id="knight" class="com.bill.knights.BraveKnight"><constructor-arg ref="quest"/></bean><bean id="quest" class="com.bill.knights.SlayDragonQuest"><constructor-arg ref="fakePrintStream"/></bean><!--PrintStream的实例。--><bean id="fakePrintStream" class="com.bill.knights.FakePrintStream" /><bean id="minstrel" class="com.bill.knights.Minstrel"><constructor-arg value="#{T(System).out}"/></bean></beans>
优点:
把类与类之间松解偶;修改方便;容易扩展
容易和其他系统进行数据交互
对象之间的关系一目了然
缺点:
配置冗长,需要额外维护;影响开发效率
类型不安全,校验不出来,出错不好排查
注解简单概括:写起来比较简单、方便,看起来也简洁,但是修改麻烦

Xml配置概括:写起来比较灵活、修改方便,但是写和维护麻烦

Java文件装配(注解)

/*** 当你使用注解配置时,该类用来装配组件。*/
@Configuration
public class KnightConfig {  @Beanpublic Knight knight() { return new BraveKnight(quest());}@Beanpublic Quest quest() { return new SlayDragonQuest(System.out);}
}
优点:
简化配置
使用起来直观且容易,提升开发的效率
类型安全,容易检测出问题
缺点:
修改起来比xml麻烦
如果不项目不了解,可能给开发和维护带来麻烦

应用切面(AOP)

先来看一下一个低内聚的代码:

public class BraveKnight implements Knight {private Quest quest;// 关联 服务类,这是一个关注点对象private Minstrel minstrel;public BraveKnight(Quest quest, Minstrel minstrel) {this.quest = quest;// 需要初始化一个关注点组件this.minstrel = minstrel;}public voi embarkOnQuest() throws QuestException {// 过于低内聚!minstrel.singBeforeQuest();quest.embark();minstrel.singAfterQuest();}
}
  1. 面向切面编程被定义为 促使软件系统实现关注点分离 的一项技术;
  2. 例如日志、事务管理和安全这样的系统服务经常融入到自身具有核心业务逻辑的组件中去,这些系统服务通常被称为 横切关注点 ,因为它们会跨越系统的多个组件;
  3. 关注点的调用往往散部到各个模块中,但这些关注点不是模块的核心业务。降低了代码的内聚性,增加了耦合度;
  4. AOP能够使关注点模块化,以声明的方式将它们应用到它们需要影响的组件中去,从而使被影响的组件有更高的内聚性;
  5. 借助AOP,使用各种功能层去包裹核心业务层。

使用XML声明一个切面

        <aop:config><aop:aspect ref="minstrel"><!--将表达式里的执行语句命名为id,令其为切入点--><aop:pointcut id="embark" expression="execution(* *.embarkOnQuest(..))"/><aop:before pointcut-ref="embark" method="singBeforeQuest"/><aop:after pointcut-ref="embark" method="singAfterQuest"/></aop:aspect></aop:config>

使用注解声明切面

开启代理类

@Configuration
@EnableAspectJAutoProxy(proxyTargetClass = true)
@ComponentScan(basePackageClasses = Performance.class)
public class ConcertConfig {//    @Bean
//    public AudienceAround audience() {//        return new AudienceAround();
//    }}

通过切面,在原有方法上引入新的功能

/*** 重写Audience,这次使用Around建言,切点表达式开头的*表示* 任意返回类型,然后是类路径,括号里是参数类型。* @author Bill Ludwig; 2020/4/23 10:29*/
@Aspect
@Component
public class AudienceAround {/*** 一个切面方法。该注解能够在一个@AspectJ切面内定义可重用的切点*/@Pointcut("execution(* com.bill.concert.Performance.perform(..))")public void action() {}/*** 一个通知/建言方法。通过Around把通知集中在一个代码块内* @param jp 通过该对象调用被通知的方法* @return 应该是返回调用被通知方法后返回的结果*/@Around("action()")public Object watchPerformance(ProceedingJoinPoint jp){try {System.out.println("Silencing cell phones");System.out.println("Taking seats");jp.proceed();System.out.println("CLAP CLAP CLAP!");} catch (Throwable e) {System.out.println("Demanding a refund!");}return jp;}
}

通过切面,给对象引入新的功能

/*** 切面类。该注解的value属性指定了哪种类型的bean要引入该接口;* defaultImpl属性指定了为引入功能提供实现的类;而注解标注* 的静态属性指明了要引入的接口* @author Bill Ludwig; 2020/4/23 17:26*/
@Aspect
@Component
public class EncoreIntroducer {@DeclareParents(value = "com.bill.concert.Performance+",defaultImpl = DefaultEncoreable.class)public static Encoreable encoreable;}
/*** 一个为引入功能提供实现的类。即实现了Encoreable接口* @author Bill Ludwig; 2020/4/23 17:50*/
public class DefaultEncoreable implements Encoreable {@Overridepublic void performEncore() {System.out.println("Performing an encore!");}
}
/*** 测试AOP引入* @author Bill Ludwig; 2020/4/23 20:38*/
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(classes = {ConcertConfig.class})
public class ConcertShowTest {@AutowiredConcertShow concertShow;/*** 测试。concertShow没有实现Encoreable接口* 但却可以使用Encoreable的方法。*/@Testpublic void playShow() {concertShow.perform();((Encoreable) concertShow).performEncore();}
}

笔记:Spring基础相关推荐

  1. 实习笔记 —— Spring基础

    系列文章目录 文章目录 系列文章目录 一.MVC开发模式 1. SSM框架应用图: 二.Spring 1.Spring框架简介 2.STS工具的使用 3.IOC控制反转 一.MVC开发模式 是当下主流 ...

  2. 【Spring 基础注解】对象创建相关注解、注入相关注解、注解扫描详解

    Spring 基础注解(2.x) 注解基础概念 注解的作用 Spring 注解的发展历程 对象创建相关注解 @Component @Repository.@Service.@Contoller @Sc ...

  3. Spring家族-spring基础知识

    看了一段时间视频教程,还是需要总结一下,不然很容易忘的,笔记如下. 一.基本概念 1.三大框架SSM:Spring.SpringMvc.Mybaits,现在用的比较多是springboot 2.程序间 ...

  4. Spring基础专题——第十一章(高级注解编程完结)

    前言:去年到现在一直没有很好的时间完成这个spring基础+源码的博客目标,去年一年比较懒吧,所以今年我希望我的知识可以分享给正在奋斗中的互联网开发人员,以及未来想往架构师上走的道友们我们一起进步,从 ...

  5. Spring基础专题——第七章(持久层整合)

    前言:去年到现在一直没有很好的时间完成这个spring基础+源码的博客目标,去年一年比较懒吧,所以今年我希望我的知识可以分享给正在奋斗中的互联网开发人员,以及未来想往架构师上走的道友们我们一起进步,从 ...

  6. Spring基础专题——第六章(Aop编程)

    前言:去年到现在一直没有很好的时间完成这个spring基础+源码的博客目标,去年一年比较懒吧,所以今年我希望我的知识可以分享给正在奋斗中的互联网开发人员,以及未来想往架构师上走的道友们我们一起进步,从 ...

  7. Spring基础专题——第五章(Aop代理)

    前言:去年到现在一直没有很好的时间完成这个spring基础+源码的博客目标,去年一年比较懒吧,所以今年我希望我的知识可以分享给正在奋斗中的互联网开发人员,以及未来想往架构师上走的道友们我们一起进步,从 ...

  8. Spring基础专题——第三章(反转控制与依赖注入)

    前言:去年到现在一直没有很好的时间完成这个spring基础+源码的博客目标,去年一年比较懒吧,所以今年我希望我的知识可以分享给正在奋斗中的互联网开发人员,以及未来想往架构师上走的道友们我们一起进步,从 ...

  9. Spring基础专题——第二章(注入Injection)

    前言:去年到现在一直没有很好的时间完成这个spring基础+源码的博客目标,去年一年比较懒吧,所以今年我希望我的知识可以分享给正在奋斗中的互联网开发人员,以及未来想往架构师上走的道友们我们一起进步,从 ...

  10. Spring基础专题——第一章(第一个Spring程序)

    前言:去年到现在一直没有很好的时间完成这个spring基础+源码的博客目标,去年一年比较懒吧,所以今年我希望我的知识可以分享给正在奋斗中的互联网开发人员,以及未来想往架构师上走的道友们我们一起进步,从 ...

最新文章

  1. “低端市场”?一线业务员这样看
  2. mysql十分钟分组_MYSQL每隔10分钟进行分组统计的实现方法
  3. 九、Node.js中文乱码问题
  4. Docker shipyard 试用
  5. OPA 7 - opaTest
  6. C# 客户端HTTP通信
  7. java 优化 寄存器_JVM性能优化系列-(6) 晚期编译优化
  8. oracle 挖掘日志,Oracle 日志挖掘(LogMiner)使用详解
  9. python 示例_带有示例的Python文件关闭属性
  10. VBA GetOpenFilename 方法
  11. Java Bean 命名规则
  12. 在CentOS7上安装vim编辑器报错无法解析阿里云主机
  13. 小程序文章怎么导出来_宠物小程序怎么进行盈利
  14. 第四天作业发布时间:2021-05-31 09:57:49相关课程:RHCSA2021-05-22 
  15. 0CTF-babyheap2017祥讲
  16. 百度搜索引擎工作原理解读
  17. 车牌识别算法 matlab,车牌识别算法及其MATLAB实现
  18. 固态硬盘(SSD)原理及相关介绍
  19. 解读CUDA Compiler Driver NVCC - Ch.2 - Compilation Phases
  20. Android源码分析 - Framework层的Binder(客户端篇)

热门文章

  1. 程序员如何写出技术好文?
  2. 海龟交易法则03_海龟的培训
  3. 请广大编程爱好者加入QQ群5907439
  4. 《Vue3+TS》开发一个自己的起始页
  5. 有活着的感觉就有未来————《时生》读后感
  6. Nginx+Tomcat服务器负载均衡实践方案
  7. 【IEEE-CPS出版,往届已检索】第二届计算机图形学、图像与虚拟化研究国际会议(ICCGIV 2022)
  8. 最全4k,8k的高清壁纸网站免费下载
  9. 这有一套完整的微信公众号代运营方案
  10. 无人驾驶不听指挥,交警该怎么办?