当前位置: 首页 > news >正文

泰安工程建设信息网站wordpress文章新窗口打开

泰安工程建设信息网站,wordpress文章新窗口打开,虚拟商城平台,带着做计算机项目的网站1. 什么是模板方法模式 模板方法模式(Template Method Pattern)是一种行为设计模式,它在操作中定义算法的框架,将一些步骤推迟到子类中。模板方法让子类在不改变算法结构的情况下重新定义算法的某些步骤。 模板方法模式的定义&…

1. 什么是模板方法模式

模板方法模式(Template Method Pattern)是一种行为设计模式,它在操作中定义算法的框架,将一些步骤推迟到子类中。模板方法让子类在不改变算法结构的情况下重新定义算法的某些步骤。
在这里插入图片描述

模板方法模式的定义:

在操作中定义算法的框架,并将一些步骤延迟到子类中。模板方法使得子类可以在不改变算法结构的情况下重新定义算法的某些步骤。

模板方法中的算法可以理解为广义上的业务逻辑,并不是特指某一个实际的算法。定义中所说的算法的框架就是模板,包含算法框架的方法就是模板方法。
在这里插入图片描述

模板方法模式包含以下主要角色:

  • 抽象父类:定义一个算法所包含的所有步骤,并提供一些通用的方法逻辑。
  • 具体子类:继承自抽象父类,根据需要重写父类提供的算法步骤中的某些步骤。

抽象类(Abstract Class):负责给出一个算法的轮廓和骨架。它由一个模板方法和若干个基本方法构成。

  • 模板方法:定义了算法的骨架,按某种顺序调用其包含的基本方法。

  • 基本方法:是实现算法各个步骤的方法,是模板方法的组成部分。基本方法又可以分为三种:

    • 抽象方法(Abstract Method):一个抽象方法由抽象类声明、由其具体子类实现。
    • 具体方法(Concrete Method):一个具体方法由一个抽象类或具体类声明并实现,其子类可以进行覆盖也可以直接继承。
    • 钩子方法(Hook Method):在抽象类中已经实现,包括用于判断的逻辑方法和需要子类重写的空方法两种。一般钩子方法是用于判断的逻辑方法,这类方法名一般为isXxx,返回值类型为boolean类型。

钩子:在模板方法的父类中,我们可以定义一个方法,它默认不做任何事,子类可以视情况要不要覆盖它,该方法称为“钩子”。钩子方法一般是空的或者有默认实现。钩子的存在,可以让子类有能力对算法的不同点进行挂钩。而要不要挂钩,又由子类去决定。

2. 代码示例

/*** 抽象父类*/
public abstract class AbstractClassTemplate {void step1(String key) {System.out.println("在模板类中 -> 执行步骤1");if (step2(key)) {step3();} else {step4();}step5();}boolean step2(String key) {System.out.println("在模板类中 -> 执行步骤2");return "x".equals(key);}abstract void step3();abstract void step4();void step5() {System.out.println("在模板类中 -> 执行步骤5");}void run(String key) {step1(key);}
}public class ConcreteClassA extends AbstractClassTemplate {@Overridevoid step3() {System.out.println("在子类A中 -> 执行步骤 3");}@Overridevoid step4() {System.out.println("在子类A中 -> 执行步骤 4");}
}public class ConcreteClassB extends AbstractClassTemplate {@Overridevoid step3() {System.out.println("在子类B中 -> 执行步骤 3");}@Overridevoid step4() {System.out.println("在子类B中 -> 执行步骤 4");}
}public class Test01 {public static void main(String[] args) {AbstractClassTemplate concreteClassA = new ConcreteClassA();concreteClassA.run("");System.out.println("===========");AbstractClassTemplate concreteClassB = new ConcreteClassB();concreteClassB.run("x");}
}// 输出结果
在模板类中 -> 执行步骤1
在模板类中 -> 执行步骤2
在子类A-> 执行步骤 4
在模板类中 -> 执行步骤5
===========
在模板类中 -> 执行步骤1
在模板类中 -> 执行步骤2
在子类B-> 执行步骤 3
在模板类中 -> 执行步骤5
3. JdbcTemplate应用模板方法模式

在原生JDBC操作中,需要执行以下步骤:

  1. 获取connection
  2. 获取statement
  3. 获取resultset
  4. 遍历resultset并封装成集合
  5. 依次关闭connection, statement, resultset,并考虑各种异常

上面步骤中大多数都是重复的、可复用的,只有在遍历ResultSet并封装成集合的步骤是可定制的。每张表都映射不同的Java bean,这部分代码是没有办法复用的,只能定制。

// 模板方法,用来执行 JDBC 操作,返回结果集或受影响的行数
protected <T> T execute(ConnectionCallback<T> action, boolean enforceReadOnly) throws DataAccessException {Assert.notNull(action, "Callback object must not be null");Connection con = DataSourceUtils.getConnection(obtainDataSource());try {boolean readOnly = enforceReadOnly || isReadOnly();// 设置是否为只读连接prepareConnection(con, readOnly);// 执行具体的 JDBC 操作,该方法为子类实现T result = action.doInConnection(con);// 提交事务DataSourceUtils.commitIfNecessary(con, getDataSource());// 返回结果集或受影响的行数return result;} catch (SQLException ex) {// 回滚事务DataSourceUtils.rollbackIfNecessary(con, getDataSource());throw translateException("Callback", getSql(action), ex);} finally {DataSourceUtils.releaseConnection(con, getDataSource());}
}// 执行给定的 SQL 语句和参数,返回查询结果
public <T> T query(final String sql, final ResultSetExtractor<T> rse, Object... args) throws DataAccessException {Assert.notNull(sql, "SQL must not be null");Assert.notNull(rse, "ResultSetExtractor must not be null");// 匿名内部类,实现 ConnectionCallback 接口return execute(new ConnectionCallback<T>() {@Overridepublic T doInConnection(Connection con) throws SQLException {PreparedStatement ps = null;ResultSet rs = null;try {// 创建 PreparedStatement 对象ps = createPreparedStatement(con, sql);// 设置 PreparedStatement 的参数setValues(ps, args);// 执行查询,返回结果集rs = ps.executeQuery();// 对结果集进行处理,返回查询结果return rse.extractData(rs);} finally {JdbcUtils.closeResultSet(rs);JdbcUtils.closeStatement(ps);}}}, true);
}

4. 运用模板方法手写简单版JdbcTemplate

  1. 定义DefineJcbcTemplate自定义jdbcTemplate接口
public interface DefineJcbcTemplate {<T> T queryForObject(String sql, DefineRowMapper<T> defineRowMapper);
}
  1. 定义DefineRowMapper函数式接口,回调作用,处理jdbc查询结果ResultSet,返回泛型T对象
@FunctionalInterface
public interface DefineRowMapper<T> {T mapRow(ResultSet rs) throws SQLException;
}
  1. DefineJcbcTemplateImpl实现类,该实现类的连接数据库、释放资源等操作都是从步骤一复制粘贴进来的,唯一不同的是把处理结果解耦出来了,定义好处理结果的接口DefineRowMapper,交由调用者去实现对结果的处理,最后回调该接口的方法mapRow并返回结果,其他的把连接数据库、释放资源封装起来,这样一来不用每次进行数据库查询都需要连接数据库、释放资源。
@Service
public class DefineJcbcTemplateImpl implements DefineJcbcTemplate {@Autowiredprivate DataSource dataSource;@Overridepublic <T> T queryForObject(String sql, DefineRowMapper<T> defineRowMapper) {// 一部分是准备和释放资源以及执行 SQL 语句,另一部分则是处理 SQL 执行结果Connection connection = null;PreparedStatement preparedStatement = null;ResultSet resultSet = null;try {// 创建dataSource,获取连接connection = dataSource.getConnection();// 执行查询preparedStatement = connection.prepareStatement(sql);// 获取执行结果resultSet = preparedStatement.executeQuery();// 交由调用者去实现对结果的处理return defineRowMapper.mapRow(resultSet);} catch (Exception e) {e.printStackTrace();} finally {// 关闭资源if (preparedStatement != null) {try {preparedStatement.close();} catch (SQLException e) {e.printStackTrace();}}if (connection != null) {try {connection.close();} catch (SQLException e) {e.printStackTrace();}}}return null;}
}
  1. 调用自定义模板方法进行数据库查询
@RunWith(SpringRunner.class)
@SpringBootTest(classes = TestSpringTemplateApplication.class)
public class TestSpringTemplateApplicationTests {@Autowiredprivate DefineJcbcTemplate defineJcbcTemplate;@Testpublic void testQueryForObject() {// 定义sqlString sql = "SELECT * FROM user";// 通过模版方法进行查询List<User> users = defineJcbcTemplate.queryForObject(sql, (rs) -> {List<User> result = new ArrayList<>();while (rs.next()) {// 遍历ResultSet并封装成集合User user = new User();user.setId(rs.getInt("id"));user.setName(rs.getString("name"));user.setEmail(rs.getString("email"));result.add(user);}return result;});System.out.println(users);}
}

通过上面的代码,您可以看到模板方法模式可以很容易地将重复的部分代码提取到父类中,而将可变的部分代码放入子类中,从而实现代码的复用和扩展。

http://www.yayakq.cn/news/635263/

相关文章:

  • 会员制网站 建设网页微博怎么下载视频
  • 徐州网站建设托管免费云主机网址
  • 怎么用ip访问vps网站风中有朵雨做的云在线网站
  • 重庆企业免费建站手机网站建设实验报告
  • 手机能用的网站注册安全工程师报考时间2023
  • 保定网站建设费用音乐网站怎么做无线增值业务
  • 网站建设与规划实训报告企查查企业查询平台
  • 新手快速建设网站小广告多的网站
  • 专业制作网站推荐青岛免费网站建设
  • 国外免费网站西宁城西区建设局网站
  • 用php做网站的开发工具自己有域名怎么建网站
  • 浙江专业做网站北京装修公司排名推荐
  • 一个网站域名一年要多少钱网站做站群
  • 电商网站建设与管理学徒制下的课程网站建设
  • wordpress接口开发seo第三方点击软件
  • 苗木推广做哪个网站好js获取网站域名
  • 迁安做网站网址二维码在线生成
  • 现在做什么网站好Drupal对比WordPress
  • 三合一网站制作价格公司logo设计大全 效果图
  • 无忧建站自己0基础怎么创业
  • 用python语言做网站深圳证券网站开发
  • 家政服务网站模板网站建设需求分析流程图
  • 完整网站模板下载蚌埠 网站制作
  • 大连微信网站制作怎么做创业网站
  • 郑州一站式网站搭建网站制作和维护费用
  • 自动做图在线网站苏州聚尚网络科技有限公司
  • 惠阳东莞网站建设怎么查看网站是用什么系统做的
  • 企业建站套餐thinkphp wordpress
  • 建网站空间都有什么平台app界面设计常用的布局具有哪些
  • 佛山网站建设公司哪家比较好微分销手机网站制作