@Autowired與xml.bean


@Autowired、setter、構造函數、beanxml-property、beanxml-constructor-arg 亂七八糟

一、寫在前面

對於標題的這幾個東西想必都不會陌生,但有的時候沒有百分百的拿捏住具體的操作上的區別,雖然,有幾個東西大家用的不多。本文只介紹用法區別。

二、用法介紹

(一)@Autowired

1、概念

(1)其實autowired它是用作裝配(拿spring容器中的現成bean來使用,裝配到當前的類bean中)。

(2)我覺得他是個局部的概念,用一個組件(組件也是個體)組裝成另一個個體,若干個組件的組裝在一起就構成了一個完整的個體。也是一個“過程”的概念。

(3)配置文件xml中的bean呢,跟Java的注解@Bean是一個意思。只是代碼與xml的不同吧。他是一個獨立的個體 + 這個個體如何去組裝別人 或者 由別人組裝。

autowired可以放在任意一個方法前,構造函數,域,Retention.RunTime意味着他的保持時間是運行時保留。

2、用法
(1)放在域前

public class Family {
	@Autowired
	private Student student;

}

這么寫的意思是,在實例化Family這個類的一個對象時,會從spring容器中拿取一個類型為Student的bean塞到Family的student字段中。
在我看來autowired是一個拿的動作,或者叫使用。

其實把autowired放在域前 《==》 在xml中配置bean,使用setter注入。

(2)放在普通的方法前

@Component
public class ClassB {

    @Getter
    private ClassA classA;

    @Autowired
    private void obtainA(ClassA classA) {
        this.classA = classA;
    }
}

從上面代碼可以看到,其實autowired可以放在任何一個普通的代碼前,除了static,畢竟這個肯定是一個對象,而不是類。

(3)構造函數

@Component
public class ClassB {

    @Getter
    private ClassA classA;

    @Autowired
    public ClassB(ClassA classA) {
        this.classA = classA;
    }

(二)配置文件xml方式配置bean

1、概念

在配置文件里寫bean什么的,很常用,與autowired的區別是,他定義一個個體(bean/類對象), 因此他也取代了@Component等注解的作用。bean的配置里面呢可以是各種組裝(他們完成了autowired的工作)

(1) property 與 setter

//類B
public class ClassB {

    @Getter
    private ClassA classA;
}

//類A
public class ClassA {
    @Getter
    private String name = "jenny";
}

//配置文件
<bean id="classB" class="autowired.ClassB">
    <property name="classA" ref="classA"/>
</bean>

<bean id="classA" class="autowired.ClassA">
    <property name="name" value="jennyA"/>
</bean>

配置文件中,property的意思是會調用你當前類中相應域的setter方法來進行裝配。如果你只是像上面這么寫的話,會報錯:

Caused by: org.springframework.beans.NotWritablePropertyException: Invalid property 'name' of bean class [autowired.ClassA]: Bean property 'name' is not writable or has an invalid setter method. Does the parameter type of the setter match the return type of the getter?

后來,你改為了:

public class ClassB {

    @Getter
    private ClassA classA;

    public void setClassA(ClassA classA) {
        this.classA = classA;
    }
}

public class ClassA {
    @Getter
    private String name = "jenny";

    public void setName(String name) {
        this.name = name;
    }
}

這樣就沒有問題了。

所以,從上面兩段代碼可以看出:bean.property + 相應字段的setter方法就可以完成 @Autowired + @Component的工作

(2)constructor-arg + 構造函數

//類B
public class ClassB {

    @Getter
    private ClassA classA;
	
    public ClassB (ClassA classA) {
        this.classA = classA;
    }
}

//類A
public class ClassA {
    @Getter
    private String name = "jenny";

    public ClassA(String name) {
        this.name = name;
    }

}

//配置文件
   <bean id="classA" class="autowired.ClassA">
        <constructor-arg name="name" value="jennyB"></constructor-arg>
    </bean>

    <bean id="classB" class="autowired.ClassB">
        <constructor-arg name="classA" ref="classA"></constructor-arg>
    </bean>

按照配置文件的寫法,那么ClassA與ClassB中一定要有相應的構造函數才行,否則會報錯。

所以,從上可以看出 constructor-arg 的方式可以等價於@Autowired注解。

這么說吧,有了@Autowired了,就取締了property 和 constructor-arg,但是取締不了bean元素,哈哈

(三)autowired與xml.bean的各種混用
隨便寫個例子吧


public class ClassB {

    @Getter
    private ClassA classA;

    @Autowired
    //或者放到域classA前也可以,方法前也可以
    public ClassB (ClassA classA) {
        this.classA = classA;
    }
}

<bean id="classA" class="autowired.ClassA">
    <constructor-arg name="name" value="jennyB"></constructor-arg>
</bean>

<bean id="classB" class="autowired.ClassB"></bean>

例子中,classB的xml.bean中並沒有寫如何裝配classA,但是在java代碼里寫了進行自動裝配,即從容器里找到這個類型的bean來裝配,classA的bean則寫在了xml文件里。

三、其他問題

1. autowired的幾種裝配方式的區別

2. autowired與構造函數執行的先后順序


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM