Spring学习笔记02 - 第一个Spring程序

第一个Spring程序

1. 软件版本

- JDK 1.8+
- Maven 3.5+
- IDEA 2018+
- SpringFramework 5.1.4+

官网开发文档https://docs.spring.io/spring/docs/current/spring-framework-reference/

2. 环境搭建

<!-- https://mvnrepository.com/artifact/org.springframework/spring-context -->
<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-context</artifactId>
    <version>5.1.14.RELEASE</version>
</dependency>
  • Spring配置文件
    配置文件放置的位置 - 任意,一般放置resources/文件夹下
    配置文件的命名 applicationContext.xml
    思考:日后应用Spring框架时,需要进行配置文件路径的设置。

Spring 的核心 API

Spring提供的 ApplicationContext 工厂
作用:用于对象的创建
好处:解藕合

ApplicationContext 是接口类型
1.接口:屏蔽实现的差异
2. 非web 环境: ClassPathAmlApplicationContext(main junit单元测试)
3. web环境:XmlWebApplicationContext

重量级资源- 占用内存多

  • ApplicationContext工厂的对象占用大量内存
  • 不会频繁的创建对.象,一个应用只会创建一个工厂对象.
  • ApplicationContext 一定是线程安全的,
    (并发访问 - 多线程访问 - 线程安全 - synchronize)

程序开发

1. 创建类型

2. 配置文件配置

id: 唯一性
class: 属性,全限定名

<bean id="person" class="com.gogogo.Person"></bean>

3. 通过工厂类 获得对象

//1. 获得Spring的工厂
ApplicationContext ctx = new ClassPathXmlApplicationContext("/applicationContext.xml"); //指定配置文件的路径
//2. 通过工厂类 获得对象
Person person = (Person) ctx.getBean("person");

4. 细节分析

Spring工厂创建对象
getBean()有多个重载函数
在这里插入图片描述

applicationContext.xml中配置如下

<bean id="person" class="com.gogogo.Person"></bean>
<bean id="person1" class="com.gogogo.Person"></bean>
<bean id="animal" class="com.gogogo.Animal"></bean>

getBean(Class aclass)
此时使用getBean(Person.class)时,会报异常,根据class 找到了两个对象,语法错误。
expected single matching bean but found 2: person, person1

ApplicationContext ctx = new ClassPathXmlApplicationContext("/applicationContext.xml");       
Person person = (Person) ctx.getBean(Person.class);

注意:若使用getBean(Person.class)这种承载,必须保证配置文件中只有一个该类型的bean标签。

getBean(String s, Class aclass)
使用getBean(“person”,Person.class)没问题,找到对应的id class 属性即可,不需要强制转换。

ApplicationContext ctx = new ClassPathXmlApplicationContext("/applicationContext.xml");
Person person = ctx.getBean("person",Person.class);

getBeanDefinitionNames(),
返回值类型: 数组
获取的是Spring工厂配置文件中所有bean标签的id值

String[] ps= ctx.getBeanDefinitionNames();
for(String id : ps){
    System.out.println("id = "+ id);
}
//output:
//id = person
//id = person1
//id = animal

getBeanNamesForType()
返回值类型: 数组
根据类型获得Spring配置文件中,所有该类型的id值。

ApplicationContext ctx = new ClassPathXmlApplicationContext("/applicationContext.xml");
String[] pts= ctx.getBeanNamesForType(Person.class);
for(String id : pts){
    System.out.println("id = "+ id);
}
//ouput:
//id = person
//id = person1

containsBeanDefinition()
返回值类型: boolean
用于判断是否存在指定id的bean

ApplicationContext ctx = new ClassPathXmlApplicationContext("/applicationContext.xml");
if(ctx.containsBeanDefinition("person")){
    System.out.println("Yes");
}else{
    System.out.println("No");
}
//output
//Yes

containsBean()

ApplicationContext ctx = new ClassPathXmlApplicationContext("/applicationContext.xml");
if(ctx.containsBean("sd")){
    System.out.println("Yes");
}else{
    System.out.println("No");
}
//output
//No
  • 配置文件中需要主要的细节
  1. 只配置class属性,没有id值

应用场景: 如果这个bean只需要使用一次,可以省去id,若多次使用,这需要配置id属性

//<bean id="person" class="com.gogogo.Person"></bean>
<bean class="com.gogogo.Person"></bean>
2. name属性
id大名,name小名,别名。
<bean id="person" name = "p" class="com.gogogo.Person"></bean>

可以通过name属性 获得和 id属性获得的一样的结果

ApplicationContext ctx = new ClassPathXmlApplicationContext("/applicationContext.xml");
Person p = (Person) ctx.getBean("p");
System.out.println("p = "+p);

区别:

  1. 别名可以定义多个,但id属性只能有一个
<bean id="person" name = "p, p1, p2" class="com.gogogo.Person"></bean>
  1. xml的id属性值,命名是有要求的:必须以字母开头,后面可以跟字母,数字,下划线。不能以特殊字符开头。而别名没有要求。
    name属性会应用在特殊命名场景下。
    XML 现在没有限制,可以用反斜杠开头
  2. 代码区别,containsBean(), 可以判断id,也可以判断name。
    containsBeanDefinition(), 只能判断id, 不能判断name值
ApplicationContext ctx = new ClassPathXmlApplicationContext("/applicationContext.xml");
//只能判断id
if(ctx.containsBeanDefinition("p")){
    System.out.println("Yes");
}else{
    System.out.println("No");
}
// id, name 都可以
if(ctx.containsBean("person")){
    System.out.println("Yes");
}else{
    System.out.println("No");
}
//output
//No
//Yes

Spring工厂底层实现的原理,简易版(无源码)

在这里插入图片描述
反射也会调用类的无参构造,也能调用私有函数
思考:
问题:未来的开发中,是不是所有的对象都交给Spring工厂来创建呢?
回答: 理论上是的,但是有特例,实体对象(entity)不会交给Spring创建,它是由持久层定义的,需要和数据库交互。

学习开心❤️
加油努力

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值