spring的概述
spring: 是java 分层的se/ee的full-stack(一站式) 开源框架
为EE的每一层都提供了解决技术:
web: struts2 springMVC
service: spring(IOC AOP 声明式事务)
dao: hibernate springJDBCTemplate
spring的作用
解耦合
声明式事务
集成junit更加方便的进行分层测试
对优秀框架进行集成
.....
IOC入门
基本配置
bean标签: 指定要创建的实体类
id属性: 可以为任意值 但是在整个配置文件中唯一
class属性: 要实例化类的全限定名 反射
scope属性: 范围
singleton: 单实例 默认值
如果是单实例,配置文件文件只要一加载 就会创建对象 放在spring容器 (map<id,对象>)
当所有人过来问spring容器要的时候(getBean),所用人用的都是同一个对象
prototype: 多实例
如果是多实例,配置文件加载,不创建对象
当每个人过来getbean的时候,getbean一次创建一次 放在容器中
*举例:
什么时候用默认值singleton(单实例)? 什么时候用prototype(多实例)?
action: prototype
service/dao: singleton
了解
singleton的对象什么时候销毁? prototype创建出来的对象什么时候销毁?
:singleton的对象 当spring容器关闭 对象销毁
prototype的对象 长时间不用自动被垃圾回收机制给回收了
init-method:指定初始化方法
destory-method:指定销毁方法
<bean id="user" class="User" scope="prototype" init-method="init" destroy-method="destory"></bean>
import标签:导入外部的配置文件
resource属性:外部配置文件的地址
举例:
web: 所有在web层创建的对象 applicationContext_web.xml
service:所有在service层创建的对象 applicationContext_service.xml
dao: 所有在dao层创建的对象 applicationContext_dao.xml
<import resource="applicationContext_web.xml"/>
<import resource="applicationContext_service.xml"/>
<import resource="applicationContext_dao.xml"/>
——————————————————————————————————————————————————————————————————————————————————————
DI
首先,了解为什么需要DI
- 举例 *:
Car接口中只有run方法,
此时CarIml继承了Car接口并且新加入了属性name
如果只是通过IOC的bean标签创建对象
那么无法给name赋值
因为 Car car = (Car)context.getBean(“car”);
Car接口实际上并没有name属性,无法赋值
此时就需要DI来解决这个问题
DI的使用:
1.set属性注入:
第一步:构建setName方法:
在CarIml中构建setName方法
第二步: 在applicationContext.xml中bean标签中添加<property>
<property name="name" value="兰博基尼"></property>
name:要赋值的属性名
value:要赋的值 (针对的是基本类型和String类型)
ref: 针对的是对象类型
指向的是spring中bean的id名
此时当类被创建时,就会自动的初始化name值
2.构造器注入
第一步:添加有参构造方法
第二部:在applicationContext.xml中bean标签中添加<constructor-arg>
name:要赋值的属性名
value:要赋的值 (针对的是基本类型和String类型)
ref: 针对的是对象类型
<constructor-arg name="name" value="BMW"></constructor-arg>
3.P名称空间注入
底层:set注入(所以还是需要有set方法)
条件: 在配置文件中有p的名称空间
xmlns:p="http://www.springframework.org/schema/p"
语法:<bean p:属性名="属性值" p:属性名-ref="bean的id对象值" >
<bean id="person" class="CarImpl" p:name="BMW" p:car-ref="car"></bean>
4.复杂属性注入:map,list[]等
<bean id="collBean" class="CollBean">
<property name="ArrayDemo">
<!-- 数组类型 -->
<list>
<value>aaa</value>
<value>bbb</value>
<value>ccc</value>
</list>
</property>
<property name="listDemo">
<!-- list类型 -->
<list>
<value>111</value>
<value>222</value>
<ref bean="car"/>
</list>
</property>
<property name="mapDemo">
<!-- map -->
<map>
<entry key="k1" value="aaa"></entry>
<entry key="k2" value="bbbb"></entry>
<entry key="k3" value-ref="car"></entry>
</map>
</property>
</bean>
Spring的ioc注解入门
注解的开发步骤:
1.导包 spring-aop.jar
2.开启注解扫描器 告诉spring应该去那个包下面解析注解
3.配置注解组件 Component
4.测试
掌握的注解
注解条件:(掌握)
1 导包 spring-aop.jar
2 配置注解扫描器
<context:component-scan base-package="自己的包"></context:component-scan>
@Component
等同于<bean id="" class=""></bean>
("bean的id值") 定义在类上 只要定义在了类上,那么注解扫描器只要一扫描到就会创建该类的实例对象 放在spring容器中。
spring发布了公告, @Component这个注解不维护了,要维护这个注解下面衍生出的3个注解
@Controller(“bean的id值”) 针对的就是web层
@Service(“bean的id值”) 针对的是service层
@Repository(“bean的id值”) 针对的是dao层
@Value(“属性值”)
定义在属性字段上 针对的是基本类型和String类型
如果使用了这个注解,该属性的set方法可以省略不写
@Autowired
定义在属性字段上的 针对的是对象类型
如果定义在了那个对象类型的属性身上 会自动去spring容器中找该类型的实例对象给赋值
@Qualifier(“userDaoxxx”)
定义在属性字段上的 指定用该类型的哪个id名称的实例对象
注意: @Qualifier要想使用 必须结合 @Autowired 一起使用
@Resource(name=”userDaoxxx”)
等同于:@Autowired+@Qualifier("userDaoxxx")
了解的注解:
@Scope("singleton"或prototype) 定义在类上的 指定当前类是单实例还是多实例
@PostConstruct 定义在方法上 配置初始化方法
@PreDestroy 定义在方法上 配置销毁的方法
Spring全注解开发
@Configuration // 表示该类是一个注解类
@ComponentScan(basePackages="包名")
**等于** <context:component-scan base-package="包名"></context:component-scan>
@PropertySource(value="classpath:jdbc.properties")
**等于** <context:property-placeholder location="classpath:jdbc.properties"/>
@Bean(name="c3p0")
**等于** <bean id="c3p0" class="com.mchange.v2.c3p0.ComboPooledDataSource">
获得Spring对象
ApplicationContext context = new AnnotationConfigApplicationContext(SpringConfig.class)
全注解开发目前比半xml半注解开发麻烦,据说企业用的较少,所以我笔记就学到了这里