(1):控制反转,把对象的创建和对象之间的调用过程,交给Spring进行管理
(2):使用IOC目的:为了降低耦合度
(3):使用入门案例就是IOC实现
package demo_01;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
public class SpringTest {
public SpringTest() {
System.out.println("我被创建了");
}
public static void main(String[] args) {
//1.加载spring配置文件
ApplicationContext context = new ClassPathXmlApplicationContext("Test.xml");
//2.获取配置创建对象
SpringTest text = context.getBean("text", SpringTest.class);
System.out.println(text.toString());
}
}
2.IOC底层原理
(1):xml解析、工厂模式、反射
IOC(接口)1.IOC思想基于IOC容器完成,IOC容器底层就是对象工厂模式
2.Spring提供IOC容器实现两种方式
(1).BeanFactory:IOC容器基本实现,是Springnn内部的使用接口,不提供开发人员进行使用
(可以使用,但一般不使用) 特点:加载配置文件时候不会创建对象,在获取对象(使用)对象的时候才去创建对象
(2) ApplicationContext:BeanFactory接口的子接口,提供更多强大的功能,一般由开发人员进行使用
*加载配置文件时候就会把在配置文件中配置的对象进行创建
3.ApplicationContext接口的实现类
第一个是:文件在你系统下的盘里的具体路径
第二个是:文件在你类src下的具体路径
IOC操作Bean管理 1.什么是Bean管理?bean管理指的是两个操作
1.Spring创建对象
2.Spring注入属性
2.Bean管理操作由两种方式1.基于xml配置文件方式实现
2.基于注解方式实现
IOC操作管理Bean(基于xml方式)1.基于xml方式创建对象
1.1.在Spring配置文件中,使用bean标签,标签里面添加对应的属性值就可以实现对象的创建
1.2.在bean标签中由许多属性,
id属性:唯一表示,它既不是对象名字,也不是类名,而是别名,可以随便取,通过这个id值找到对象,不可以加特殊符号
name属性:与id属性一样 不过可以加特殊符号
class属性:类的全路径
1.3。创建对象时候,默认页是执行无参数构造器完成对象的创建
2.基于xml方式注入属性
2.1 DI:依赖注入,就是注入属性
DI与IOC的区别:DI是ioc中的一种具体实现,它表示注入属性,但是它在创建完对象的基础之上完成
3.第一种注入方式:使用set方法进行注入3.1.创建类,定义属性和对应set方法
在Spring配置文件配置对象创建并注入属性
4.第二种注入方式:使用有参数构造器进行注入
4.1. 创建类,定义属性。创建属性和对应的有参构造器
在Spring中xml中的配置
5.第三种使用P名称空间注入属性(了解)5.1.使用p名称空间注入,可以简化基于xml配置方式
第一步:添加p名称空间在配置文件中
第二步:进行属性主语,在bean标签中操作
IOC操作Bean管理(xml注入其他类型的属性)1. 字面量:向属性中注入固定的内容 这个内容就叫字面量
1.1: 设置null值
注入特殊字符
1.可以使用 < %gt;
2.把带有特殊符号的内容卸载CDATA中
2.注入外部Bean(比如通过Service去调用Dao中的结构)简单说就是:在一个类中创建另一个类的对象
结果
3.注入属性-内部bean和级联赋值1.一对多关系
2.在实体类直接表示一对多关系,员工表示所属部门,使用对象类型属性进行表示
级联赋值:是在一个bean对象中注入另一个bean对象(外部bean)的属性并对该属性进行赋值。
内部注入: 在一个对象的内部注入另外一个对象 级联赋值:是在一个bean对象中注入另一个bean对象(外部bean)的属性并对该属性进行赋值。也可以理解为,对属性的属性进行赋值
第一种方式:
第二种方式:
必须要保证dept这个对象在emp类中有对应的get方法 否则报错
IOC操作Bean管理(xml注入集合属性)1.注入数组类型属性
2.注入List集合类型属性
3.注入Map集合类型属性
Spring中XML配置
4.在集合里面设置对象类型值
Book类:
5.把集合注入部分提取处理
提取map例子 list则是
IOC操作Bean管理(FactoryBean)
1.Spring 有两种类型bean,一种普通Bean,另一种是工厂Bean(FactoryBean)
1.1:普通bean:在配置文件中定义bean类型救是返回类型
1.2:工厂bean:在配置文件定义bean类型可以和返回类型不一样
第一步 创建类,让这个类作为工厂Bean,实现接口 FactoryBean
第二步 实现接口里面的方法,在实现的方法中定义返回的bean类型
IOC操作Bean管理(bean作用域)
如何设置单实例还是多实例:
1.在Spring里面,设置创建bean实例是单实例还是多实例
2.在Spring 里面,默认情况下,bean是单实例对象
默认情况:singleton
在方法中重复获取:
地址一样表示为单例模式:
3.如何设置单实例还是多实例
1.在spring配置文件bean标签里面有属性(scope)用于设置单实例还是多实例
2.scope属性值
第一个值 默认值,singleton,表示是单实例对象
第二个值 prototype,表示是多实例对象
prototype:
3.singleton和prototype区别
第一:sinleton 单实例,prototype 多实例
第二:设置scope值是sinleton的时候,加载spring配置文件的时候就会创建单实例对象
设置scope值是prototype的时候,不是在加载spring配置文件的时候就创建对象,在调用getBean方法时候创建多实例对象
request值:当scope值是request时,每次创建对象会放到request域中(不常用)
seesion值:当scope值是seesion时,每次创建对象会放到session域中(不常用)
IOC操作Bean管理(Bean生命周期)1.生命周期:从对象创建到d对象销毁的过程
2.bean生命周期
2.1.通过无参构造器创建对象
2.2.为bean的属性设置值和对其他bean引用(调用set方法)
2.3.调用bean中的初始化方法
2.4bean可以使用了(对象获取到了)
2.5当容器关闭时候,调用bean的销毁方法(需要手动配置销毁的方法)
演示生命周期代码
调用销毁对象的方法后 对象任然可以使用并且可以输出,
证明是在第五步的时候执行销毁对象的操作,否则无对象调用会报空指针异常。
Bean的后置处理,生命周期有7步1.bean生命周期
1.1.通过无参构造器创建对象
1.2.为bean的属性设置值和对其他bean引用(调用set方法)
1.3.把bean实例传递给bean的后置处理器的方法PostprocessBeforInitialization
1.1.调用bean中的初始化方法
1.5.把bean实例传递给bean的后置处理器的方法PostprocessAfterInitialization
1.6.bean可以使用了(对象获取到了)
1.7.当容器关闭时候,调用bean的销毁方法(需要手动配置销毁的方法)
IOC操作Bean管理(xml自动装配)
1.什么是自动装箱(属性名称或者属性类型),Spring自动将配置的属性值进行注入
bean标签属性autowire,配置自动装箱
autowire属性常用两个值
byName根据属性名称注入,注入值bean的id值和类属性名字一样(可配置多个)
byType根据属性类型注入(不可配置多个)
把外部文件注入Spring文件配置:
首先要要映入context名称空间
xmlns:context="http://www.springframework.org/schema/context"
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd"
通过 :
properties文件:
IOC操作Bean管理(基于注解) (1).什么是注解?1.注解是代码特殊标记,格式:@注解名称(属性名称=属性值,属性名称=属性值)
2.使用注解,注解作用在类上面,方法上面,属性上面
3.使用注解目的:简化xml配置
(2). Spring针对Bean管理中创建对象提供注解1.@Component
2.@Service
3.@Controller
4.@Repository
***这四种注解功能是一样的,都可以用来创建bean实例
(3).基于注解方法实现对象创建第一步 引入依赖
第二步 开启组件扫描
1.如果扫描多个包,多个包之间使用逗号隔开,
2. 扫描包上层目录
2.1.先引入名称空间 context
通过Component注解来创建对象:
结果:
(4)扫描配置细节:user-default-filters="false" 表示现在不适用默认filter,自己配置filter,若不写则扫描全部
context:include-filter,设置扫描哪些配置
这段配置指的是去com.atguigu中只扫描用Controller注解
下面配置扫描包所有内容
context:exclude-filter:设置哪些内容不进行扫描 (下面表示扫描除Controller外的 所有注解)
1.@Autowired:根据属性类型进行自动装配
第一步:把service和dao对象创建,在service和dao类添加创建对象注解
第二步:在service注入dao对象,在service类中定义dao对象并在属性上面实现属性注入
2.@Qualifier:根据属性名称进行注入
这个注解的使用,需要和上面@Autowired一起使用
3.@Resource:可以根据属性类型注入,也可以根据名称注入
4.@Value:注入普通类型属性
@Autowired演示Dao
service:
@Qualifier的演示
效果与上面一致,假设故意写错名称:
报错:
@Resource演示
效果与上面一致
@Value注解的演示:
(6)完全注解开发1.创建配置类,替代xml配置文件
Spring中的AOP(面向切面编程) 什么是AOP?
它利用一种称为“横切”的技术,剖解开封装的对象内部,并将那些影响了多个类的公共行为封装到一个可重用模块,并将其名为“Aspect”,即方面。AOP把软件系统分为两个部分:核心关注点和横切关注点。业务处理的主要流程是核心关注点,与之关系不大的部分是横切关注点。横切关注点的一个特点是,他们经常发生在核心关注点的多处,而各处都基本相似。比如权限认证、日志、事务处理。Aop 的作用在于分离系统中的各种关注点,将核心关注点和横切关注点分离开来。通俗描述就是:不通过修改源代码方式,在主干功能里面添加新功能。
假如我们在登陆功能需要添加一个新的判断功能,可以不通过修改源代码的方式添加;
怎么实现AOP?(1).AOP底层使用动态代理
第一种有接口的情况,使用JDK动态代理
创建接口实现类代理对象,增强类的方法
第二种没有接口情况,使用CGLIB动态代理
创建自雷的代理对象,增强类的方法
AOP(JDK动态代理) 1.使用JDK动态代理,使用Proxy类里面的方法创建代理对象
(1) 调用newProxyInstance方法
方法有三个参数:
第一个参数:类加载器
第二个参数:增强方法所在类的实现的接口
第三个参数:实现这个接口InvocationHandler,创建代理对象,写增强的方法
2.演示JDK动态代理代码AOP(术语)
1.连接点:类里面哪些方法可以被增强,这些方法称为连接点
2.切入点:事迹被真正增强的方法,称为切入点
3.通知(增强)
(1).实际增强的逻辑部分称为通知(增强)
(2).通知有多种类型:
1.前置通知
//前置代码 增强方法执行前执行 @Before(value = "xxx")
2.后置通知
//在方法返回值后执行,在方法有异常时不执行,后置通知(返回通知) @AfterReturning(value = "execution(xxx)")
3.环绕通知
//在方法执行前后都会执行 环形通知
@Around(value = "execution("xxx")
4.异常通知
5.最终通知:与finally相似
//不管有没有异常都执行, 最终通知 @After(value = "execution(xxx)" )
4.切面:是动作,增强类发出的动作作用在被增强类上,把通知应用到切入点的过程
AOP操作(基于注解,重点掌握)1.Spring框架一般基于AspectJ实现AOP操作
(1)双满是AspectJ
AspectJ不是Spring组成部分,独立AOP框架,一般AspectJ和Spring框架一起使用,
进行AOP操作
2.基于AspectJ实现AOP操作
1.基于xml配置文件实现
2.基于注解方式实现
(1).基于xml配置文件实现
(2).基于注解方式实现(使用)
3.在项目工程里面引入AOP相关依赖
4.切入点表达式
(1)切入点表达式作用:知道对哪个类里面的哪个方式进行增强
(2)语法结构:
execution([权限修饰符][返回类型][类的全路径]([参数列表]))
举例1:对com.atguigu.dao.BookDao类里面的add方法进行增强
*:表示所有权限修饰符
*:表示对类里面所有的方法都进行增强
excution(* 空格 com.atguigu.dao.BookDao.add(Object...args))
*:表示对类里面所有的方法都进行增强
举例2:对com.atguigu.dao.BookDao类里面的所有的方法都进行增强
excution(* 空格 com.atguigu.dao.BookDao.*(Object...args))
举例3:对com.atguigu.dao包里面所有类,类里面的所有方法都进行增强
*:表示com.atguigu.dao包里面所有类
excution(* 空格 com.atguigu.dao.*.*(Object...args))
AOP操作(Aspectj 注解) 1.创建被增强类,在类里面定义方法 2.创建 增强类 3.进行通知的配置(1).在spring配置文件中,开启注解扫描
声明名声空间
(2).使用注解创建被增强类和增强类的对象
(3)在增强类上面添加注解@Aspect
(4)在spring配置文件中开启生成代理对象
声明名声空间
4.配置不同类型的通知 @Before注解表示作为前置通知
@Before(value = "execution(* demo_04.Aop.UserDao.add())")测试before通知: 测试所有类型通知:
5.相同的切入点抽取
上面的很多切入点表达式都是为了增强add方法 所以可以做个提取
上面的int count=5;均是误输入
6.有多个增强类对同一个方法进行增强,设置增强的优先级(1)再增强类上面添加注解@Order(数字类型值),数值类型越小优先级越高 从0开始
如果一个类设置了这个注解并且他的数值是低的 那么他的前置通知是先执行的 后置通知是后执行的,
AOP操作(Aspectj 配置文件)(了解) 1.增强类和被增强类 2.配置xml文件:
JdbcTemplate(概念和准备)
1.什么是JdbcTemplate
(1)Spring框架对JDBC进行封装,使用JdbcTemplate方便实现对数据库操作



