Spring学习二

Spring的表达式语言 SpEL,使用方法是#{}

SpEL的特性如下

  • 使用Bean 的ID 来引用Bean ;
  • 调用方法和访问对象的属性;
  • 对值进行算术、关系和逻辑运算;
  • 正则表达式匹配;
  • 集合操作。

目前能知道的SpEL的作用就是在运行期赋值,正常情况下我们在配置bean的xml档的时候就会赋值,而使用SpEL能达成动态的效果???

具体详细应用请查看http://blog.csdn.net/sunnyyoona/article/details/50638957

简单代码应用

<bean id="car" class="com.test2.Car" >
<property name="factory" value="#{'china'}"></property>
<property name="price" value="#{600}"></property>
<property name="year" value="#{5}"></property>
<property name="city" value="#{'shanghai'}"></property>
</bean> <bean id="person" class="com.test2.Person">
<property name="name" value="xiaozhi"></property>
<property name="age" value="23"></property>
<property name="car" value="#{car}"></property>
<property name="city" value="#{car.city}"></property>
<property name="info" value="#{car.price>800?'gold':'white'}"></property>
</bean> 在原先的Person类多city ,原先的Car类多city。测试类不再赘述。

Bean的生命周期

1实例化bean

2给bean属性赋值和其他bean的引用

3bean的初始构造方法

4bean的使用

5bean的销毁

用 init-method 和destroy-mothod指定bean的构造方法和销毁方法

Spring学习二

具体生命周期          http://www.cnblogs.com/zrtqsk/p/3735273.html

二、各种接口方法分类

Bean的完整生命周期经历了各种方法调用,这些方法可以划分为以下几类:

1、Bean自身的方法  :  这个包括了Bean本身调用的方法和通过配置文件中<bean>的init-method和destroy-method指定的方法

2、Bean级生命周期接口方法  :  这个包括了BeanNameAware、BeanFactoryAware、InitializingBean和DiposableBean这些接口的方法

3、容器级生命周期接口方法  :  这个包括了InstantiationAwareBeanPostProcessor 和 BeanPostProcessor 这两个接口实现,一般称它们的实现类为“后处理器”。

4、工厂后处理器接口方法  :  这个包括了AspectJWeavingEnabler, ConfigurationClassPostProcessor, CustomAutowireConfigurer等等非常有用的工厂后处理器  接口的方法。工厂后处理器也是容器级的。在应用上下文装配配置文件之后立即调用。

以下代码实现。

package com.test2;

public class Address {//新写的类
private String city;
private String name;
public String getCity() {
return city;
}
public void setCity(String city) {
this.city = city;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public void init (){//名字可以自己取,不用init也行,在后面的init-method里面写对应的名字就是
System.out.println("我init()啦");
}
public void destory(){
System.out.println("我destory()啦");
}
@Override
public String toString() {
return "Address [city=" + city + ", name=" + name + "]";
} }

接口类! 很重要

package com.test2;

import org.springframework.beans.BeansException;
import org.springframework.beans.factory.config.BeanPostProcessor; public class MyPostProfessor implements BeanPostProcessor{//这个有很多类似的接口,可以自己取看。另外这是Bean级别的,意思是每个Bean都享用这个。 public Object postProcessAfterInitialization(Object bean, String beanname)
throws BeansException {
System.out.println("after name:"+beanname+" object:"+bean); return bean;
} public Object postProcessBeforeInitialization(Object bean, String beanname)
throws BeansException {
System.out.println("before name:"+beanname+" object:"+bean);
if (beanname.equals("address")){//这里是判断bean文档写的bean 加载id 判断之后进行修改。
Address address =(Address)bean;
address.setCity("上海");
return address;
}
return bean;
} }

bean 文件

<bean id="address" class="com.test2.Address" init-method="init"   destroy-method="destory"></bean>
<!-- 后置处理器 填写自己实现的对应接口类 -->
<bean id="beanprocessor" class="com.test2.MyPostProfessor"></bean>

测试代码以及输出、

package com.test2;

import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext; import com.test2.Person; public class Main {
public static void main(String[] args) {
ClassPathXmlApplicationContext context = new ClassPathXmlApplicationContext("Beans.xml");//在工程目录下读取bean的配置。
Address address = null;
context.close();
}
}
/*
输出
before name:address object:Address [city=null, name=null]
我init()啦
after name:address object:Address [city=上海, name=null]
九月 12, 2017 11:07:10 上午 org.springframework.context.support.ClassPathXmlApplicationContext doClose
信息: Closing org.springframework.context.support.ClassPathXmlApplicationContext@21b8d17c: startup date [Tue Sep 12 11:07:10 CST 2017]; root of context hierarchy
我destory()啦
*/
这个就可以对应上面的周期来看

注入bean还有一个方法,静态工厂方法和实例工厂方法

工厂方法,就是将创建的bean的过程封装在方法里面,需要的时候就直接使用,而不在意过程。

静态工厂模式则是   在bean中加入 factory-method  构造函数需要输入参数值则用 <constructor-arg value="fute" />

实例工厂方法,则是实例化工厂,之后再注入,java文件也写得很不一样,仔细看。

package com.test2;//静态工厂类

import java.util.HashMap;
import java.util.Map; public class StaticFactory {//静态工厂方法
private static Map<String,Car> hm = new HashMap<String,Car>(); static {
hm.put("fute", new Car("futo",60000));
hm.put("kaite", new Car("kaite",30000));
}
public static Car getCar (String name){//这里要用静态方法,不然会错误。
return hm.get(name);
}
} package com.test2;//实例类 import java.util.HashMap;
import java.util.Map; public class InstanceFactory {
private Map<String,Car> hm = null;
public InstanceFactory(){
hm=new HashMap<String,Car>();
hm.put("fute", new Car("futo",60000));
hm.put("kaite", new Car("kaite",30000));
}
public Car getCar (String name){
return hm.get(name);
}
}

bean文件添加,测试文件类不再写

<!-- 这里不是实例化com.test2.StaticFactory,而是实例化Car,如果有参数这用 constructor-arg来使用 -->
<bean id="car" class="com.test2.StaticFactory" factory-method="getCar">
<constructor-arg value="fute" />
</bean> <!--实例化工厂注入bean,就是先实例化工厂,之后再注入,class文件写的也不一样,要仔细看。 -->
<bean id= "insfactory" class="com.test2.InstanceFactory"></bean>
<bean id="car2" factory-bean="insfactory" factory-method="getCar">
<constructor-arg value="kaite"></constructor-arg>
</bean>

利用FactoryBean 来配置  Bean(据说整合框架很需要用到)

package com.test2;

import org.springframework.beans.factory.FactoryBean;

public class MyFactoryBean implements FactoryBean{//实现这个接口

    private double price;

    public double getPrice() {
return price;
} public void setPrice(double price) {
this.price = price;
} public Object getObject() throws Exception {//这是正常返回的object
Car car = new Car("test",price);
return car;
} public Class getObjectType() {
// TODO Auto-generated method stub
return null;
} public boolean isSingleton() {
// TODO Auto-generated method stub
return false;
} }

bean填写

<!-- 属性设置的是MyFactoryBean的属性,但是它会返回一个Car  -->
<bean id="carf" class="com.test2.MyFactoryBean">
<property name="price" value="5000"></property>
</bean>
上一篇:让你成功安装vscode中go的相关插件


下一篇:Matplotlib中文乱码问题