3、理论推导,通过set方法实现对象的创建由控制层(程序员控制)到测试类(用户控制)
4、讲些理论。(控制反转是一种通过描述(XML或注解)并通过第三方去生产或获取特定对象的方式。在Spring中实现控制反转的是IOC容器,其实现方式是依赖注入(DI))
5、第一个spring,讲些参数(value:普通属性值,ref:引入容器中已经创建好的对象),然后将p3的例子用spring实现
6、无参和有参构造构造器注入,容器,容器中的对象已经事先创建好存放在容器中了,默认是单例模式(容器中只实例化一个对象)。只要获取到容器,想要什么对象直接拿就ok
7、别名,Bean的配置,import导入其它xml配置文件
8-9、String,Map,List等不同数据类型的Set方式注入属性。10、其它注入方式。(依赖注入分为:1、构造器注入。2、Set方式注入。3、其它方式注入。)
11、Bean的作用域,主要了解singleton(单例),prototype(原型,多个对象,可用于多线程并发)
12、autowire = “byName / byType”
13、@Autowired是先byType,如果唯一則注入,否则byName查找。@Resource是先byname,不符合再继续byType
14、@Component有几个衍生注解,会按照web开发中,mvc架构中分层。
dao (@Repository)
service(@Service)
controller(@Controller)
这四个注解的功能是一样的,都是代表将某个类注册到容器中
注:使用注解开发的时候别忘了:开启注解、指定要扫描的包(这个包下的注解就会生效)和保证aop包的导入
15、@Configuration
//@Configuration代表这是一个配置类,就和之前的applicationContext.xml一样
//这个也会Spring容器托管,注册到容器中,因为他本来就是一个@Component
@Configuration
@ComponentScan("com.yyy.pojo")
@Import(Appconfig2.class)
public class Appconfig {
//注册一个bean,相当与之前写的一个bean标签
//这个方法的名字,就相当于bean标签的id属性
//这个方法的返回值,就相当于bean标签中的class属性
@Bean
public User getUser(){
return new User(); //就是返回要注入到bean的对象
}
//要么使用@Bean,要么使用@Component和ComponentScan,两种效果一样【!!】
}
17-18、静态代理。代码步骤:1、接口(抽象角色)。2、真实角色(被代理的角色)。3、代理角色(一般都会有些附属的操作)。4、客户端访问代理角色。优点:职责单一,不改变原有代码。缺点:每多一个真实角色就要多一个代理类
19、动态代理。动态代理和静态代理的角色一样。动态生成代理类(运用到反射的知识点),解决了静态代理的缺点
20-22、动态代理在spring中的应用,三章分别介绍了3种AOP的实现方式:1、使用spring的API接口。2、使用自定义类实现(自定义切面)。3、注解实现。
23-24、整合Mybatis
26、事务:要么都成功,要么都失败。事务ACID原则:1、原子性。2、一致性。3、隔离性。4、持久性。
27、管理事务的方式一般有两种:1、用AOP的方式配置事务,横切进去,不影响原有代码(推荐)。2、编程式事务管理,利用try{}catch{transactionManager.rollback()}方式回滚。
面试题:
-
说一下Spring Bean的生命周期?
先说生命周期有五部:1.实例化。2.赋值。3.初始化。4.使用。5.销毁。
然后再详细介绍:
1、解析类得到BeanDefinition
2、如果有多个构造方法,则要推断构造方法
3、确定好构造方法后,进行实例化得到一个对象
4、对对象中的加了@Autowired注解的属性进行属性填充
5、回调Aware方法,比如BeanNameAware,BeanFactoryAware
6、调用BeanPostProcessor的初始化前的方法
7、调用初始化方法
8、调用BeanPostProcessor的初始化后的方法,在这里会进行AOP
9、如果当前创建的bean是单例的则会把bean放入单例池
10、使用 bean
11、Spring容器关闭时调用DisposableBean中destory()方法 -
spring是如何解决循环依赖的?
1、A创建过程中需要B,于是A将自己放到三级缓存里面,去实例化B
2、B实例化的时候发现需要A,于是B先查一级缓存,没有,再查二级缓存,还是没有,再查三级缓存,找到了A然后把三级缓存里面的这个A放到二级缓存里面,并删除三级缓存里面的A
3、B顺利初始化完毕,将自己放到一级缓存里面(此时B里面的A依然是创建中状态)然后回来接着创建A,此时B已经创建结束,直接从一级缓存里面拿到B,然后完成创建,并将A放到一级缓存中。
ps:出现循环依赖可能是设计上出了点问题,而且因为高版本的spring好像是可以设置允不允许循环依赖,如果不可避免循环依赖,但循环依赖又会报错,可以用懒加载解决,+@Lazy注解。 -
说说你对 IOC 和 DI 的理解?
IOC 是控制反转的意思,是一种面向对象编程的设计思想,指将对象的控制权将给Spring容器,由Spring来负责控制对象的生命周期和对象之间的关系,将所有的类都放在Spring容器中,当我们需要某个对象时,不再需要我们去new,只需要告诉Spring容器,然后Spring就会把对应的对象返回给你。在不采用这种思想的情况下,我们需要自己维护对象与对象之间的依赖关系,很容易造成对象的耦合度过高,IOC可以帮我们维护对象与对象之间的依赖关系,并且降低对象之间的耦合度。
DI 是依赖注入的意思,指的是应用程序在运行时依赖IOC容器来动态注入组件所需要的某个依赖对象,它是IOC实现的实现方式,实现依赖注入的关键是IOC容器,它的本质就是一个工厂。有三种注入方式:构造器、setter、接口注入。 -
说说 BeanFactory 和 FactoryBean 的区别?
BeanFactory 是一个 Factory,是一个工厂类,它是一个负责生产和管理 Bean 的工厂,是 IOC 的核心接口,也就是 IOC 容器,主要职责包括:Bean 的实例化和定位以及配置应用程序中的对象及建立这些对象间的依赖,在 Spring 中,所有的 Bean 都是由 BeanFactory 来进行管理的;
FactoryBean 是一个接口,是一个 Bean,FactoryBean 是一个能产生或者修饰对象生成的工厂Bean,可以让我们自定义 Bean 的创建过程。