1.Spring作用:
1.生态体系庞大,全能型选手!【springmvc是其一个子模块,jdbcTemplate能直接操作数据库!】
2.将其他组件粘合在一起
比如将SpringMVC和Mybaits连在一起
3.包括:IOC容器和AOP【面向切面编程】
Spring的IOC机制(控制反转和依赖注入)正是用在此处。
Spring的IOC(控制反转和依赖注入)
控制反转[IOC]:就是由容器控制程序之间的(依赖)关系,而非传统实现中,由程序代码直接操控。
控制反转是一种思想,其具体实现就是依赖注入!
依赖注入[DI:Dependency Injection]:组件之间的依赖关系由容器在运行期决定 ,由容器动态的将某种依赖关系注入到组件之中。
比如在controller层要调用service层方法 不需要new一个对象,用注解的形式,将对象放入容器里,进行调用,这就用到了依赖注入
2.IOC容器细节
1.使用IOC容器创建对象
2.使用IOC容器在创建对象的同时,给对象的属性赋值
3.在创建对象的过程中,实现组件对象之间的自动装配
3.搭建Spring IOC容器需要的开发环境
1.导入IOC容器需要的jar包
spring-beans-4.0.0.RELEASE.jar
spring-context-4.0.0.RELEASE.jar
spring-core-4.0.0.RELEASE.jar
spring-expression-4.0.0.RELEASE.jar
commons-logging-1.1.3.jar
2.创建Spring配置文件[Spring bean Configuration File]
实验1:通过IOC容器创建对象,并为属性赋值
<!-- 需要由IOC容器创建对象的全类名 -->
<property>是通过 set 方法注入的,所以实体类必须有set方法
?
1
2
3
4
5
6
|
<!-- class 指定类对象的全类名,交给服务器创建一个对象 id是一个唯一标识,在IOC只能出现一个id为book的bean对象 -->
<bean id= "book" class = "com.neuedu.spring.bean.Book" >
<property name= "bookName" value= "JAVA" ></property>
<property name= "author" value= "you" ></property>
<property name= "price" value= "123.123" ></property>
</bean>
|
?
1
2
3
4
5
6
7
8
9
10
|
public class TestIOC {
@Test
public void test() {
//1.获取IOC容器本身这个对象
ApplicationContext ioc = new ClassPathXmlApplicationContext( "applicationContext.xml" );
//2.从IOC容器中获取bean对象
Object bean = ioc.getBean( "book" );
System.out.println(bean);
}
}
|
注意:
①IOC容器本身对象创建时,会将配置文件中配置好的bean先创建出来
②默认是单实例的,只创建bean的一个对象
③如果设置bean的scope属性为prototype,那么创建bean的对象就是多实例的,在获取的时候创建,每次获取对象都会创建新的
④.从IOC容器中获取对象
①根据bean的id获取
②根据bean的类型获取:要求容器中指定类型的bean是唯一的
bean的后置处理器:
1.指的是在bean的初始化方法前后执行操作的专门的对象。
2.自定义的后置处理器:
1) 需要实现接口:org.springframework.beans.factory.config.BeanPostProcessor .
2) 做相应的配置就好!
实验2:根据bean的类型从IOC容器中获取bean的实例
?
1
2
3
4
5
6
7
8
9
10
|
public class TestIOC {
@Test
public void test() {
//1.获取IOC容器本身这个对象
ApplicationContext ioc = new ClassPathXmlApplicationContext( "applicationContext.xml" );
//2.从IOC容器中获取bean对象
Book bean = ioc.getBean(Book. class );
System.out.println(bean.getBookName()+ "---" +bean.getAuthor()+ "---" +bean.getPrice());
}
}
|
要注意,创建实体类的时候要有无参构造器,没有无参的话会默认有一个无参构造器,但是这时要是有一个有参构造器,就构建不成对象,获取不到bean实例。
实验3:通过构造器为bean的属性赋值、通过index属性指定参数的位置、通过类型不同区分重载的构造器
通过<constructor-arg> 给构造器赋值,通过index给属性排序,让该属性与有参构造器的顺序一直,index 是从 0 开始的,type 指定 你输入的值的类型,进而将该值付给对应的实体类的属性中,比如“22.22”会付给double 修饰的属性,而不是其他属性
?
1
2
3
4
5
|
<bean id= "book01" class = "com.neuedu.spring.bean.Book" >
<constructor-arg value= "you" index= "1" ></constructor-arg>
<constructor-arg value= "C++" index= "0" ></constructor-arg>
<constructor-arg value= "22.22" index= "2" type= "double" ></constructor-arg>
</bean>
|
实验4:给bean的级联属性赋值
创建三个实体类,第一个类包含第二个类,第二个类包含第三个类,第三个类有一个 username 属性
分别 get、set、toString 方法
?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
|
public class StudentController {
private StudentService studentService;
public StudentService getStudentService() {
return studentService;
}
public void setStudentService(StudentService studentService) {
this .studentService = studentService;
}
@Override
public String toString() {
return "StudentController [studentService=" + studentService + "]" ;
}
}
|
?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
|
public class StudentService {
private StudentDao studentDao;
public StudentDao getStudentDao() {
return studentDao;
}
public void setStudentDao(StudentDao studentDao) {
this .studentDao = studentDao;
}
@Override
public String toString() {
return "StudentService [studentDao=" + studentDao + "]" ;
}
}
|
?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
|
public class StudentDao {
private String username;
public String getUsername() {
return username;
}
public void setUsername(String username) {
this .username = username;
}
@Override
public String toString() {
return "StudentDao [username=" + username + "]" ;
}
}
|
value 只能给字符串赋值,ref 指向对象 ,与该对象的 id 相配
最后页面调用 studentController
?
1
2
3
4
5
6
7
8
|
<!-- 给bean的级联属性赋值 -->
<bean id= "studentDao" class = "com.neuedu.spring.bean.StudentDao" ></bean>
<bean id= "studentService" class = "com.neuedu.spring.bean.StudentService" ></bean>
<bean id= "studentController" class = "com.neuedu.spring.bean.StudentController" >
<property name= "studentService" ref= "studentService" ></property>
<property name= "studentService.studentDao" ref= "studentDao" ></property>
<property name= "studentService.studentDao.username" value= "zhangsan" ></property>
</bean>
|
?
1
2
3
4
5
6
7
8
9
10
|
public class TestIOC {
@Test
public void test() {
//1.获取IOC容器本身这个对象
ApplicationContext ioc = new ClassPathXmlApplicationContext( "applicationContext.xml" );
//2.从IOC容器中获取bean对象
Object bean = ioc.getBean( "studentController" );
System.out.println(bean);
}
}
|
实验5:通过p名称空间为bean赋值
在spring.xml 文件中的namespace 中选中 p 标签
?
1
2
3
4
5
6
7
|
<!-- 通过p名称空间为bean赋值 -->
<bean id= "student" class = "com.neuedu.spring.bean.Student"
p:name= "zhangsan"
p:gender= "1"
p:address= "China"
>
</bean>
|
实验6:测试bean的作用域,分别创建单实例和多实例的bean
在两个实体类中的无参构造器中分别输入一句话,判断对象创建几次
通过 scope 控制单例还是多例:singleton是单例;prototype是多例
单例 是在IOC容器创建的时候创建
多例 是每一次获取bean对象的时候创建
?
1
2
3
|
<!-- 测试bean的作用域,分别创建单实例和多实例的bean -->
<bean id= "book2" scope= "singleton" class = "com.neuedu.spring.bean.Book" ></bean>
<bean id= "student2" scope= "prototype" class = "com.neuedu.spring.bean.Student" ></bean>
|
显示 一个book ,三个 student
?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
|
public class TestIOC {
//1.获取IOC容器本身这个对象
private ApplicationContext ioc = new ClassPathXmlApplicationContext( "applicationContext.xml" );
@Test
public void test() {
ioc.getBean( "book" );
ioc.getBean( "book" );
ioc.getBean( "book" );
ioc.getBean( "student" );
ioc.getBean( "student" );
ioc.getBean( "student" );
}
}
|
实验7:创建带有生命周期方法的bean
在两个实体类中的无参构造器中分别输入一句话,判断对象是否被创建
?
1
2
|
<bean id= "book" class = "com.neuedu.spring.bean.Book" ></bean>
<bean id= "student" class = "com.neuedu.spring.bean.Student" ></bean>
|
test() 中啥都不写,运行之后发现两个对象都被创建了
说明当 ioc 容器被创建时,对象就被创建了
?
1
2
3
4
5
6
7
8
9
|
public class TestIOC {
private ApplicationContext ioc = new ClassPathXmlApplicationContext( "applicationContext.xml" );
@Test
public void test() {
}
}
|
实验8:创建带有生命周期方法的bean
在实体类中创建两个方法:init()和destroy()
分别输入“init方法执行”、“destroy方法执行”
在 bean 中 添加 init-method 和 destroy-method
分别对应 init 方法和 destroy 方法
?
1
|
<bean id= "teacher" class = "com.neuedu.spring.bean.Teacher" init-method= "teacherinit" destroy-method= "destroy" ></bean>
|
但是调用不了 destroy 方法,通过 ApplicationContext 的子类的 close 方法调用 destroy 方法
?
1
2
3
4
5
6
7
8
9
10
11
|
public class TestIOC {
private ApplicationContext ioc = new ClassPathXmlApplicationContext( "applicationContext.xml" );
@Test
public void test() {
ConfigurableApplicationContext cac = (ConfigurableApplicationContext) ioc;
ioc.getBean( "teacher" );
cac.close();
}
}
|
实验9:bean之间的依赖 depends-on="order"被依赖的对象会先创建
如果没有depends-on 会按照 bean 顺序创建对象
但是有了之后,被依赖的先创建,本例中 book 依赖 student ,所以 student 会先创建
?
1
2
3
|
<bean id= "book" class = "com.neuedu.spring.bean.Book" depends-on= "student" ></bean>
<bean id= "student" class = "com.neuedu.spring.bean.Student" ></bean>
<bean id= "teacher" class = "com.neuedu.spring.bean.Teacher" init-method= "teacherinit" destroy-method= "destroy" ></bean>
|
实验10:通过继承实现bean配置信息的重用
通过 parent 进行继承
book1 继承 book 的 bookName 和 author 其余的两个进行了修改
输出 book1 会输出
Book [bookName=JAVA, author=you, price=34.23 , isbn=house]
?
1
2
3
4
5
6
7
8
9
10
11
|
<bean id= "book" class = "com.neuedu.spring.bean.Book" >
<property name= "bookName" value= "JAVA" ></property>
<property name= "author" value= "you" ></property>
<property name= "price" value= "43.43" ></property>
<property name= "isbn" value= "home" ></property>
</bean>
<bean id= "book1" class = "com.neuedu.spring.bean.Book" parent= "book" >
<property name= "price" value= "34.23" ></property>
<property name= "isbn" value= "house" ></property>
</bean>
|
实验11:通过abstract属性创建一个模板bean
通过 abstract 使 book 对象抽象化,这样就不能调用 book 对象
但是可以调用子对象 book1
?
1
2
3
4
5
6
7
8
9
10
11
|
<bean id= "book" class = "com.neuedu.spring.bean.Book" abstract = "true" >
<property name= "bookName" value= "JAVA" ></property>
<property name= "author" value= "you" ></property>
<property name= "price" value= "43.43" ></property>
<property name= "isbn" value= "home" ></property>
</bean>
<bean id= "book1" parent= "book" >
<property name= "price" value= "43.43" ></property>
<property name= "isbn" value= "home" ></property>
</bean>
|
实验12:测试使用null值
book 属性少了 author 所以会显示 null
?
1
2
3
4
5
|
<bean id= "book" class = "com.neuedu.spring.bean.Book" >
<property name= "bookName" value= "java" ></property>
<property name= "price" value= "33.5" ></property>
<property name= "isbn" value= "house" ></property>
</bean>
|
也可以这么写,将<null/> 写进<property> 中
?
1
2
3
4
5
6
7
8
|
<bean id= "book" class = "com.neuedu.spring.bean.Book" >
<property name= "bookName" value= "java" ></property>
<property name= "author" >
< null />
</property>
<property name= "price" value= "33.5" ></property>
<property name= "isbn" value= "house" ></property>
</bean>
|
以上都是 String 类型,如果是 int/double 类型,就不能用<null/>
应该直接 <value="0"> 这样就会显示0/0.0
包装类 会显示 null
实验13:引用其他bean
新建 BookShop ,包含 book 属性, 通过 ref 连接上
调用bookShop,即可
?
1
2
3
4
5
6
7
8
|
<bean id= "book" class = "com.neuedu.spring.bean.Book" >
<property name= "bookName" value= "java" ></property>
<property name= "isbn" value= "house" ></property>
</bean>
<bean id= "bookShop" class = "com.neuedu.spring.bean.BookShop" >
<property name= "address" value= "河北" ></property>
<property name= "book" ref= "book" ></property>
</bean>
|
实验14:引用内部bean
在 bean 中在声明一个 bean
?
1
2
3
4
5
6
7
8
9
10
11
|
<bean id= "bookShop" class = "com.neuedu.spring.bean.BookShop" >
<property name= "address" value= "河北" ></property>
<property name= "book" >
<bean class = "com.neuedu.spring.bean.Book" >
<property name= "bookName" value= "java" ></property>
<property name= "author" value= "you" ></property>
<property name= "price" value= "43.32" ></property>
<property name= "isbn" value= "house" ></property>
</bean>
</property>
</bean>
|
实验15:使用List类型的集合属性
在 BookShop 类中添加 bookList 属性,并添加set/get方法
bookList 分别 ref 上 book1、book2、book3、book4
?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
|
<bean id= "book1" class = "com.neuedu.spring.bean.Book" >
<property name= "bookName" value= "java" ></property>
</bean>
<bean id= "book2" class = "com.neuedu.spring.bean.Book" >
<property name= "author" value= "you" ></property>
</bean>
<bean id= "book3" class = "com.neuedu.spring.bean.Book" >
<property name= "price" value= "43.43" ></property>
</bean>
<bean id= "book4" class = "com.neuedu.spring.bean.Book" >
<property name= "isbn" value= "home" ></property>
</bean>
<bean id= "bookShop" class = "com.neuedu.spring.bean.BookShop" >
<property name= "bookList" >
<list>
<ref bean= "book1" />
<ref bean= "book2" />
<ref bean= "book3" />
<ref bean= "book4" />
</list>
</property>
</bean>
|
?
1
2
3
4
5
6
7
8
9
10
11
12
|
public class TestIOC {
private ApplicationContext ioc = new ClassPathXmlApplicationContext( "applicationContext.xml" );
@Test
public void test() {
BookShop bean = ioc.getBean(BookShop. class );
List<Book> bookList = bean.getBookList();
for (Book book : bookList){
System.out.println(book);
}
}
}
|
实验16:使用Map类型的集合属性
在 BookShop 类中添加 Map 属性,并添加set/get方法
<map> 里面用 <entry>,一个键值对就是一个 <entry>
?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
|
<bean id= "bookShop" class = "com.neuedu.spring.bean.BookShop" >
<property name= "bookMap" >
<map>
<entry>
<key>
<value>book1</value>
</key>
<ref bean= "book1" />
</entry>
<entry>
<key>
<value>book2</value>
</key>
<ref bean= "book2" />
</entry>
<entry>
<key>
<value>book3</value>
</key>
<ref bean= "book3" />
</entry>
<entry>
<key>
<value>book4</value>
</key>
<ref bean= "book4" />
</entry>
</map>
</property>
</bean>
|
用 .entry 遍历 map 集合
?
1
2
3
4
5
6
7
8
9
10
11
12
13
|
public class TestIOC {
private ApplicationContext ioc = new ClassPathXmlApplicationContext( "applicationContext.xml" );
@Test
public void test() {
BookShop bean = ioc.getBean(BookShop. class );
Map<String, Book> bookMap = bean.getBookMap();
Set<Entry<String,Book>> entrySet = bookMap.entrySet();
for (Entry<String, Book> entry : entrySet) {
System.out.println(entry.getKey()+ "===" +entry.getValue());
}
}
}
|
实验17:使用prop子元素为Properties类型的属性赋值
在 BookShop 类中添加 Properties 属性,并添加set/get方法
?
1
2
3
4
5
6
7
8
9
10
|
<bean id= "bookShop" class = "com.neuedu.spring.bean.BookShop" >
<property name= "p" >
<props>
<prop key= "book1" >value1</prop>
<prop key= "book2" >value2</prop>
<prop key= "book3" >value3</prop>
<prop key= "book4" >value4</prop>
</props>
</property>
</bean>
|
?
1
2
3
4
5
6
7
8
9
10
11
12
13
|
public class TestIOC {
private ApplicationContext ioc = new ClassPathXmlApplicationContext( "applicationContext.xml" );
@Test
public void test() {
BookShop bean = ioc.getBean(BookShop. class );
java.util.Properties p = bean.getP();
System.out.println(p.get( "book1" ));
System.out.println(p.get( "book2" ));
System.out.println(p.get( "book3" ));
System.out.println(p.get( "book4" ));
}
}
|
时间: 2024-10-12 06:23:10