SSM授课实录-002期-Spring IoC&DI

SSM授课实录-002期-Spring IoC&DI

DI的全称是Dependency Injection,中文称之为依赖注入。它与控制反转(IoC)的含义相同,只不过这两个称呼是从两个角度描述的同一个概念。

1. IoC

在使用Spring框架之后,对象的实例不再由调用者来创建,而是由Spring容器来创建,Spring容器会负责控制程序之间的关系,而不是由调用者的程序代码直接控制。这样,控制权由应用代码转移到了Spring容器,控制权发生了反转,这就是控制反转。

2. DI

从Spring容器的角度来看,Spring容器负责将被依赖对象赋值给调用者的成员变量,这相当于为调用者注入了它依赖的实例,这就是Spring的依赖注入。

3. 依赖注入的实现方式

3.1 setter注入
注意点:
1. 属性的setter方法
2. 类中的无参构造方法
  • UserService.java
package com.liuhaolie.spring.di;

public interface UserService {

	void say();
	
}
  • UserServiceImpl.java
package com.liuhaolie.spring.di;

public class UserServiceImpl implements UserService {

	private UserDao userDao;
	
	public void setUserDao(UserDao userDao) {
		this.userDao = userDao;
	}

	@Override
	public void say() {
		userDao.say();
		System.out.println("userService say hello !!!");
	}

}

  • UserDao.java
package com.liuhaolie.spring.di;

public interface UserDao {

	void say();
	
}

  • UserDaoImpl.java
package com.liuhaolie.spring.di;

public class UserDaoImpl implements UserDao {

	@Override
	public void say() {
		System.out.println("userDao say hello !!!");
	}

}

  • applicationContext.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://www.springframework.org/schema/beans
        http://www.springframework.org/schema/beans/spring-beans.xsd">

	<!-- setter注入 -->
	<bean id="ud1" class="com.liuhaolie.spring.di.UserDaoImpl"/>
	
	<bean id="us1" class="com.liuhaolie.spring.di.UserServiceImpl">
		<!-- setter注入
			1) 在类中添加属性,并添加属性的setter方法
			2) 在bean中通过property进行属性注入
				
				注意点:类中必须要默认的无参构造方法
			
			问:
				什么时候就没有默认的无参构造方法了?
			答:
				java默认为每个类都提供了默认的隐式的无参构造方法;
				但是,当类中写了任何一个有参数的构造方法,那么默认
				提供的无参构造方法就失效了。通常为了保证类的对象可
				以被其他技术(大多是框架技术,比如Spring)方便使用,
				一般会在写了有参构造方法之后,额外的再提供默认的无参
				构造方法(显式)。
		 -->
		<property name="userDao" ref="ud1"></property>
	</bean>

</beans>
  • TestDI.java
package com.liuhaolie.spring.di;

import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

public class TestDI {

	public static void main(String[] args) {
		ApplicationContext ctxt = 
			new ClassPathXmlApplicationContext("applicationContext.xml");
		
		/*
		 * 通过类型获取bean
		 * 如果当前spring容器中,有多个该类型实例,此时会报错
		 */
		UserService userService = ctxt.getBean(UserService.class);
		userService.say();

	}

}

  • 运行结果
    在这里插入图片描述
3.2 构造器注入
注意点:
1. 对应参数个数的构造方法
2. 构造方法重载注意符合语法要求
  • Circle.java
package com.liuhaolie.spring.di;

public class Circle {
	//圆心
	private Point point;
	//半径
	private double r;
	
	//有参构造方法(全参构造方法)
	public Circle(Point point, double r) {
		this.point = point;
		this.r = r;
	}

	@Override
	public String toString() {
		return "圆心=" + point + ", 半径=" + r;
	}
	
}

  • Point.java
package com.liuhaolie.spring.di;

public class Point {
	private double x,y;

	public Point() {
	}
	
	public Point(double x, double y) {
		this.x = x;
		this.y = y;
	}

	//getter & setter
	public double getX() {
		return x;
	}

	public void setX(double x) {
		this.x = x;
	}

	public double getY() {
		return y;
	}

	public void setY(double y) {
		this.y = y;
	}

	@Override
	public String toString() {
		return "(" + x + "," + y + ")";
	}
	
}

  • applicationContext.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://www.springframework.org/schema/beans
        http://www.springframework.org/schema/beans/spring-beans.xsd">

	<!-- 构造器注入 -->
	<bean id="c1" class="com.liuhaolie.spring.di.Circle">
		<constructor-arg name="point" ref="p1"/>
		<constructor-arg name="r" value="10"/><!-- 半径为10 -->
	</bean>

	<bean id="p1" class="com.liuhaolie.spring.di.Point">
		<constructor-arg index="0" value="2"/><!-- 参数索引,从0开始计数 -->
		<constructor-arg index="1" value="5"/>
	</bean>

</beans>
  • TestDI.java
package com.liuhaolie.spring.di;

import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

public class TestDI {

	public static void main(String[] args) {
		ApplicationContext ctxt = 
			new ClassPathXmlApplicationContext("applicationContext.xml");
		
		Circle c1 = ctxt.getBean(Circle.class);
		System.out.println(c1);
	}

}

  • 运行结果
    在这里插入图片描述
3.3 静态工厂注入
注意点:
1. 工厂的概念:创建产品
2. 只要是创建产品的类都可以宽泛的理解为工厂
3. 静态工厂注入,指的是通过工厂的静态方法返回对象
4. 既然是静态方法,实质是通过类型名进行调用,无需创建对象
  • Book.java
package com.liuhaolie.spring.bean.factory;

public class Book {
	// 这里仅仅为了测试对象的创建,无需添加任何属性,当然加入属性也可以
}	

  • BookStaticFactory.java
package com.liuhaolie.spring.bean.factory;

/**
 * 静态工厂类
 * @author liuhaolie
 */
public class BookStaticFactory {

	/**
	 * 静态工厂方法
	 * @return Book对象(工厂思想的根本)
	 */
	public static Book getBook() {
		return new Book();
	}
	
}

  • applicationContext.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://www.springframework.org/schema/beans
        http://www.springframework.org/schema/beans/spring-beans.xsd">

	<!-- 静态工厂的方式 -->
	<bean id="b2" class="com.liuhaolie.spring.bean.factory.BookStaticFactory" 
factory-method="getBook"/>

</beans>
  • TestFactory.java
package com.liuhaolie.spring.bean.factory;

import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

public class TestFactory {

	public static void main(String[] args) {
		
		ApplicationContext ctxt = new ClassPathXmlApplicationContext("applicationContext.xml");
		
		Book b2 = (Book) ctxt.getBean("b2");
		System.out.println(b2);
		
	}

}

  • 运行结果
    在这里插入图片描述
3.4 实例工厂注入
注意点:
1. 和静态工厂不同的是,实例工厂是先需要创建工厂实例
2. 通过工厂实例再去创建其他实例
  • Book.java(同上)
  • BookFactory.java
package com.liuhaolie.spring.bean.factory;

/**
 * 实例工厂类
 * @author liuhaolie
 */
public class BookFactory {

	/**
	 * 实例工厂方法
	 * @return
	 */
	public Book getBook() {
		return new Book();
	}
	
}

  • applicationContext.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://www.springframework.org/schema/beans
        http://www.springframework.org/schema/beans/spring-beans.xsd">

	<!-- 
		实例工厂创建对象,两步:1) 创建实例工厂 2)创建对象
	 -->
	<bean id="bookFactory" class="com.liuhaolie.spring.bean.factory.BookFactory"></bean>
	<bean id="b3" factory-bean="bookFactory" factory-method="getBook"></bean>

</beans>
  • TestFactory.java
package com.liuhaolie.spring.bean.factory;

import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

public class TestFactory {

	public static void main(String[] args) {
		
		ApplicationContext ctxt = new ClassPathXmlApplicationContext("applicationContext.xml");
		
		Book b3 = (Book) ctxt.getBean("b3");
		System.out.println(b3);
		
	}

}

  • 运行结果
    在这里插入图片描述

4. 小结

依赖注入的四种方式:
1. setter注入
2. 构造器注入
3. 静态工厂注入
4. 实例工厂注入 

END…
PS:如有不懂,请联系okeyliu@163.com,备注来源CSDN

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值