1 spring的主要作用就是方便解耦,简化开发。
2 耦合:就是类与类之间存在的依赖关系。
3 IoC:即控制反转。其实就是创建对象的过程让spring来做了。如下:
4 创建spring容器的两种方法:
第一种:ClassPathXmlApplicationContext:只能加载类路径下的配置文件bean.xml(这个使用最多)
ApplicationContext ac=new classPathXmlApplicationContext();
其中BeanFactory:提供的是一种延迟思想来创建bean对象 bean什么时候用就什么时候创建
ApplicationContext:提供的是一种立即加载的思想来创建bean对象。只要一解析配置文件,就会立马创建bean对象
第二种:FileSystemXmlApplicationContext:加载磁盘任意文件
5 Bean的作用范围:可以通过配置的方式来调整作用范围:
配置属性:bean标签的scope的属性
属性的取值:singleton:单例(这个 是默认值)
prototype:多例,可以存在多个对象
6 Bean的生命周期: init-method destroy-method
单例:出生:容器创建时对象就产生了 。
活着:只要容器在,对象就一直在。
死亡:容器销毁,对象就消亡了。
多例:出生:每次使用就创建对象
活着:只要有对象在使用它就要一直活着
死亡:当对象长时间不用,没有其他对象进行引用时由垃圾回收器gc进行回收。
7 spring的依赖注入
注入方式有三种:a 使用构造函数进行注入(一般用来注入基本数据类型或者String)
b 使用set方法进行注入(可以注入基本数据类型或者String也可以注入复杂的类型)
c 使用注解进行注入
a 构造函数进行注入:construction-arg
type:指定参数的类型 index:指定参数的索引位置,从0开始 name:指定参数名称(用的最多)
-------------------------------------以上三个都是用来指定给那个参数进行赋值,下面两个用指定赋什么值-----------------------------------
ref:指定其他的bean类型数据(必须是spring配置文件里存在的bean)
value:基本数据类型或者String类型
b 使用set方法进行注入:property 标签出现的位置在bean标签的内部
name:指定参数名称(用的最多)
------------------------------以上三个都是用来指定给那个参数进行赋值,下面两个用指定赋什么值----------------------------
ref:指定其他的bean类型数据(必须是spring配置文件里存在的bean)
value:基本数据类型或者String类型
c 其他复杂类型的注入都是利用set方法进行注入的
总结一下:结构相同的,标签可以互换
list-----String []-----set 这个三个里面的标签是可以互换的
map-----properties这些键值对类型子标签也是互换的
c 使用注解进行注入 用于创建对象的注解
@Component作用:相当于配置了一个bean的标签 @Component(value="customerService") 不写value时默认是当前类的短名首字母小写。
相当于<bean id="customerService" calss="com.itheima.service.impl.CustomerServiceImpl">
@Component注解可以放在类的头上,@Component不推荐使用。
@Controller:对应表现层的bean也就是常说的 Action
@Service:对应的业务层Bean
@Repository:数据层dao
用于注入对象相当于:<property name="" ref="">
<property name="" value="">
@Autowired
作用:
自动按照类型注入。当使用注解注入属性时,set方法可以省略。它只能注入其他bean类型。当有多个类型匹配时,使用要注入的对象变量名称作为bean的id,在spring容器查找,找到了也可以注入成功。找不到就报错。
@Qualifier
作用:
在自动按照类型注入的基础之上,再按照Bean的id注入。它在给字段注入时不能独立使用,必须和@Autowire一起使用;但是给方法参数注入时,可以独立使用。
属性:
value:指定bean的id。
@Resource
作用:
直接按照Bean的id注入。它也只能注入其他bean类型。
属性:
name:指定bean的id。
@Value
作用:
注入基本数据类型和String类型数据的
属性:
value:用于指定值
用于改变作用范围范围的注解:相当于:<bean id="" class="" scope="">
@Scope
作用:
指定bean的作用范围。
属性:
value:指定范围的值。
取值:singleton prototype request session globalsession
示例代码:
业务层代码:
/**
* 客户的业务层接口
*/
public interface ICustomerService {
/**
* 保存客户
* @param customer
*/
void saveCustomer();
}
/**
* 客户的业务层实现类
*/
//作用就相当于在xml中配置了一个bean标签,该注解有value属性,含义是bean的id。
//不写的时候,默认的id是:当前类名,且首字母小写。即:customerServiceImpl
@Component(value="customerService")
@Scope(value="singleton")
public class CustomerServiceImpl implements ICustomerService {
// @Autowired
// 自动按照数据类型注入,拿着当前变量的数据类型在spring的容器中找,找到后,给变量赋值。
// 当有多个类型匹配时,会使用当前变量名称customerDao作为bean的id,继续在容器中找。
// 找到了,也能注入成功。找不到就报错。
// @Qualifier(value="customerDao2")//在自动按照类型注入的基础之上,再按照id注入
@Resource(name="customerDao2")//直接按照bean的id注入
private ICustomerDao customerDao = null;
@Value("com.mysql.jdbc.Driver")//注入基本类型和String类型数据
private String driver;
@Override
public void saveCustomer() {
System.out.println(driver);
customerDao.saveCustomer();
}
}
持久层代码:
/**
* 客户的持久层接口
*/
public interface ICustomerDao {
/**
* 保存客户
*/
void saveCustomer();
}
/**
* 客户的持久层实现类11111111111111111111
*/
@Repository("customerDao1")
public class CustomerDaoImpl implements ICustomerDao {
@Override
public void saveCustomer() {
System.out.println("保存了客户111111111111111111");
}
}
/**
* 客户的持久层实现类222222222222222222222222
*/
@Repository("customerDao2")
public class CustomerDaoImpl2 implements ICustomerDao {
@Override
public void saveCustomer() {
System.out.println("保存了客户2222222222222222222");
}
}
测试类代码:
public class Client {
public static void main(String[] args) {
//1.获取容器
ApplicationContext ac = new ClassPathXmlApplicationContext("bean.xml");
//2.根据id获取对象
ICustomerService cs = (ICustomerService) ac.getBean("customerService"); cs.saveCustomer();
}
}
配置文件:
<?xml version="1.0" encoding="UTF-8"?>
<!-- 我们导入约束时,除了昨天的那部分之外,还要单独导入一个context名称空间 -->
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
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">
<!-- 告知spring框架在通过读取配置文件创建容器时,扫描的包,并根据包中类的注解创建对象-->
<context:component-scan base-package="com.itheima"></context:component-scan>
</beans>
<!-- 告知spring在创建容器时要扫描的包。当配置了此标签之后,spring创建容器就会去指定的包下寻找对应的注解-->
<!-- 进行注解文件的配置 -->
<context:component-scan base-package="com.itheima"></context:component-scan>
8 关于Spring注解和XML的选择问题
注解的优势:
配置简单,维护方便(我们找到类,就相当于找到了对应的配置)。
XML的优势:
修改时,不用改源码。不涉及重新编译和部署