spring框架学习(一):设值注入和构造注入

本文介绍了Spring框架中的两种依赖注入方式——设值注入和构造注入。通过实例展示了如何在beans.xml中配置,并通过测试类进行验证。文章探讨了两种注入方式的适用场景,强调在依赖关系复杂时,设值注入更为简洁;而在需要默认构造函数的场景下,构造注入可能受限。最后,作者建议根据实际需求和个人喜好选择注入方式。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

之前一直都是用jsp+servlet+javabeans搭建网站应用,遂总结下今天学习的spring框架的内容

相应的jar包:http://download.youkuaiyun.com/detail/fengsigaoju/9835903

为了统一,在src下建立一个包命名为spring.firstdemo

我们首先假设一个卖票的场景,有一个实体类ticket,其有3个属性,起点终点和票价。

package spring.firstdemo;

public class ticket {
    private double value;//价格
    private String start;//起点
    private String end;//终点
	public double getValue() {
		return value;
	}
	public void setValue(double value) {
		this.value = value;
	}
	public String getStart() {
		return start;
	}
	public void setStart(String start) {
		this.start = start;
	}
	public String getEnd() {
		return end;
	}
	public void setEnd(String end) {
		this.end = end;
	}
	public void PrintInformation() {
		System.out.println("从"+start+"开往"+end+"的票价为:"+value);
	}
	public static void main(String[] args) {
		ticket t=new ticket();
		t.setStart("南京");
		t.setEnd("上海");
		t.setValue(89.5);
		t.PrintInformation();
	}
}

输出信息:

从南京开往上海的票价为:89.5

我们采用spring框架的依赖注入来实现相同的效果:

 

设值注入

首先在src新建一个名为beans.xml的文件

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN"
 "http://www.springframework.org/dtd/spring-beans.dtd">
<beans>
  <bean id="t" class="spring.firstdemo.ticket">
    <property name="start" value="南京"/>
    <property name="end" value="上海"/>
    <property name="value" value="89.5"/>
  </bean>
</beans>

同时新建一个测试类test_first:

package spring.firstdemo;
import org.springframework.beans.factory.xml.XmlBeanFactory;
import org.springframework.core.io.ClassPathResource;
public class test_first {
  public static void main(String[] args) {
	  XmlBeanFactory factory = new XmlBeanFactory(new ClassPathResource("first_beans.xml"));
	  ticket t= (ticket)factory.getBean("t");//使用spring控制反转创建对象
	  t.PrintInformation();
	  factory.destroySingletons();
}
}

也能起到同样的效果,我们分析下xml配置文件,这里整个bean类就是一个ticket实例,对于每一个实例赋值时 name就是变量名,value就是值,注意如果删去相应的set类,那么spring将无法正常对这些数据初始化。也就是说采用配置注入需要在需要实例化的类中创建相应的set方法(eclipse中可以右击后点击source自动加载)


传入数值参数比较好理解,那么如果传入的是类呢。

我们再假设一个车站类station,该车站仅卖一种票。

修改xml文件内容:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN"
 "http://www.springframework.org/dtd/spring-beans.dtd">
<beans>
  <bean id="t" class="spring.firstdemo.ticket">
    <property name="start" value="南京"/>
    <property name="end" value="上海"/>
    <property name="value" value="89.5"/>
  </bean>
  <bean id="s" class="spring.firstdemo.station">
    <property name="tick" ref="t"/>
  </bean>
</beans>

新建station及其测试类:

package spring.firstdemo;

import org.springframework.beans.factory.xml.XmlBeanFactory;
import org.springframework.core.io.ClassPathResource;

public class station {
  private ticket tick;
  public ticket getTick() {
	return tick;
}
  public void setTick(ticket tick) {
	this.tick = tick;
}
  public void print(){
	  System.out.println("station已经加载");
  }
  public static void main(String[] args) {
	  XmlBeanFactory factory = new XmlBeanFactory(new ClassPathResource("first_beans.xml"));
	  station s= (station)factory.getBean("s");//使用spring控制反转创建对象
	  s.print();
	  factory.destroySingletons();
}
}

可以观察到station是采用ref传入参数ticket的,注意xml里的顺序不影响程序,也就是两者可以颠倒,同样需要注意配置注入需要保留set方法的参数。

运行结果为:

station已经加载

但是正常车站明显并不会只卖一种车票,所以我们需要用一个list存储所有的车票信息.

再次修改配置信息:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN"
 "http://www.springframework.org/dtd/spring-beans.dtd">
<beans>
  <bean id="t" class="spring.firstdemo.ticket">
    <property name="start" value="南京"/>
    <property name="end" value="上海"/>
    <property name="value" value="89.5"/>
  </bean>
  <bean id="t2" class="spring.firstdemo.ticket">
     <property name="start" value="南京"/>
     <property name="end" value="北京"/>
     <property name="value" value="200.1"/>
   </bean>
   <bean id="t3" class="spring.firstdemo.ticket">
      <property name="start" value="杭州"/>
      <property name="end" value="成都"/>
      <property name="value" value="115.2"/>
   </bean>
   <bean id="station" class="spring.firstdemo.true_station">
      <property name="list">
         <list>
            <ref bean="t"/>
            <ref bean="t2"/>
            <ref bean="t3"/>
         </list>
     </property>
   </bean>
  <bean id="s" class="spring.firstdemo.station">
    <property name="tick" ref="t"/>
  </bean>
</beans>

创建真车站true_station类:

package spring.firstdemo;

import java.util.ArrayList;
import java.util.List;

import org.springframework.beans.factory.xml.XmlBeanFactory;
import org.springframework.core.io.ClassPathResource;

public class true_station {
  private List<ticket>list=new ArrayList<ticket>();
  public List<ticket> getList() {
	return list;
  }
   public void setList(List<ticket> list) {
	this.list = list;
} 
   public void print(){//打印当前拥有的车票
	   for (ticket t:list){
		   t.PrintInformation();//打印每一张车票的信息
	   }
   }
   public static void main(String[] args) {
	   XmlBeanFactory factory = new XmlBeanFactory(new ClassPathResource("first_beans.xml"));
	   true_station true_station= (true_station)factory.getBean("station");//使用spring控制反转创建对象
	   true_station.print();
	   factory.destroySingletons();
}
}

输出结果为:

从南京开往上海的票价为:89.5
从南京开往北京的票价为:200.1
从杭州开往成都的票价为:115.2


构造注入

如果说设值注入需要保留属性相应的set方法,那么构造注入需要保留相应的构造函数,这里以第三个station类为例子。

新建一个配置文件second_beans.xml

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN"
 "http://www.springframework.org/dtd/spring-beans.dtd">
<beans>
  <bean id="t" class="spring.firstdemo.ticket">
    <property name="start" value="南京"/>
    <property name="end" value="上海"/>
    <property name="value" value="89.5"/>
  </bean>
  <bean id="station" class="spring.firstdemo.station_second">
    <constructor-arg index="0"   ref="t"/>
   </bean>
</beans>

新建station_second类:

package spring.firstdemo;

import org.springframework.beans.factory.xml.XmlBeanFactory;
import org.springframework.core.io.ClassPathResource;

public class station_second {
	 private ticket tick;
	 public station_second(ticket tick){//需要保留构造函数
		 this.tick=tick;
	 }
	 public void print(){
		  System.out.println("station已经加载");
	  }
	  public static void main(String[] args) {
		  XmlBeanFactory factory = new XmlBeanFactory(new ClassPathResource("second_beans.xml"));
		  station_second s= (station_second)factory.getBean("station");//使用spring控制反转创建对象
		  s.print();
		  factory.destroySingletons();
	}
}

两者的选择:

1,如果依赖关系非常复杂,考虑到构造注入需要保留构造函数,那么构造函数里的内容会比较复杂,所以此时采用设值注入比较简洁。

2,如果使用没写第三方库,可能要求组建必须提供一个默认的构造函数,此时构造注入类型的依赖注入机制就存在局限性。

3,构造方法由于不存在set方法,不用担心上层代码在调用过程中执行set方法对组件产生印象。

总结:绝大情况下忽略二者的区别,哪个用的爽用哪个..

 








评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值