初识Spring(AOP、IOC和DI)——对新手友好♥♥♥

初识Spring容器

在这里插入图片描述
继承体系(有点复杂,简单工厂模式)
在这里插入图片描述

本篇博客主要简单介绍Spring的环境搭建spring特点、优势,以及AOP(面向切面编程)IOC(控制反转)和一些spring的面试基础题。

什么是Spring

度娘走一波(嘿嘿♥)

Spring框架是一个开放源代码的J2EE应用程序框架,由Rod Johnson发起,是针对bean的生命周期进行管理的轻量级容器(lightweight container)。 Spring解决了开发者在J2EE开发中遇到的许多常见的问题,提供了功能强大IOC、AOP及Web MVC等功能。Spring可以单独应用于构筑应用程序,也可以和Struts、Webwork、Tapestry等众多Web框架组合使用,并且可以与 Swing等桌面应用程序AP组合。因此, Spring不仅仅能应用于J2EE应用程序之中,也可以应用于桌面应用程序以及小应用程序之中。Spring框架主要由七部分组成,分别是 Spring Core、 Spring AOP、 Spring ORM、 Spring DAO、Spring Context、 Spring Web和 Spring Web MVC。

百度完之后来总结一下,首先spring是属于一种开源轻量级的容器,主要针对于java bean对象的一个管理,我们都知道平时创建一个对象都是通过new或者通过反射的手段去获取对象,而由程序员自行创建对象不仅麻烦,还会提高程序代码的一个耦合度。spring为了解决这一系列问题而诞生,在spring里不需要通过new手段去创建一个对象,而是采用配置xml文件去创建定义一个对象。Spring致力于J2EE应用的各层的解决方案,而不是仅仅专注于某一层的方案。可以说Spring是企业应用开发的“一站式”选择,并贯穿表现层、业务层及持久层。然而,Spring并不想取代那些已有的框架,而是与它们无缝地整合。
spring特征:

轻量——从大小与开销两方面而言Spring都是轻量的。完整的Spring框架可以在一个大小只有1MB多的JAR文件里发布。并且Spring所需的处理开销也是微不足道的。此外,Spring是非侵入式的:典型地,Spring应用中的对象不依赖于Spring的特定类。
控制反转——Spring通过一种称作控制反转(IoC)的技术促进了低耦合。当应用了IoC,一个对象依赖的其它对象会通过被动的方式传递进来,而不是这个对象自己创建或者查找依赖对象。你可以认为IoC与JNDI相反——不是对象从容器中查找依赖,而是容器在对象初始化时不等对象请求就主动将依赖传递给它。它的底层设计模式采用了工厂模式,所有的 Bean 都需要注册到Bean工厂中,将其初始化和生命周期的监控交由工厂实现管理。程序员只需要按照规定的格式进行Bean开发,然后利用XML文件进行bean 的定义和参数配置,其他的动态生成和监控就不需要调用者完成,而是统一交给了平台进行管理。 [4] 控制反转是软件设计大师 Martin Fowler在 2004 年发表的”Inversion of Control Containers and the Dependency Injection pattern”提出的。这篇文章系统阐述了控制反转的思想,提出了控制反转有依赖查找和依赖注入实现方式。控制反转意味着在系统开发过程中,设计的类将交由容器去控制,而不是在类的内部去控制,类与类之间的关系将交由容器处理,一个类在需要调用另一个类时,只要调用另一个类在容器中注册的名字就可以得到这个类的实例,与传统的编程方式有了很大的不同,“不用你找,我来提供给你”,这就是控制反转的含义 [5] 。
面向切面——Spring提供了面向切面编程的丰富支持,允许通过分离应用的业务逻辑与系统级服务(例如审计(auditing)和事务(transaction)管理)进行内聚性的开发。应用对象只实现它们应该做的——完成业务逻辑——仅此而已。它们并不负责(甚至是意识)其它的系统级关注点,例如日志或事务支持。
容器——Spring包含并管理应用对象的配置和生命周期,在这个意义上它是一种容器,你可以配置你的每个bean如何被创建——基于一个可配置原型(prototype),你的bean可以创建一个单独的实例或者每次需要时都生成一个新的实例——以及它们是如何相互关联的。然而,Spring不应该被混同于传统的重量级的EJB容器,它们经常是庞大与笨重的,难以使用。
框架——Spring可以将简单的组件配置、组合成为复杂的应用。在Spring中,应用对象被声明式地组合,典型地是在一个XML文件里。Spring也提供了很多基础功能(事务管理、持久化框架集成等等),将应用逻辑的开发留给了你。
MVC——Spring的作用是整合,但不仅仅限于整合,Spring 框架可以被看做是一个企业解决方案级别的框架。客户端发送请求,服务器控制器(由DispatcherServlet实现的)完成请求的转发,控制器调用一个用于映射的类HandlerMapping,该类用于将请求映射到对应的处理器来处理请求。HandlerMapping 将请求映射到对应的处理器Controller(相当于Action)在Spring 当中如果写一些处理器组件,一般实现Controller 接口,在Controller 中就可以调用一些Service 或DAO 来进行数据操作 ModelAndView 用于存放从DAO 中取出的数据,还可以存放响应视图的一些数据。 如果想将处理结果返回给用户,那么在Spring 框架中还提供一个视图组件ViewResolver,该组件根据Controller 返回的标示,找到对应的视图,将响应response 返回给用户。

所有Spring的这些特征使你能够编写更干净、更可管理、并且更易于测试的代码。它们也为Spring中的各种模块提供了基础支持。
优势:

1.方便解耦,简化开发
通过Spring提供的IoC容器,我们可以将对象之间的依赖关系交由Spring进行控制,避免硬编码所造成的过度程序耦合。有了Spring,用户不必再为单实例模式类、属性文件解析等这些很底层的需求编写代码,可以更专注于上层的应用。
2.AOP编程的支持
通过Spring提供的AOP功能,方便进行面向切面的编程,许多不容易用传统OOP实现的功能可以通过AOP轻松应付。
3.声明式事务的支持
在Spring中,我们可以从单调烦闷的事务管理代码中解脱出来,通过声明式方式灵活地进行事务的管理,提高开发效率和质量。
4.方便程序的测试
可以用非容器依赖的编程方式进行几乎所有的测试工作,在Spring里,测试不再是昂贵的操作,而是随手可做的事情。例如:Spring对Junit4支持,可以通过注解方便的测试Spring程序。
5.方便集成各种优秀框架
Spring不排斥各种优秀的开源框架,相反,Spring可以降低各种框架的使用难度,Spring提供了对各种优秀框架(如Struts,Hibernate、Hessian、Quartz)等的直接支持。
6.降低Java EE API的使用难度
Spring对很多难用的Java EE API(如JDBC,JavaMail,远程调用等)提供了一个薄薄的封装层,通过Spring的简易封装,这些Java EE API的使用难度大为降低。
7.Java 源码是经典学习范例
Spring的源码设计精妙、结构清晰、匠心独运,处处体现着大师对Java设计模式灵活运用以及对Java技术的高深造诣。Spring框架源码无疑是Java技术的最佳实践范例。如果想在短时间内迅速提高自己的Java技术水平和应用开发水平,学习和研究Spring源码将会使你收到意想不到的效果。
总结:
1.低侵入式设计,代码污染极低
2.独立于各种应用服务器,基于Spring框架的应用,可以真正实现Write Once,Run Anywhere的承诺
3.Spring的DI机制降低了业务对象替换的复杂性,提高了组件之间的解耦
4.Spring的AOP支持允许将一些通用任务如安全、事务、日志等进行集中式管理,从而提供了更好的复用
5.Spring的ORM和DAO提供了与第三方持久层框架的良好整合,并简化了底层的数据库访问
6.Spring并不强制应用完全依赖于Spring,开发者可自由选用Spring框架的部分或全部

spring的7层基础框架

Spring 框架是一个分层架构,由 7 个定义良好的模块组成。Spring模块构建在核心容器之上,核心容器定义了创建、配置和管理 bean 的方式,如图所示:
组成Spring框架的每个模块(或组件)都可以单独存在,或者与其他一个或多个模块联合实现。每个模块的功能如下:1、核心容器:核心容器提供 Spring 框架的基本功能(Spring Core)。核心容器的主要组件是 BeanFactory,它是工厂模式的实现。BeanFactory 使用控制反转(IOC) 模式将应用程序的配置和依赖性规范与实际的应用程序代码分开 [3] 。
2、Spring 上下文:Spring 上下文是一个配置文件,向 Spring框架提供上下文信息。Spring 上下文包括企业服务,例如JNDI、EJB、电子邮件、国际化、校验和调度功能。
3、Spring AOP:通过配置管理特性,Spring AOP 模块直接将面向切面的编程功能集成到了 Spring 框架中。所以,可以很容易地使 Spring 框架管理的任何对象支持AOP。Spring AOP 模块为基于 Spring 的应用程序中的对象提供了事务管理服务。通过使用 Spring AOP,不用依赖 EJB 组件,就可以将声明性事务管理集成到应用程序中。
4、Spring DAO:JDBCDAO抽象层提供了有意义的异常层次结构,可用该结构来管理异常处理和不同数据库供应商抛出的错误消息。异常层次结构简化了错误处理,并且极大地降低了需要编写的异常代码数量(例如打开和关闭连接)。Spring DAO 的面向 JDBC 的异常遵从通用的 DAO 异常层次结构。
5、Spring ORM:负责框架中对象关系映射,提供相关ORM 接入框架的关系对象管理工具 [2] 。Spring 框架插入了若干个ORM框架,从而提供了 ORM 的对象关系工具,其中包括JDO、Hibernate和iBatisSQL Map。所有这些都遵从 Spring 的通用事务和 DAO 异常层次结构。
6、Spring Web 模块:Web 上下文模块建立在应用程序上下文模块之上,为基于 Web 的应用程序提供了上下文。所以,Spring框架支持与 Jakarta Struts 的集成。Web 模块还简化了处理多部分请求以及将请求参数绑定到域对象的工作。
7、Spring MVC 框架:MVC框架是一个全功能的构建 Web应用程序的 MVC 实现。通过策略接口,MVC框架变成为高度可配置的,MVC 容纳了大量视图技术,其中包括 JSP、Velocity、Tiles、iText 和 POI。模型由javabean构成,存放于Map;视图是一个接口,负责显示模型;控制器表示逻辑代码,是Controller的实现。Spring框架的功能可以用在任何J2EE服务器中,大多数功能也适用于不受管理的环境。Spring 的核心要点是:支持不绑定到特定 J2EE服务的可重用业务和数据访问对象。毫无疑问,这样的对象可以在不同J2EE 环境(Web 或EJB)、独立应用程序、测试环境之间重用。

耦合有什么含义

耦合性(Coupling),也叫耦合度,是对模块间关联程度的度量。模块间的耦合度是指模块之间的依赖关系,包括控制关系、调用关系、数据传递关系。模块间联系越多,其耦合性越强,同时表明其独立性越差( 降低耦合性,可以提高其独立性)。简单地说, 软件工程中对象之间的 耦合度就是对象之间的依赖性。指导使用和维护对象的主要问题是对象之间的多重依赖性。对象之间的耦合越高,维护成本越高。因此对象的设计应使类和构件之间的耦合最小。

spring的核心

AOP
AOP: 面向切面编程,指扩展功能不修改源码,将功能从业务逻辑代码中分离出来。
IOC
IOC: 控制反转
在这里插入图片描述

IOC和DI

环境搭建

1.需要用到的工具有IDEAMAVEN
2.开始搭建
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
创建成功
在这里插入图片描述
2.pom.xml文件添加spring依赖
你只需导入<dependencies></dependencies>里面的内容

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>
    <groupId>org.example</groupId>
    <artifactId>springs</artifactId>
    <version>1.0-SNAPSHOT</version>
    <dependencies>
        <!-- https://mvnrepository.com/artifact/org.springframework/spring-core -->
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-core</artifactId>
            <version>5.3.5</version>
        </dependency>
        <!-- https://mvnrepository.com/artifact/org.springframework/spring-beans -->
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-beans</artifactId>
            <version>5.3.5</version>
        </dependency>
        <!-- https://mvnrepository.com/artifact/org.springframework/spring-context -->
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-context</artifactId>
            <version>5.3.5</version>
        </dependency>
        <!-- https://mvnrepository.com/artifact/org.springframework/spring-aop -->
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-aop</artifactId>
            <version>5.3.5</version>
        </dependency>
        <!-- https://mvnrepository.com/artifact/org.springframework/spring-webmvc -->
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-webmvc</artifactId>
            <version>5.3.5</version>
        </dependency>
        <!-- https://mvnrepository.com/artifact/junit/junit -->
        <dependency>
            <groupId>junit</groupId>
            <artifactId>junit</artifactId>
            <version>4.12</version>
            <scope>test</scope>
        </dependency>



    </dependencies>
    <properties>
        <maven.compiler.source>8</maven.compiler.source>
        <maven.compiler.target>8</maven.compiler.target>
    </properties>

</project>

spring的bean对象的生命周期

首先实现BeanPostProcessor 接口,创建完成之后不需要手动去调用该类,但是要在xml文件里进行定义,不然其他对象无法识别到。

package com.xiaoliu.pojo;

import org.springframework.beans.BeansException;
import org.springframework.beans.factory.config.BeanPostProcessor;

public class BeanLife implements BeanPostProcessor {
    
    


    @Override
    public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
    
    
        System.out.println("init_初始化之后----");
        return BeanPostProcessor.super.postProcessAfterInitialization(bean, beanName);
    }
    @Override
    public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
    
    
        System.out.println("init_初始化之前----");
        return BeanPostProcessor.super.postProcessBeforeInitialization(bean, beanName);
    }
}

创建一个周期类

package com.xiaoliu.pojo;

public class BeanLifeCreate {
    
    
    private String name;

    public void setName(String name) {
    
    
        System.out.println("调用set方法");
        this.name = name;
    }
    public void init(){
    
    
        System.out.println("调用初始化");
    }
    public void destroy(){
    
    
        System.out.println("销毁bean对象");
    }
}

test类

    public void test02(){
    
    
        AbstractApplicationContext context = new ClassPathXmlApplicationContext("spring-config.xml");
        BeanLifeCreate blc = (BeanLifeCreate) context.getBean("beanlifetest");
        System.out.println("使用bean对象————————");
        context.close();
    }

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

spring属性注入的方式

1.默认无参构造方法<bean id="car" class="com.xiaoliu.pojo.Car"></bean>
默认是单例创建,采用单例模式,意味着只能创建一个对象,通过scope="singleton"控制,也可以设置为prototype不采用单例创建。
2.有参的构造方法,采用constructor-arg,一个bean意味着是一个对象的配置,对于一个对象的赋值,且此时必须类要存在对应的构造方法,否则会报错,index代表构造方法里参数的位置,name表示参数的属性名。

<bean class="com.xiaoliu.pojo.Car" id="car1">
        <constructor-arg index="0" name="brand" value="奥迪"></constructor-arg>
        <constructor-arg index="1" name="corp" value="北气集团"></constructor-arg>
        <constructor-arg index="2" name="price" type="double" value="500000"></constructor-arg>
        <constructor-arg index="3" name="maxpeed" type="int" value="200"></constructor-arg>
    </bean>

3.通过set方法去设置一个对象的属性值,此时类必须也要实现set方法,否则程序运行会报错,在bean里面id标识意味着一个对象申明时的标识。

    <bean class="com.xiaoliu.pojo.Car" id="car2">
        <property name="brand" value="jeep"></property>
        <property name="corp" value="上海集团"></property>
        <property name="maxpeed" value="180"></property>
        <property name="price"  value="100000"></property>
    </bean>

spring注入一个集合或者数组

如果注入的集合类型是基本数据类型或者是String时,可以把<ref></ref>换成<value></value>在中间直接赋值,下面代码是list集合,需要给一个对象赋值bean,然后采用ref连接的方式。<array></array>代表数组 <set></set>代表set集合,<map></map>代表map集合。

 <!-- 集合-->
    <bean class="com.xiaoliu.pojo.Car" name="c1" p:price="100000" p:maxpeed="100" p:corp="北汽"  p:brand="奥迪"></bean>
    <bean class="com.xiaoliu.pojo.Car" name="c2" p:price="200000" p:maxpeed="200" p:corp="北汽" p:brand="宝马"></bean>
    <bean class="com.xiaoliu.pojo.Car" name="c3" p:price="300000" p:maxpeed="100" p:corp="北汽"  p:brand="奔驰"></bean>
    <bean class="com.xiaoliu.pojo.Car" name="c4" p:price="400000" p:maxpeed="120" p:corp="北汽"  p:brand="红旗"></bean>
    <bean id="person3" class="com.xiaoliu.pojo.Person">
        <property name="car">
            <list>
                <ref bean="c1"></ref>
                <ref bean="c2"></ref>
                <ref bean="c3"></ref>
                <ref bean="c4"></ref>
            </list>
        </property>
    </bean>

第二种方式:通过util方式,最后通过bean的ref指向

 <!--集合-->
    <util:list id="carlist">
        <ref bean="c1"></ref>
        <ref bean="c2"></ref>
        <ref bean="c3"></ref>
        <ref bean="c4"></ref>
    </util:list>
    <bean id="person4" class="com.xiaoliu.pojo.Person" p:car-ref="carlist" p:name="哆啦A蒙" p:money="10000000"></bean>

spring的作用域

在这里插入图片描述

五种作用域中,request、session和global session三种作用域仅在基于web的应用中使用(不必关心你所采用的是什么web应用框架),只能用在基于web的Spring ApplicationContext环境。
  (1)当一个bean的作用域为Singleton,那么Spring IoC容器中只会存在一个共享的bean实例,并且所有对bean的请求,只要id与该bean定义相匹配,则只会返回bean的同一实例。Singleton是单例类型,就是在创建起容器时就同时自动创建了一个bean的对象,不管你是否使用,他都存在了,每次获取到的对象都是同一个对象。注意,Singleton作用域是Spring中的缺省作用域。要在XML中将bean定义成singleton,可以这样配置:
(2)当一个bean的作用域为Prototype,表示一个bean定义对应多个对象实例。Prototype作用域的bean会导致在每次对该bean请求(将其注入到另一个bean中,或者以程序的方式调用容器的getBean()方法)时都会创建一个新的bean实例。Prototype是原型类型,它在我们创建容器的时候并没有实例化,而是当我们获取bean的时候才会去创建一个对象,而且我们每次获取到的对象都不是同一个对象。根据经验,对有状态的bean应该使用prototype作用域,而对无状态的bean则应该使用singleton作用域。在XML中将bean定义成prototype,可以这样配置:

<bean id="account" class="com.foo.DefaultAccount" scope="prototype"/>  
 <!--或者-->
<bean id="account" class="com.foo.DefaultAccount" singleton="false"/> 

(3)当一个bean的作用域为Request,表示在一次HTTP请求中,一个bean定义对应一个实例;即每个HTTP请求都会有各自的bean实例,它们依据某个bean定义创建而成。该作用域仅在基于web的Spring ApplicationContext情形下有效。考虑下面bean定义:

<bean id="loginAction" class=com.foo.LoginAction" scope="request"/>

针对每次HTTP请求,Spring容器会根据loginAction bean的定义创建一个全新的LoginAction bean实例,且该loginAction bean实例仅在当前HTTP request内有效,因此可以根据需要放心的更改所建实例的内部状态,而其他请求中根据loginAction bean定义创建的实例,将不会看到这些特定于某个请求的状态变化。当处理请求结束,request作用域的bean实例将被销毁。
  (4)当一个bean的作用域为Session,表示在一个HTTP Session中,一个bean定义对应一个实例。该作用域仅在基于web的Spring ApplicationContext情形下有效。考虑下面bean定义:

<bean id="userPreferences" class="com.foo.UserPreferences" scope="session"/>

针对某个HTTP Session,Spring容器会根据userPreferences bean定义创建一个全新的userPreferences bean实例,且该userPreferences bean仅在当前HTTP Session内有效。与request作用域一样,可以根据需要放心的更改所创建实例的内部状态,而别的HTTP Session中根据userPreferences创建的实例,将不会看到这些特定于某个HTTP Session的状态变化。当HTTP Session最终被废弃的时候,在该HTTP Session作用域内的bean也会被废弃掉。
  (5)当一个bean的作用域为Global Session,表示在一个全局的HTTP Session中,一个bean定义对应一个实例。典型情况下,仅在使用portlet context的时候有效。该作用域仅在基于web的Spring ApplicationContext情形下有效。考虑下面bean定义:

<bean id="user" class="com.foo.Preferences "scope="globalSession"/>

global session作用域类似于标准的HTTP Session作用域,不过仅仅在基于portlet的web应用中才有意义。Portlet规范定义了全局Session的概念,它被所有构成某个portlet web应用的各种不同的portlet所共享。在global session作用域中定义的bean被限定于全局portlet Session的生命周期范围内。

面试常考问题

1.什么是spring?
2.spring框架的设计目标,设计理念和核心是什么?
3.spring的优缺点?
4.spring的应用场景
5.spring的组成模块
6.spring用到了哪些设计模式?
7.控制反转IOC和切面编程AOP
8.BeanFactory和ApplicationContext的区别?

spring测试案例

简单例子:用户购买汽车
1.spring-car配置文件

<?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="car" class="com.xiaoliu.pojo.Car"></bean>
    <!--调用有参构造方法-->
    <bean class="com.xiaoliu.pojo.Car" id="car1">
        <constructor-arg index="0" name="brand" value="奥迪"></constructor-arg>
        <constructor-arg index="1" name="corp" value="北气集团"></constructor-arg>
        <constructor-arg index="2" name="price" type="double" value="500000"></constructor-arg>
        <constructor-arg index="3" name="maxpeed" type="int" value="200"></constructor-arg>
    </bean>
    <!--调用get/set方法-->
    <bean class="com.xiaoliu.pojo.Car" id="car2">
        <property name="brand" value="jeep"></property>
        <property name="corp" value="上海集团"></property>
        <property name="maxpeed" value="180"></property>
        <property name="price"  value="100000"></property>
    </bean>
</beans>

2.spring-person.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" xmlns:p="http://www.springframework.org/schema/p"
       xmlns:util="http://www.springframework.org/schema/util"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/util https://www.springframework.org/schema/util/spring-util.xsd">
    <!--调用无参构造方法,singletion默认单例模式创建-->
    <bean class="com.xiaoliu.pojo.Person" id="person" scope="singleton"></bean>
    <!--调用有参构造方法-->
    <bean class="com.xiaoliu.pojo.Person" id="person1">
        <constructor-arg index="0" name="name"  type="java.lang.String"  value="小牛"></constructor-arg>
        <constructor-arg index="1" name="money" type="int" value="1000000"></constructor-arg>
    </bean>
    <!--调用get/set方法-->
    <bean id="person2" class="com.xiaoliu.pojo.Person">
        <property name="name" value="大哈"></property>
        <property name="money" value="200000"></property>
    </bean>
    <!-- 依赖关系-->
    <bean name="pYn" class="com.xiaoliu.pojo.Person">
        <property name="Mycar">
            <bean class="com.xiaoliu.pojo.Car" p:brand="北汽" p:maxpeed="100" p:price="2000000"></bean>
        </property>
    </bean>
    <!-- 集合-->
    <bean class="com.xiaoliu.pojo.Car" name="c1" p:price="100000" p:maxpeed="100" p:corp="北汽"  p:brand="奥迪"></bean>
    <bean class="com.xiaoliu.pojo.Car" name="c2" p:price="200000" p:maxpeed="200" p:corp="北汽" p:brand="宝马"></bean>
    <bean class="com.xiaoliu.pojo.Car" name="c3" p:price="300000" p:maxpeed="100" p:corp="北汽"  p:brand="奔驰"></bean>
    <bean class="com.xiaoliu.pojo.Car" name="c4" p:price="400000" p:maxpeed="120" p:corp="北汽"  p:brand="红旗"></bean>
    <bean id="person3" class="com.xiaoliu.pojo.Person">
        <property name="car">
            <list>
                <ref bean="c1"></ref>
                <ref bean="c2"></ref>
                <ref bean="c3"></ref>
                <ref bean="c4"></ref>
            </list>
        </property>
    </bean>
    <!--集合-->
    <util:list id="carlist">
        <ref bean="c1"></ref>
        <ref bean="c2"></ref>
        <ref bean="c3"></ref>
        <ref bean="c4"></ref>
    </util:list>
    <bean id="person4" class="com.xiaoliu.pojo.Person" p:car-ref="carlist" p:name="哆啦A蒙" p:money="10000000"></bean>
</beans>

3.Car和person的pojo

package com.xiaoliu.pojo;

public class Car {
    
    
    private String brand;
    private String corp;
    private double price;
    private int maxpeed;
    public Car(){
    
    
        System.out.println("调用无参构造方法car");
    }
    public Car(String brand,String corp,double price,int maxpeed){
    
    
        this.brand = brand;
        this.corp = corp;
        this.price = price;
        this.maxpeed = maxpeed;
    }

    public void setBrand(String brand) {
    
    
        this.brand = brand;
    }

    public void setCorp(String corp) {
    
    
        this.corp = corp;
    }

    public void setMaxpeed(int maxpeed) {
    
    
        this.maxpeed = maxpeed;
    }

    public void setPrice(double price) {
    
    
        this.price = price;
    }

    public double getPrice() {
    
    
        return price;
    }

    @Override
    public String toString() {
    
    
        return "Car{" +
                "brand='" + brand + '\'' +
                ", corp='" + corp + '\'' +
                ", price=" + price +
                ", maxpeed=" + maxpeed +
                '}';
    }
}

package com.xiaoliu.pojo;

import java.util.ArrayList;
import java.util.List;

public class Person {
    
    
    private String name;
    private int money;
    private List<Car> car;
    private Car mycar;
    private int CarCount;
    public Person(){
    
    
        System.out.println("调用无参构造方法person");
    }
    public Person(String name,int money){
    
    
        car = new ArrayList<>();
        this.name = name;
        this.money = money;
    }
    public void setMycar(Car car){
    
    
        this.mycar = car;
    }
    public int getCarCount() {
    
    
        return car.size();
    }
    public String getName() {
    
    
        return name;
    }
    public void addCar(Car c){
    
    
        this.car.add(c);
    }
    public void setCarCount(int carCount) {
    
    
        this.CarCount = carCount;
    }

    public void setMoney(int money) {
    
    
        this.money = money;
    }

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

    public int getMoney() {
    
    
        return money;
    }
    public void showCar(){
    
    
        System.out.println("车库有:"+getCarCount()+"辆");
        if(getCarCount()>0){
    
    
            for(Car c:car){
    
    
                System.out.println(c.toString());
            }
        }
    }

    public void setCar(List<Car> car) {
    
    
        this.car = car;
    }
}

4.Test测试类

在这里插入代码片
```package com.xiaoliu.test;

import com.xiaoliu.pojo.Car;
import com.xiaoliu.pojo.Person;
import org.junit.Test;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

public class BuyCar {
    
    
@Test
//有参构造方法
    public void buyCar(){
    
    
    ApplicationContext at1 = new ClassPathXmlApplicationContext("spring-car.xml");//
    System.out.println("a----------------");
    ApplicationContext at2 = new ClassPathXmlApplicationContext("spring-person.xml");
    System.out.println("b----------------");
    Car c1 = at1.getBean("car1",Car.class);
    Person p1 = at2.getBean("person1",Person.class);
    int moneyP1 = p1.getMoney();
    double carC1 = c1.getPrice();
    if(moneyP1>=carC1){
    
    
        p1.setMoney((int)(moneyP1-carC1));
        p1.addCar(c1);
        System.out.println(p1.getName()+"恭喜你购买成功!"+c1.toString());
    }else{
    
    
        System.out.println("余额不足!");
       }
    System.out.println("----------------------");
    p1.showCar();
    }
    @Test
    //无参
    public void buyCar1(){
    
    
       ApplicationContext at1 = new ClassPathXmlApplicationContext("spring-car.xml");
       ApplicationContext at2 = new ClassPathXmlApplicationContext("spring-person.xml");
        System.out.println("----------------------");
        //Person p1 = (Person) at2.getBean("person");

    }
    @Test
    public void showCar(){
    
    
        ApplicationContext at2 = new ClassPathXmlApplicationContext("spring-person.xml");
        Person person = at2.getBean("person3",Person.class);
        person.showCar();
    }
} 

猜你喜欢

转载自blog.csdn.net/cout_s/article/details/120268671