Spring
理念:使現有技術更加實用,本身是大雜燴整合現有的框架技術
優點:
- 輕量級框架
- Ioc 容器-控制反轉 inversion of Control
- Aop 面向切面編程
- 對事務支持
- 對框架的支持
一、Ioc 控制反轉
Ioc 是一種編程思想,由主動編程變爲被動接收
別名:依賴注入 dependency injection
控制:
指誰來控制對象的創建
傳統的應用程序對象的創建是由程序本身控制的
使用 spring 之後,由 spring 創建對象
反轉:
正轉指程序來創建對象
反轉指程序本身不創建對象,而變成被動接受對象
總結:
以前對象是由程序本身創建,
使用 spring 之後,程序變爲接收 spring 創建好的對象
簡單示例
1、依賴 pom.xml
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context-support</artifactId>
<version>5.2.6.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
<version>5.2.6.RELEASE</version>
</dependency>
2、Person.java
package com.pengshiyu.bean;
public class Person {
private String name;
public void setName(String name) {
this.name = name;
}
public void sayHello() {
System.out.println("hello " + this.name);
}
}
3、beans.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 name="person" class="com.pengshiyu.bean.Person">
<property name="name" value="張三" />
</bean>
</beans>
4、Demo.java
package com.pengshiyu.spring;
import com.pengshiyu.bean.Person;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
public class Demo {
public static void main(String[] args) {
// 解析beans.xml 文件,生成對應的Bean對象
ApplicationContext context = new ClassPathXmlApplicationContext("beans.xml");
Person person = (Person)context.getBean("person");
person.sayHello();
}
}
二、Dao 管理示例
Ioc: 對象由 spring 來創建
1、UserDao
package com.spring.dao;
public interface UserDao {
public void getUser();
}
2、UserDaoMysqlImpl
package com.spring.dao.impl;
import com.spring.dao.UserDao;
public class UserDaoMysqlImpl implements UserDao {
@Override
public void getUser() {
System.out.println("Mysql 獲取用戶信息");
}
}
3、UserDaoOracleImpl
package com.spring.dao.impl;
import com.spring.dao.UserDao;
public class UserDaoOracleImpl implements UserDao {
@Override
public void getUser() {
System.out.println("Oracle 獲取用戶信息");
}
}
4、UserService
package com.spring.service;
public interface UserService {
public void getUser();
}
5、UserServiceImpl
package com.spring.service.impl;
import com.spring.dao.UserDao;
import com.spring.service.UserService;
public class UserServiceImpl implements UserService {
private UserDao userDao = null;
public void setUserDao(UserDao userDao) {
this.userDao = userDao;
}
@Override
public void getUser() {
this.userDao.getUser();
}
}
6、beans.xml(簡化版)
<beans >
<bean id="mysqlDao" class="com.spring.dao.impl.UserDaoMysqlImpl" />
<bean id="oracleDao" class="com.spring.dao.impl.UserDaoOracleImpl" />
<bean id="service" class="com.spring.service.impl.UserServiceImpl">
<property name="userDao" ref="mysqlDao"></property>
</bean>
</beans>
7、TestDemo
package com.spring.test;
import com.spring.service.UserService;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
public class TestDemo {
public static void main(String[] args) {
ApplicationContext context = new ClassPathXmlApplicationContext("beans.xml");
UserService service = (UserService)context.getBean("service");
service.getUser();
}
}
三、使用 Ioc 來創建對象的 3 種方法
Person 類
package com.pengshiyu.bean;
public class Person {
private String name;
public Person() {
}
public Person(String name) {
this.name = name;
}
public void sayHello() {
System.out.println("hello " + this.name);
}
}
創建對象
package com.spring.test;
import com.pengshiyu.bean.Person;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
public class Demo {
public static void main(String[] args) {
ApplicationContext context = new ClassPathXmlApplicationContext("beans.xml");
Person person = (Person) context.getBean("person");
person.sayHello();
}
}
beans.xml(簡化版)
1、無參構造
<beans>
<bean name="person" class="com.pengshiyu.bean.Person" />
</beans>
2、有參構造
(1)根據參數下標設置
<beans>
<bean name="person" class="com.pengshiyu.bean.Person">
<!-- index 構造方法下標從 0 開始 -->
<constructor-arg index="0" value="Tom" />
</bean>
</beans>
(2)根據參數名稱設置
<beans>
<bean name="person" class="com.pengshiyu.bean.Person">
<!-- name 參數名-->
<constructor-arg name="name" value="Tom" />
</bean>
</beans>
(3)根據參數類型設置
<beans>
<bean name="person" class="com.pengshiyu.bean.Person">
<!-- type 參數類型 -->
<constructor-arg type="java.lang.String" value="Tom" />
</bean>
</beans>
3、工廠方法創建
(1)靜態工廠
package com.pengshiyu.factory;
import com.pengshiyu.bean.Person;
public class PersonFactory {
public static Person newInstance(String name) {
return new Person(name);
}
}
<beans >
<bean name="person" class="com.pengshiyu.factory.PersonFactory" factory-method="newInstance">
<constructor-arg name="name" value="Tom" />
</bean>
</beans>
(2)動態工廠
package com.pengshiyu.factory;
import com.pengshiyu.bean.Person;
public class PersonFactory {
public Person newInstance(String name) {
return new Person(name);
}
}
<beans>
<bean id="factory" class="com.pengshiyu.factory.PersonFactory" />
<bean name="person" factory-bean="factory" factory-method="newInstance">
<constructor-arg name="name" value="Tom"/>
</bean>
</beans>
注意靜態工廠 static
四、Spring 配置文件
id 是 bean 的唯一標識符,如果沒有配置 id,name 默認爲標識符
如果配置了 id,又配置了 name,則 name 是別名
name 可以設置多個別名分隔符可以是空格、逗號、分號
class 是 bean 的全限定名=包名+類名
如果不配置 id 和 name,那麼可以可以使用如下方式獲取對象
applicationContext.getBean(class)
配置如下
<beans >
<bean id="person1" name="person user" class="com.pengshiyu.bean.Person" />
</beans>
獲取方式
Person person = (Person) context.getBean("person1");
// 或者
Person person = (Person) context.getBean("user");
// 或者
Person person = (Person) context.getBean(Person.class);
導入文件
<beans>
<import resource="person.xml"/>
</beans>
五、Spring 依賴注入 DI
dependency injection
依賴:指 bean 對象創建依賴於容器,bean 對象的依賴資源
注入:指 bean 對象依賴的資源由容器來設置和裝配
spring 注入
測試
package com.spring.test;
import com.pengshiyu.bean.Person;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
public class Demo {
public static void main(String[] args) {
ApplicationContext context = new ClassPathXmlApplicationContext("beans.xml");
Person person = (Person) context.getBean("person");
person.sayHello();
}
}
- 構造器注入
package com.pengshiyu.bean;
public class Person {
private String name;
public Person(String name) {
this.name = name;
}
public void sayHello() {
System.out.println("hello " + this.name);
}
}
<beans>
<bean name="person" class="com.pengshiyu.bean.Person">
<constructor-arg name="name" value="Tom"/>
</bean>
</beans>
- setter 注入
(1)常量注入
package com.pengshiyu.bean;
public class Person {
private String name;
public void setName(String name) {
this.name = name;
}
public void sayHello() {
System.out.println("hello " + this.name);
}
}
<beans >
<bean name="person" class="com.pengshiyu.bean.Person">
<property name="name" value="Tom"/>
</bean>
</beans>
(2)bean 注入
package com.pengshiyu.bean;
public class Address {
private String address;
public void setAddress(String address) {
this.address = address;
}
public String getAddress() {
return address;
}
}
package com.pengshiyu.bean;
public class Person {
private String name;
private Address address;
public void setAddress(Address address) {
this.address = address;
}
public void setName(String name) {
this.name = name;
}
public void sayHello() {
System.out.println("hello " + this.name + this.address.getAddress());
}
}
<beans >
<bean id="address" class="com.pengshiyu.bean.Address">
<property name="address" value="北京"/>
</bean>
<bean name="person" class="com.pengshiyu.bean.Person">
<property name="name" value="Tom"/>
<property name="address" ref="address"/>
</bean>
</beans>
(3)數組注入
package com.pengshiyu.bean;
public class Book {
private String name;
public Book(String name){
this.name = name;
}
@Override
public String toString() {
return "《" + this.name + "》";
}
}
package com.pengshiyu.bean;
import java.util.Arrays;
public class Person {
private Book[] books;
public void setBooks(Book[] books) {
this.books = books;
}
@Override
public String toString() {
return "Person{" +
"books=" + Arrays.toString(books) +
'}';
}
}
<beans >
<bean name="person" class="com.pengshiyu.bean.Person">
<property name="books">
<array>
<value>水滸傳</value>
<value>紅樓夢</value>
<value>三國演義</value>
<value>西遊記</value>
</array>
</property>
</bean>
</beans>
(4)List 注入
package com.pengshiyu.bean;
import java.util.Arrays;
import java.util.List;
public class Person {
private List<String>[] books;
public void setBooks(List<String>[] books) {
this.books = books;
}
@Override
public String toString() {
return "Person{" +
"books=" + Arrays.toString(books) +
'}';
}
}
<beans>
<bean name="person" class="com.pengshiyu.bean.Person">
<property name="books">
<list>
<value>水滸傳</value>
<value>紅樓夢</value>
<value>三國演義</value>
<value>西遊記</value>
</list>
</property>
</bean>
</beans>
(5)Map 注入
package com.pengshiyu.bean;
import java.util.Map;
public class Person {
private Map<String, String> cards;
public void setCards(Map<String, String> cards) {
this.cards = cards;
}
@Override
public String toString() {
return cards.toString();
}
}
<beans>
<bean name="person" class="com.pengshiyu.bean.Person">
<property name="cards">
<map>
<entry key="中國銀行" value="123456"></entry>
<entry key="建設銀行" value="123456"></entry>
</map>
</property>
</bean>
</beans>
(6)Set 注入
package com.pengshiyu.bean;
import java.util.Set;
public class Person {
private Set<String> games;
public void setGames(Set<String> games) {
this.games = games;
}
@Override
public String toString() {
return games.toString();
}
}
<beans>
<bean name="person" class="com.pengshiyu.bean.Person">
<property name="games">
<set>
<value>英雄聯盟</value>
<value>王者榮耀</value>
</set>
</property>
</bean>
</beans>
(7)null 注入
package com.pengshiyu.bean;
public class Person {
public void setWife(String wife) {
this.wife = wife;
}
private String wife;
@Override
public String toString() {
return wife;
}
}
<beans>
<bean name="person" class="com.pengshiyu.bean.Person">
<property name="wife"><null/></property>
</bean>
</beans>
(8) Properties 注入
package com.pengshiyu.bean;
import java.util.Properties;
public class Person {
private Properties props;
public void setProps(Properties props) {
this.props = props;
}
@Override
public String toString() {
return this.props.toString();
}
}
<beans >
<bean name="person" class="com.pengshiyu.bean.Person">
<property name="props">
<props>
<prop key="name">Tom</prop>
<prop key="sex">Man</prop>
</props>
</property>
</bean>
</beans>
(9) p 命名空間注入
需要有對應的 set 方法
package com.pengshiyu.bean;
public class Person {
private String name;
private int age;
public void setName(String name) {
this.name = name;
}
public void setAge(int age) {
this.age = age;
}
@Override
public String toString() {
return "Person{" +
"name='" + name + '\'' +
", age=" + age +
'}';
}
}
頭文件需要引入
xmlns:p="http://www.springframework.org/schema/p"
<?xml version="1.0" encoding="utf-8" ?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:p="http://www.springframework.org/schema/p"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd">
<bean name="person" class="com.pengshiyu.bean.Person"
p:name="Tom" p:age="23"/>
</beans>
(10)c 命名空間注入
要求有對應的構造方法
package com.pengshiyu.bean;
public class Person {
private String name;
private int age;
public Person(String name, int age) {
this.name = name;
this.age = age;
}
@Override
public String toString() {
return "Person{" +
"name='" + name + '\'' +
", age=" + age +
'}';
}
}
頭文件需要引入
xmlns:c="http://www.springframework.org/schema/c"
<?xml version="1.0" encoding="utf-8" ?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:c="http://www.springframework.org/schema/c"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd">
<bean name="person" class="com.pengshiyu.bean.Person"
c:name="Tom" c:age="23"/>
</beans>
六、bean 的作用域
spring
橋樑
輕量級
易學
ioc di
app
事務
整合框架
scope:
- singleton 單例 整個容器只有一個對象實例(默認)
- prototype 原型 每次獲取 Bean 都產生一個新對象
- request 每次請求時創建一個新的對象
- session 會話範圍內有一個對象
- global session 只在 portlet 下有用,表示 applicatio
- application 在應用範圍中有一個對象
Bean 自動裝配
autowire
- byName
- byType
- constructor
不推薦使用自動裝配