我是一個從汽車行業轉行IT的項目經理,我是Edward,如想了解更多,請關注我的公衆號【轉行項目經理的逆襲之路】。關於Spring容器,還有這些補充
1. 自動裝配
Spring可以將容器中存在的任何對象自動賦值到某個屬性或參數中去!這樣的機制就稱之爲“自動裝配”!簡單的說,當某個屬性或參數需要值時,只要這個值是在Spring容器中,Spring就可以爲它自動賦值!
在需要被自動裝配的屬性之前添加@Autowired
註解,即表示“希望Spring爲該屬性自動的裝配值”,例如:
@Controller
public class UserLoginServlet {
@Autowired
private UserDao userJdbcDao;
public void doPost() {
System.out.println("UserLoginServlet.doPost()");
userJdbcDao.login();
}
}
當然,自動裝配的前提是Spring容器中有合適的值!以上需要被裝配的是UserDao
類型的屬性,那就要求某個類是實現了UserDao
接口的,並且這個類是被Spring管理的(組件掃描+註解),例如:
package cn.tedu.spring;
import org.springframework.stereotype.Repository;
@Repository
public class UserJdbcDao implements UserDao {
public void reg() {
System.out.println("UserJdbcDao.reg()");
}
public void login() {
System.out.println("UserJdbcDao.login()");
}
}
Spring框架在實現自動裝配時,有2種裝配模式:
byName
模式:根據名稱實現自動裝配,在這種模式下,要求被裝配的屬性的名稱,與Bean的名稱是完全一致的!byType
模式:根據類型實現自動裝配,在這種模式下,要求被裝配的屬性,在Spring容器中存在類型匹配的對象,如果被裝配的屬性是聲明爲父級類型,則Spring容器存在子級類型的對象即可裝配成功,如果被裝配的屬性是聲明爲接口類型,則Spring容器存在實現類的對象即可裝配成功!注意:使用這種模式時,如果在Spring容器中匹配類型的對象超過1個,就會裝配失敗!
當使用@Autowired
註解時,其裝配機制是:首先,會以byType
模式在Spring容器中查找匹配類型的對象的數量,如果爲0個,會報告錯誤,例如:
Caused by: org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type 'cn.tedu.spring.UserDao' available: expected at least 1 bean which qualifies as autowire candidate. Dependency annotations: {@org.springframework.beans.factory.annotation.Autowired(required=true)}
如果有1個,則直接裝配,無視名稱是否匹配;
如果超過1個,會嘗試通過byName
模式來裝配,如果名稱匹配成功,則實現裝配,如果名稱均不匹配,則報告錯誤,例如:
Caused by: org.springframework.beans.factory.NoUniqueBeanDefinitionException: No qualifying bean of type 'cn.tedu.spring.UserDao' available: expected single matching bean but found 2: userJdbcDao,userMybatisDao
當然,不可以存在2個對象使用相同的名稱,否則,會因爲名稱衝突而出現錯誤:
Caused by: org.springframework.context.annotation.ConflictingBeanDefinitionException: Annotation-specified bean name 'a' for bean class [cn.tedu.spring.UserMybatisDao] conflicts with existing, non-compatible bean definition of same name and class [cn.tedu.spring.UserJdbcDao]
另外,還可以使用@Resource
註解來修飾被裝配的屬性,例如:
@Controller
public class UserLoginServlet {
@Resource // 這裏既可以使用@Autowired,也可以使用@Resource
private UserDao userMybatisDao;
public void doPost() {
System.out.println("UserLoginServlet.doPost()");
userMybatisDao.login();
}
}
使用
@Resource
時,必須將環境改爲JDK 1.8,或添加Tomcat環境。
使用@Resource
時,其執行效果與@Autowired
是完全一致的!但是,其裝配機制並不相同!@Resource
的裝配機制是:先嚐試byName
模式來裝配,如果存在名稱匹配的對象,則直接裝配,如果不存在,則嘗試byType
模式來裝配。
2. Spring階段小結
- 【理解】Spring框架的主要作用是:創建對象,管理對象;
- 【理解】使用Spring的好處在於:降低類與類之間的耦合度,改爲依賴於接口,實現解耦;
- 【理解】Spring框架通過DI(Dependency Injection:依賴注入,通過Spring框架使得某個屬性有值了)實現了IoC(Inversion of Control:控制反轉,通過註解或某些做法將對象的控制權交給了Spring框架);
- 【掌握】使用
@Bean
註解結合某個返回對象的方法,使得Spring框架管理相關的對象; - 【掌握】通過組件掃描(配置
@ComponentScan
註解的參數)和@Component
/@Controller
/@Service
/@Repository
註解,使得Spring框架管理類的對象; - 【瞭解】關於Spring管理的對象的作用域及生命週期;
- 【掌握】通過Spring框架讀取**.properties**配置文件中的信息;
- 【掌握】通過
@Autowired
註解實現自動裝配; - 【理解】Spring的自動裝配的機制,及
@Autowired
和@Resource
這2個自動裝配的註解的裝配機制的區別。