Spring的意义:以一个具体场景说明spring IOC的意义
我们知道spring是一个非常通用的框架,几乎所有java企业开发的用户都用到了spring,这是为什么呢?spring有什么意义呢?
我们知道软件开发中有个非常著名的原则,叫开闭原则,即对扩展开发,而对修改关闭。spring的意义就在于使用它可以很方便的开发出符合开闭原则的软件。
下面我们通过实例说明。假定我们有这么一个场景,计算打折,我们知道打折有很多不同的算法,而有可能会需要不停的加入新的打折算法。这里对应到开闭元则中就是对添加新的打折算法是开发的,而对于之前的代码修改是要关闭的。
打折算法的计算其实是经典的策略模式,我们可以把计算打折作为一种策略类抽象出来。我们首先定义计算打折逻辑的接口,其代码如下:
package cn.outofmemory.spring; public interface DiscountLogic { double calcDiscount(double price); }
这个接口只有一个方法calcDiscount(price),接受一个原始价格,计算出打折之后的价格。
我们实现了两种不同的打折,算法,一种是按配置好的折扣打折,另一种是0折扣,就是不打折,两种算法的实现类如下:
package cn.outofmemory.spring; public class SimpleDiscountLogic implements DiscountLogic { private int discountRate; public int getDiscountRate() { return discountRate; } public void setDiscountRate(int discountRate) { this.discountRate = discountRate; } @Override public double calcDiscount(double price) { return price * this.discountRate / 100; } }
package cn.outofmemory.spring; public class LazyDiscountLogic implements DiscountLogic { @Override public double calcDiscount(double price) { return price; } }
假定我们的应用中就是这两个打折算法的实现,有了打折算法,还需要具体计算打折的类Discount,这个类有一个打折逻辑discountLogic的属性,可以通过属性指定不同的打折算法,他的实现如下。
package cn.outofmemory.spring; public class Discount { private DiscountLogic discountLogic; public DiscountLogic getDiscountLogic() { return discountLogic; } public void setDiscountLogic(DiscountLogic discountLogic) { this.discountLogic = discountLogic; } public double getDiscountPrice(double price) { return this.discountLogic.calcDiscount(price); } }
这样涉及到的类就都就绪了,我们看下如何在spring的配置文件中配置这些类,以便方便的切换不同的打折算法。spring配置文件的内容如下:
<?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 class="cn.outofmemory.spring.SimpleDiscountLogic" id="simple"> <property name="discountRate" value="80" /> </bean> <bean class="cn.outofmemory.spring.Discount"> <property name="discountLogic" ref="simple" /> </bean> </beans>
在spring的配置文件中,我们定义了两个bean,一个是SimpleDiscountLogic的simple实例;另一个bean是Discount类,他的属性discountLogic引用了simple。
我们看下如何使用,App类代码:
package cn.outofmemory.spring; import org.springframework.context.ApplicationContext; import org.springframework.context.support.ClassPathXmlApplicationContext; public class App { public static void main(String[] args) { ApplicationContext appContext = new ClassPathXmlApplicationContext("/spring.xml"); Discount discount = appContext.getBean(Discount.class); double price = 10.9d; double dis = discount.getDiscountPrice(price); System.out.println("discount price is " + dis); } }
在main方法中我们首先初始化了ApplicationContext的实例,然后获得了配置文件中定义的discount实例,然后就可以使用discount实例计算折扣了。
写到这里似乎没有显示出spring ioc的意义,别急,我们继续,加入我们需要另一个折扣算法,商品在每天的早上9点10分到9点半之间打五折,其他时间打7折,这就需要一个新的打折逻辑类,我们实现如下:
package cn.outofmemory.spring; import java.util.Calendar; public class TimedDiscount implements DiscountLogic { @Override public double calcDiscount(double price) { Calendar cal = Calendar.getInstance(); int hour = cal.get(Calendar.HOUR_OF_DAY); int minute = cal.get(Calendar.MINUTE); if (hour == 9 && minute <= 20) { return price * .5; } return price * .7; } }
我们添加了一种新的打折算法,这是对扩展开放了,也没修改原有的代码,利用spring的ioc就可以将这个类应用到Discount实例上。
我们只需要修改spring的配置文件:
<?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 class="cn.outofmemory.spring.SimpleDiscountLogic" id="simple"> <property name="discountRate" value="80" /> </bean> <bean class="cn.outofmemory.spring.TimedDiscountLogic" id="timed"/> <bean class="cn.outofmemory.spring.Discount"> <property name="discountLogic" ref="timed" /> </bean> </beans>
我们在spring配置文件中添加了TimedDiscountLogic的实例timed,并且将Discount实例的discountLogic属性的实例设置为timed,再次运行程序可以看到已经使用上新的打折算法了。
使用spring的IOC可以很容易的实现开闭原则,这样设计的软件更容易维护。
共同学习,写下你的评论
评论加载中...
作者其他优质文章