溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務條款》

Spring注入Bean方式是什么

發布時間:2021-12-23 11:28:26 來源:億速云 閱讀:196 作者:iii 欄目:大數據

這篇文章主要講解了“Spring注入Bean方式是什么”,文中的講解內容簡單清晰,易于學習與理解,下面請大家跟著小編的思路慢慢深入,一起來研究和學習“Spring注入Bean方式是什么”吧!

Spring框架的核心功能之一就是通過依賴注入的方式來管理Bean之間的依賴關系。

依賴注入

每個基于應用程序的 java 都有幾個對象,由這些對象一起工作來呈現出終端用戶所看到的工作的應用程序。當編寫一個復雜的 Java 應用程序時,應用程序類應該盡可能獨立于其他 Java 類來增加這些類重用的可能性,并且在做單元測試時,測試獨立于其他類的獨立性。依賴注入(或有時稱為布線)有助于把這些類粘合在一起,同時保持他們獨立。

Spring通過DI(依賴注入)實現IOC(控制反轉),常用的注入方式主要有三種:

  1. 構造方法注入

  2. setter注入

  3. 基于注解的注入

1. 構造方法注入 

<!-- 注冊userService -->
<bean id="userService">

問題一:如果有多個有參數的構造方法并且每個構造方法的參數列表里面都有要注入的屬性,那userDaoJdbc會注入到哪里呢?

public class UserService implements IUserService {

	private IUserDao userDao;
	private User user;
	
	public UserService(IUserDao userDao) {
		System.out.println("這是有一個參數的構造方法");
		this.userDao = userDao;
	}
	
	public UserService(IUserDao userDao, User user) {
		System.out.println("這是有兩個參數的構造方法");
		this.userDao = userDao;
		this.user = user;
	}
	
	public void loginUser() {
		userDao.loginUser();
	}

}

結果:會注入到只有一個參數的構造方法中,并且經過測試注入哪一個構造方法與構造方法的順序無關

問題二:如果只有一個構造方法,但是有兩個參數,一個是待注入的參數,另一個是其他類型的參數,那么這次注入可以成功嗎?

public class UserService implements IUserService {

	private IUserDao userDao;
	private User user;
	
	public UserService(IUserDao userDao, User user) {
		this.userDao = userDao;
		this.user = user;
	}
	
	public void loginUser() {
		userDao.loginUser();
	}

}

結果:失敗了,即使在costract-arg標簽里面通過name屬性指定要注入的參數名userDao也會失敗.

問題三:如果我們想向有多個參數的構造方法中注入值該在配置文件中怎么寫呢?

public class UserService implements IUserService {

	private IUserDao userDao;
	private User user;
	
	public UserService(IUserDao userDao, User user) {
		this.userDao = userDao;
		this.user = user;
	}
	
	public void loginUser() {
		userDao.loginUser();
	}

}
參考寫法:通過name屬性指定要注入的值,與構造方法參數列表參數的順序無關。

<!-- 注冊userService -->
<bean id="userService" class="com.spring.service.impl.UserService">
	<constructor-arg name="userDao" ref="userDaoJdbc"></constructor-arg>
	<constructor-arg name="user" ref="user"></constructor-arg>
</bean>

<!-- 注冊實體User類,用于測試 -->
<bean id="user" class="com.spring.entity.User"></bean>

<!-- 注冊jdbc實現的dao -->
<bean id="userDaoJdbc" class="com.spring.dao.impl.UserDaoJdbc"></bean>

問題四:如果有多個構造方法,每個構造方法只有參數的順序不同,那通過構造方法注入多個參數會注入到哪一個呢?

public class UserService implements IUserService {

	private IUserDao userDao;
	private User user;
	
	public UserService(IUserDao userDao, User user) {
		System.out.println("這是第二個構造方法");
		this.userDao = userDao;
		this.user = user;
	}
	
	public UserService(User user, IUserDao userDao) {
		System.out.println("這是第一個構造方法");
		this.userDao = userDao;
		this.user = user;
	}
	
	public void loginUser() {
		userDao.loginUser();
	}

}

結果:哪個構造方法在前就注入哪一個,這種情況下就與構造方法順序有關。

2. setter注入

<!-- 注冊userService -->
<bean id="userService" class="com.spring.service.impl.UserService">
	<!-- 寫法一 -->
	<!-- <property name="UserDao" ref="userDaoMyBatis"></property> -->
	<!-- 寫法二 -->
	<property name="userDao" ref="userDaoMyBatis"></property>
</bean>

<!-- 注冊mybatis實現的dao -->
<bean id="userDaoMyBatis" class="com.spring.dao.impl.UserDaoMyBatis"></bean>


注:上面這兩種寫法都可以。spring會將name值的每個單詞首字母轉換成大寫,然后再在前面拼接上"set"構成一個方法名,然后去對應的類中查找該方法,通過反射調用,實現注入。
public class UserService implements IUserService {

	private IUserDao userDao1;
	
	public void setUserDao(IUserDao userDao1) {
		this.userDao1 = userDao1;
	}
	
	public void loginUser() {
		userDao1.loginUser();
	}

}


注意:如果通過set方法注入屬性,那么spring會通過默認的空參構造方法來實例化對象,所以如果在類中寫了一個帶有參數的構造方法,一定要把空參數的構造方法寫上,否則spring沒有辦法實例化對象,導致報錯。

3. 基于注解的注入

在介紹注解注入的方式前,先簡單了解bean的一個屬性autowire,autowire主要有三個屬性值:constructor,byName,byType。

  • constructor:通過構造方法進行自動注入,spring會匹配與構造方法參數類型一致的bean進行注入,如果有一個多參數的構造方法,一個只有一個參數的構造方法,在容器中查找到多個匹配多參數構造方法的bean,那么spring會優先將bean注入到多參數的構造方法中。

  • byName:被注入bean的id名必須與set方法后半截匹配,并且id名稱的第一個單詞首字母必須小寫,這一點與手動set注入有點不同。

  • byType:查找所有的set方法,將符合符合參數類型的bean注入。

主要有四種注解可以注冊bean,每種注解可以任意使用,只是語義上有所差異:

@Component:可以用于注冊所有bean
@Repository:主要用于注冊dao層的bean
@Controller:主要用于注冊控制層的bean
@Service:主要用于注冊服務層的bean

描述依賴關系主要有兩種:

  • @Resource:java的注解,默認以byName的方式去匹配與屬性名相同的bean的id,如果沒有找到,就會以byType的方式查找,如果byType查找到多個的話,使用@Qualifier注解(spring注解)指定某個具體名稱的bean。

@Resource
@Qualifier("userDaoMyBatis")
private IUserDao userDao;

public UserService(){
	
}
  • @Autowired:spring注解,默認是以byType的方式去匹配類型相同的bean,如果只匹配到一個,那么就直接注入該bean,無論要注入的 bean 的 name 是什么;如果匹配到多個就會調用 DefaultListableBeanFactory 的 determineAutowireCandidate 方法來決定具體注入哪個bean。determineAutowireCandidate 方法的內容如下:

@Autowired
@Qualifier("userDaoJdbc")
private IUserDao userDao;

可以簡單的理解為先以 ByType 的方式去匹配,如果匹配到了多個再以 ByName 的方式去匹配,找到了對應的 bean 就去注入,沒找到就拋出異常。

感謝各位的閱讀,以上就是“Spring注入Bean方式是什么”的內容了,經過本文的學習后,相信大家對Spring注入Bean方式是什么這一問題有了更深刻的體會,具體使用情況還需要大家實踐驗證。這里是億速云,小編將為大家推送更多相關知識點的文章,歡迎關注!

向AI問一下細節

免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。

AI

亚洲午夜精品一区二区_中文无码日韩欧免_久久香蕉精品视频_欧美主播一区二区三区美女