结合Spring实现设计模式与面向接口编程(不断更新中...)
在学设计模式的时候,遇到的一个比较大的问题就是,虽然设计模式可以解决很多的重用性、解耦和的问题,但是最后在类之间建立关系的时候,还是需要显示的编写代码,在代码修改的时候,还是需要修改比较大量的代码,现在结合Spring,设计好类结构以后,就可以进行容器外类依赖注入,这是非常好的思想,不仅在更深程度实现了解耦和,同时让程序员更关注业务,而不是实现,真正实现面向接口的编程,可以说,纯设计模式是将类关系延迟到子类,而在Spring中,我认为类关系延迟到了容器外,或者直接说延迟到了XML文件中(不仅仅是XML配置文件,还有注解),通过简单的配置文件修改,就可以修改程序整个的类依赖关系.在我们实际开发过程中,我们完全可以设计好接口的结构,完全不用管实现类,在接口设计合理后,再进行实现,那么只需要添加配置文件的内容就可以实现程序的运转
?
工厂模式:
我们很了解这个模式,对于面向接口编程的思想,我们只需要定义接口,然后利用Spring进行装配,实现结束以后,再将实现类的类名写入配置文件中去。
工厂模式类图
?
?
?
????????????? applicationContext.xml文件结构图
?
?
客户端使用代码:
????????????????????????????????????????????????????? view plaincopy to clipboardprint?
package org.ys.spring.factory;??
?
???
?
import org.springframework.context.ApplicationContext;??
?
import org.springframework.context.support.ClassPathXmlApplicationContext;??
?
???
?
public class Test {??
?
???
?
??? public static void main(String[] args) {??
?
?????? ApplicationContext cs = new ClassPathXmlApplicationContext(??
?
????????????? "applicationContext.xml");??
?
?????? IFactory bean = (IFactory) cs.getBean("factory");??
?
?????? bean.createProduct().operation();??
?
??? }??
?
}?
package org.ys.spring.factory;
?
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
?
public class Test {
?
??? public static void main(String[] args) {
?????? ApplicationContext cs = new ClassPathXmlApplicationContext(
????????????? "applicationContext.xml");
?????? IFactory bean = (IFactory) cs.getBean("factory");
?????? bean.createProduct().operation();
??? }
}
?
?
如果我们需要更改工厂或者产品,我们就可以在配置文件,将红色线内的字符串进行修改就可以,完全不用修改任何代码,
?
?
单例模式:
在默认的情况下,Spring中的bean都是单例模式,只是这个单例,不是通过代码限制,而是通过Spring容器限制,也就是说如果你想通过Spring获得对象时,这个对象是单例的。
?
?结构型模式中的组合模式
类图:
?
?相信大家也都很熟悉这个设计模式,applicationContext.xml文件结构图:
?
代码如下:
?????????????????????? view plaincopy to clipboardprint?
<?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-2.0.xsd">?
??? <bean id="factory"?
??????? abstract="true">?
??? </bean>?
??? <bean id="rootnode"?
??????? 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-2.0.xsd">
?<bean id="factory"
??abstract="true">
?</bean>
?<bean id="rootnode"
??encoding="UTF-8"?>?
<beans xmlns="http://www.springframework.org/schema/beans"?
??? xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"?
??? xmlns:context="http://www.springframework.org/schema/context"?
??? xmlns:aop="http://www.springframework.org/schema/aop"?
??? xmlns:tx="http://www.springframework.org/schema/tx"?
??? xsi:schemaLocation="??
??? http://www.springframework.org/schema/beans???
??? http://www.springframework.org/schema/beans/spring-beans-2.5.xsd???
??? http://www.springframework.org/schema/context???
??? http://www.springframework.org/schema/context/spring-context-2.5.xsd??
??? http://www.springframework.org/schema/aop??
??? http://www.springframework.org/schema/aop/spring-aop-2.5.xsd??
??? http://www.springframework.org/schema/tx??
??? http://www.springframework.org/schema/tx/spring-tx-2.5.xsd">?
?
??? <!-- tx: Spring注解的事务 -->?
??? <!-- context: Spring注解的依赖注入 -->?
??? <!-- aop: Spring注解的AOP -->?
?
??? <context:annotation-config />?
??? <!-- 使用注解的方式实现依赖注入 -->?
??? <!-- @Resource(name="")在字段上或者在set方法上 -->?
??? <aop:aspectj-autoproxy />?
??? <!-- 使用注解的方式实现AOP编程 -->?
??? <!-- 切面(类上): @Aspect -->?
??? <!-- 切点(方法上): @Pointout(execution(* package..*.*(..))) public void anyMethod(){} -->?
??? <!-- 通知(方法上): @Before("anyMethod") 代表在anyMethod这个切入点的前置通知-->?
??? <!-- 将切面交给Spring -->?
??? <bean id="aspectId" />?
??? <!-- 进行AOP配置 -->?
??? <aop:config>?
??????? <aop:aspect id="aspectI" ref="aspectId2">?
??????????? <aop:pointcut id="pointout"?
??????????????? expression="execution(* package..*.*(..))" />?
??????????? <aop:before method="切面类中的方法" pointcut-ref="pointout" />?
??????????? <aop:after-throwing method="抛出异常后执行"?
??????????????? pointcut-ref="pointout" />?
??????? </aop:aspect>?
??? </aop:config>?
?
??? <!-- 使用XML进行依赖注入 -->?
??? <bean id="factory"?
??????? abstract="true" factory-method="getTreeRoot">?
??? </bean>?
??? <bean id="rootnode"?
??????? value="驱动的包名加类名"></property>?
??????? <property name="url"?
??????????? value="jdbc:mysql://localhost:8080/databaseName">?
??????? </property>?
??????? <property name="username" value="root"></property>?
??????? <property name="password" value="***"></property>?
??????? <property name="initialSize" value="10"></property>?
??????? <property name="maxActive" value="100"></property>?
??????? <property name="maxIdle" value="20"></property><!-- 现在有500个空闲,释放连接的数,最多剩下20个 -->?
??????? <property name="minIdle" value="1"></property><!-- 最少链接的数,就算再少,也要有1个 -->?
??? </bean>?
??? <!-- Spring事务管理器 -->?
??? <bean id="txManager"?
??????? ref="dataSource"></property>?
??? </bean>?
?
??? <!-- Spring与JDBC使用注解 -->?
??? <tx:annotation-driven transaction-manager="txManager" />?
??? <!-- 接下来就可以进行进行数据库的增删改查的操作了,将DAO的实现类交给Spring -->?
??? <bean id="dao" ref="dataSource"></property>?
??????? <!-- 在dao实现类中,对DataSource变量进行注入 -->?
??? </bean>?
??? <!-- 然后就可以使用JdbcTemplate进行JDBC操作??
??????? JdbcTemplate template = new JdbcTemplate(dataSource);??
??????? //保存??
??????? template.update("insert into person values(?, ?)", new Object[]{1, "name"}, new int[]{java.sql.Types.INT, java.sql.Types.VARCHAR});??
??????? template.update("update person set name=? ", new Object[]{"name"}, new int[]{java.sql.Types.VARCHAR});??
??????? //查找??
??????? Object o = template.queryForObject("select * from person where id= ?", new Object[]{2}, new int[]{java.sql.Types.INT}, new RowMapper(){??
??????????????? public Object mapRow(ResultSet set, int index) {??
??????????????????? Person p = new Person();??
??????????????????? 从set中取得信息放入p??
??????????????????? return p;??
??????????????? }??
??????????? }??
??????? );??
??????? queryForObject返回一个对象??
??????? query返回多个对象,实际上返回List对象??
??????? queryFor...返回对应类型??
??????????
??????? 如果没有事务管理器,那么方法中的每条语句都会在自身的事务中执行,所以在类上加上??
??????? @Transactional??
??????? 那么在每个方法都是事务级的??
但是当需要在某个具体的方法上加上注解的时候,则涉及到事务的一些属性??
比如在方法上加上@Transactional(readonly=true,rollBackFor=Exception.class, propagation=Propagation.NOT_SUPPORT,isolation=Isolation.READ_COMMITTED)??
其中:readonly代表这个事务方法是只读的,不会插入修改,对于这样的方法,设置为true可以提高效率??
rollBackFor代表回滚原因,这里代表异常是Exception的回滚??
propagation代表事务传播方式,个人认为其主要关注点在于嵌套事务的处理方法。??
isolation就是代表事务的隔离级别??
?
?
?
??? -->?
</beans>
本文来自CSDN博客,转载请标明出处:http://blog.csdn.net/neusoftware_20063500/archive/2009/04/18/4090299.aspx