Spring 的读取和存储对象

目录

1.Spring 更简单的存储对象(使用注解)

1.1配置spring.xml设置spring存入对象的根路径

1.2使用注解将Bean对象存储到spring中

1.3方法注解重命名Bean

2.Spring更简单的获取对象

2.1对象装配(对象注入)的实现方法有3种

3.1三种注入方式的优缺点 

 2.2同一类型多个@Bean报错

2.1解决办法1:使用@Resource(name=‘别名’)

2.2解决办法2:使用@Qualifier注解定义名称


1.Spring 更简单的存储对象(使用注解)

1.1配置spring.xml设置spring存入对象的根路径

(此处的base-package=" com.**"的路径要和根路径一致)

<?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:content="http://www.springframework.org/schema/context"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context https://www.springframework.org/schema/context/spring-context.xsd">

    <!-- 配置 Spring 扫描的根路径(此根路径下的所有 Spring 存对象的注解才能生效) -->
    <content:component-scan base-package=""></content:component-scan>

</beans>

1.2使用注解将Bean对象存储到spring中

1)类注解:@Controller控制器(对象的存储)

       @Service服务器

       @Respository(仓库存储)

       @Component(组件存储)(其余四个类注解都是它的子类)

       @Configuration(配置存储) 

代码示例:(五类注解用法一样)

package com.wwzz.controller;
import org.springframework.stereotype.Controller;
@Controller
public class UserController {
    /**
     * 这个方法只是用来测试的
     * @param name
     */
    public void SayHello(String name){
        System.out.println("Hello! " + name);
    }
}
package com.wwzz;

import com.wwzz.controller.UserController;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

public class App {
    public static void main(String[] args) {
        ApplicationContext context = new ClassPathXmlApplicationContext("spring.xml");

        //读取存入对象的id默认情况下要小写
        UserController userController = context.getBean("userController", UserController.class);

        userController.SayHello("Controller");
        
    }
}

2)方法注解:

        @Bean

首先创建一个类User

public class User {
    public int id;
    public String name;
    public int age;
	// ... 一堆 getter和setter
}

创建一个UserBean 

package com.wwzz.util;

import com.wwzz.model.User;
import org.springframework.context.annotation.Bean;
import org.springframework.stereotype.Component;

@Component
public class UserBean {
    @Bean
    public User user() {
        // 伪代码 获取数据库中的内容....
        User user = new User();
        user.setId(1);
        user.setName("张三");
        user.setAge(18);
        return user;
    }
}

测试这个注解读取到bean的代码

1.3方法注解重命名Bean

(Spring默认是类扫描,要想使用方法注解@Bean就需要配合类注解@Component一起使用,才能将方法返回对象顺利存储到Spring中)

(重命名之后,方法名就无法使用了)

import com.wwzz.model.User;
import org.springframework.context.annotation.Bean;
import org.springframework.stereotype.Component;

@Component
public class UserBean {

    //对方法名重命名为“u1”,“u2”
    @Bean(name = {"u1","u2"})

    public User user() {
        // 伪代码 获取数据库中的内容....
        User user = new User();
        user.setId(1);
        user.setName("张三");
        user.setAge(18);
        return user;
    }
}

 

2.Spring更简单的获取对象

获取Bean对象也叫作对象分配,是把对象取出来放到某个类中,有时候也叫对象注入

(在进行注入的时候,可以使用@Autowired关键字,也可以使用@Resource关键字,但是@Resource无法进行构造方法注入

区别:

1)出生不同:@Autowired来自Spring框架,@Resource来自JDK

2)作用范围不同:@Autowired可以进行属性注入, 构造方法注入, Setter 注入,@Resource可以进行 属性注入, Setter注入, 不能使用构造方法注入

3)功能不同:相比于@Autowired,@Resource支持更多的参数设置,例name设置,根据名称获取Bean

2.1对象装配(对象注入)的实现方法有3种

1)属性注入

2)构造方法注入

3)Setter注入

属性注入:

package com.wwzz.controller;

import com.wwzz.model.User;
import com.wwzz.service.UserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;

@Controller
public class UserController {
    // 1. 属性注入 从Spring 中获取一个对象, 并注入到当前类
    @Autowired
    private UserService userService;

    public User findUserById(Integer id) {
        if (id == null){
            return new User();
        }
        return userService.findUserById(id);
    }
}

    public static void main(String[] args) {
        ApplicationContext context = new ClassPathXmlApplicationContext("spring.xml");
        UserController controller = context.getBean("userController",UserController.class);
        User user = controller.findUserById(1);
        System.out.println(user);
    }

构造方法注入:(如果当前类里构造方法只有一个,那么@Autowired是可以被省略的)

package com.wwzz.controller;

import com.wwzz.model.User;
import com.wwzz.service.UserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;

@Controller
public class UserController2 {
    private UserService userService;

    // 方法二: 构造方法注入是在类的构造方法种实现注入
    @Autowired
    public UserController2(UserService userService) {
        this.userService = userService;
    }
    public User findUserById(Integer id){
        if(id == null){
            return  null;
        }
        return userService.findUserById(id);
    }
}

    public static void main(String[] args) {
        ApplicationContext context = new ClassPathXmlApplicationContext("spring.xml");
        UserController2 userController2 = context.getBean("userController2",UserController2.class);
        User user = userController2.findUserById(1);
        System.out.println(user);
    }

Setter注入:

package com.wwzz.controller;

import com.wwzz.model.User;
import com.wwzz.service.UserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;

@Controller
public class UserController1 {
    // 1. 将 UserService 注入到当前类(使用Setter)
    private UserService userService;

    @Autowired // 必须要添加
    public void setUserService(UserService userService) {
        this.userService = userService;
    }
    // 2. 新建一个方法, 在方法里面调用 UserService 的查询方法. 返回用户对象
    public User findUserById(Integer id){
        if(id == null){
            return null;
        }
        return userService.findUserById(id);
    }
}

    public static void main(String[] args) {
        ApplicationContext context = new ClassPathXmlApplicationContext("spring.xml");
        UserController1 userController1 = context.getBean("userController1",UserController1.class);
        User user = userController1.findUserById(1);
        System.out.println(user);
    }

3.1三种注入方式的优缺点 

属性注入:

优点:简洁使用方便

缺点:只能用于loc容器,如果是非loc容器不可用,并且只有在使用能够的时候才会出现NPE(空指针异常)

构造方法注入:Spring官方推荐的注入方式

优点:通用性,在使用之前一定能保证注入的类不为空

缺点:如果有多个注入会显得比较臃肿

Setter注入:通用性不如构造方法

 2.2同一类型多个@Bean报错

package com.wwzz.util;

import com.wwzz.model.User;
import org.springframework.context.annotation.Bean;
import org.springframework.stereotype.Component;

@Component
public class UserBean {
    @Bean
    public User user1() {
        // 伪代码 获取数据库中的内容....
        User user = new User();
        user.setId(1);
        user.setName("张三");
        user.setAge(18);
        return user;
    }
    @Bean
    public User user2() {
        User user = new User();
        user.setId(2);
        user.setName("李四");
        user.setAge(20);
        return user;
    }
}

在另一个类中获取User对象:

package com.wwzz.controller;

import com.wwzz.model.User;
import org.springframework.stereotype.Controller;

import javax.annotation.Resource;

@Controller
public class UserController5 {
    @Resource
    private User user;

    public User getUser() {
        return user;
    }
}

以上代码会报错,原因是:获取Bean对象的方法,比如他们首先从名称获取,如果获取不到,就会从类型获取,上面的代码,从名称获取不到,类型又有多个,就会注入失败

2.1解决办法1:使用@Resource(name=‘别名’)

package com.wwzz.controller;

import com.wwzz.model.User;
import org.springframework.stereotype.Controller;

import javax.annotation.Resource;

@Controller
public class UserController5 {

    //使用别名
    @Resource(name='user3')
    private User user;

    public User getUser() {
        return user;
    }
}

2.2解决办法2:使用@Qualifier注解定义名称

这里配合@Autowired 和 @Resource 都可以

package com.wwzz.controller;

import com.wwzz.model.User;
import org.springframework.stereotype.Controller;

import javax.annotation.Resource;

@Controller
public class UserController5 {

    //@Qualifier注解定义名称
    @Resource
    @Qualifier(value="user3")
    private User user;

    public User getUser() {
        return user;
    }
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值