Spring笔记4--构造方法实现bean,探讨bean对象的作用域

76 阅读4分钟

本文已参与「新人创作礼」活动,一起开启掘金创作之路。

上节我们留下了一个疑问,就是Spring里面的bean对象是通过怎样的方式来被实例化的 我们知道创建一个对象的方法有很多种,比如:无参构造有参构造反射(本质上还是通过 newInstance()方法来获取类的构造器), Object类的clone方法(不调用构造器,前提得有对象供你使用,所以不太可能),反序列化.... 这些都只是猜测而已,下面我真正用代码进行实例测试来验证一下吧

一、无参还是有参来实例对象?

新建一个模板,名字你们自己取,在蓝色的java下创建一个包,我这里的包叫(com.ysj.study),在该包下面创建一个 类 HelloDemo1,如下 在这里插入图片描述 (如果是IDEA的用户,按左alt+insert键就可以一键快速写好有参构造和getter和setter方法,IDEAnb)

package com.ysj.study;

@SuppressWarnings("ALL")
public class HelloDemo1 {

    private String name;

    public HelloDemo1(){
        System.out.println("HelloDemo1的 无 参构造");
    }

    public HelloDemo1(String name) {
        System.out.println("HelloDemo1的 有 参构造");
        this.name = name;
    }

    public String getName() {
        return name;
    }

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

依旧在resources文件夹下创建一个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
       https://www.springframework.org/schema/beans/spring-beans.xsd">

</beans>

然后写入下面的bean的id创建代码 在这里插入图片描述 老方法,写入测试类代码(暂时不用@Test注解),在下面test文件夹下的java文件夹内创建myTest IDEA以后只需要输入CPX就有提示了 在这里插入图片描述 在这里插入图片描述

输出结果: 在这里插入图片描述

通过上面的输出,不难看出,bean的默认实例化对象走的路线是类的==无参构造==

二、有参构造来实例化对象

有时候我们需求用类的有参构造来实例化类,因为这样可以帮这个对象实例化一些数据(确实setter方法也可以全部初始化,只是为了学习一下如果通过有参构造使用bean)

<constructor-arg name="有参构成参数名" value="所需要赋的值"/>

在这里插入图片描述 我们再输出一下结果 在这里插入图片描述 这是当有参构造只有一个参数的时候,那如果有多个参数呢,用法还是和上面一样,只是多写几个constructor-arg的标签就可以

同时,我们发现如果我们去掉setter方法,bean还是能完成属性注入的,

所以bean的有参构造是不依赖于属性的setter方法的!!! 还有一种是通过BeanFactory的方式来构造bean-id,上次博客忘记写了,大家有兴趣可以自己查查学习一下,还是蛮重要的


三、每次获取的Bean-id的对象是一样的吗?

很多人会疑惑,我们每次或者的id对象转到java代码里面都是同一个对象吗 比如看下面的测试代码 在这里插入图片描述 那helloDemo1和helloDemo2和helloDemo3是同一个对象吗,我们说,判断对象是否是一样的,可以通过查看对象地址的HashCode,如果HashCode一样,那就是同一个对象,反之,那就是不一样的对象 我们分部输出一下HashCode看看是不是一致的 在这里插入图片描述 居然真的是同一个对象。 同一个对象的好处是可以节省内存,提升开发效率,也是就是我们所说的单例模式 但是它有缺点,我们有时候不希望这个对象在内存中唯一,因为我们的事务需求中可能需要几份不同的对象来实现,那该怎么办?

四、对象在IOC的生命周期及模式更改

官方给我们提供了一张有关对象在IOC容器的模式图 在这里插入图片描述 分别是singleton(单例模式),prototype(原型模式),request(请求模式),session(会话模式),application(应用模式),websocket(通信模式) 其实叫什么也不是很重要。而且我们目前学习的是spring5,也就是入门,我们目前暂时只接触前两个(单例模式和原型模式)就可以了,后面的等我们学到springmvc,javaweb及以后才会用到 那我们就具体说说单例模式原型模式

singleton(单例模式):约束每次创建的对象都是全局唯一的,内存中只存在一份 prototype(原型模式):约束每次创建的对象都是不一样的,内存中存在多份且独立

单例模式: 在这里插入图片描述 原型模式 在这里插入图片描述 IOC容器对于每个类对象的创建默认是单例模式,这也就说明了上面为什么所有在java外获取的对象的HashCode都是一样的,那我们如果某个类IOC容器内的实例模式呢

scope="模式名称"

在这里插入图片描述 我们再输出一下结果,看看每个对象的HashCode 在这里插入图片描述 输出结果证明了一切!!! 本节就到这里,知识慢慢吸收O(∩_∩)O哈哈~