使用模板方法模式简化JDBC操作

在使用JDBC时,会重复的写很多重复的代码,例如

                Connection conn = null;
        PreparedStatement ps = null;
        ResultSet rs = null;
                String sql="insert into t_user(username,brithday) values(?,?)";
        try {
            conn = JdbcUtils.getConnection();
            ps = conn.prepareStatement(sql);

        } catch (SQLException e) {
            throw new DaoException(e.getMessage(), e);
        } finally {
            JdbcUtils.free(rs, ps, conn);
        }
    

这部分代码在数据库操作方法中都会有。因此我们可以把这部分不变的内容提取出来,作为一个公用的方法。

例如,我们的增,删,改操作可以这样写

/**
     * 增,删,改方法
     * @param sql
     * @param args sql参数
     * @return
     */
    public int update(String sql, Object[] args) {
        Connection conn = null;
        PreparedStatement ps = null;
        ResultSet rs = null;
        try {
            conn = JdbcUtils.getConnection();
            ps = conn.prepareStatement(sql);
            for (int i = 0; i < args.length; i++)
                ps.setObject(i + 1, args[i]);
            return ps.executeUpdate();
        } catch (SQLException e) {
            throw new DaoException(e.getMessage(), e);
        } finally {
            JdbcUtils.free(rs, ps, conn);
        }
    }

最麻烦的就是返回一个对象的操作了。因为我不知道要返回的对象是什么,所以在往对象里设值的时候就不确定了。因此我们可以在这个类里面定义一个抽象的方法,具体怎么实现,它的子类知道。

因此我们的这个类就可以这样设计了

package com.zzg.jdbc.base;

import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;

import com.zzg.jdbc.exception.DaoException;
import com.zzg.jdbc.util.JdbcUtils;

public abstract class BaseDao {

    /**
     * 增,删,改方法
     * @param sql
     * @param args sql参数
     * @return
     */
    public int update(String sql, Object[] args) {
        Connection conn = null;
        PreparedStatement ps = null;
        ResultSet rs = null;
        try {
            conn = JdbcUtils.getConnection();
            ps = conn.prepareStatement(sql);
            for (int i = 0; i < args.length; i++)
                ps.setObject(i + 1, args[i]);
            return ps.executeUpdate();
        } catch (SQLException e) {
            throw new DaoException(e.getMessage(), e);
        } finally {
            JdbcUtils.free(rs, ps, conn);
        }
    }

    /**
     * 返回一个对象
     * @param <T>
     * @param sql
     * @param args
     * @return
     */
    public <T> T find(String sql, Object[] args) {
        Connection conn = null;
        PreparedStatement ps = null;
        ResultSet rs = null;
        try {
            conn = JdbcUtils.getConnection();
            ps = conn.prepareStatement(sql);
            for (int i = 0; i < args.length; i++)
                ps.setObject(i + 1, args[i]);
            rs = ps.executeQuery();
            T t = null;
            if (rs.next()) {
                t = rowMapper(rs);
            }
            return t;
        } catch (SQLException e) {
            throw new DaoException(e.getMessage(), e);
        } finally {
            JdbcUtils.free(rs, ps, conn);
        }
    }

    /**
     * 返回一个List
     * @param <T>
     * @param sql
     * @param args
     * @return
     */
    public <T> List<T> list(String sql, Object[] args) {
        Connection conn = null;
        PreparedStatement ps = null;
        ResultSet rs = null;
        try {
            conn = JdbcUtils.getConnection();
            ps = conn.prepareStatement(sql);
            for (int i = 0; i < args.length; i++)
                ps.setObject(i + 1, args[i]);
            rs = ps.executeQuery();
            T t = null;
            List<T> list = new ArrayList<T>();
            while (rs.next()) {
                t = rowMapper(rs);
                list.add(t);
            }
            return list;
        } catch (SQLException e) {
            throw new DaoException(e.getMessage(), e);
        } finally {
            JdbcUtils.free(rs, ps, conn);
        }
    }

    abstract protected <T> T rowMapper(ResultSet rs) throws SQLException;

}

在使用时我们的类只需要继承上面那个类就可以了。

package com.zzg.jdbc.dao.impl;

import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.List;

import com.zzg.jdbc.base.BaseDao;
import com.zzg.jdbc.dao.UserDao;
import com.zzg.jdbc.domain.User;

public class UserDaoImpl extends BaseDao implements UserDao {

    @Override
    public User findUser(int id) {
        String sql = "select *from t_user where id=?";
        Object[] args = new Object[] { id };
        User user = super.find(sql, args);
        return user;
    }

    @Override
    public List<User> listUser(String username) {
        String sql = "select *from t_user where username=?";
        Object[] args = new Object[] { username };
        List<User> list = super.list(sql, args);
        for (User u : list) {
            System.out.println(u.getId());
        }
        return list;
    }

    @Override
    protected Object rowMapper(ResultSet rs) throws SQLException {
        User user = new User();
        user.setId(rs.getInt("id"));
        user.setUsername(rs.getString("username"));
        user.setBrithday(rs.getDate("brithday"));
        return user;
    }

}

附加分页的方法:

/**
     * 分页
     * @param tableName
     * @param PK
     * @param methodPageNum
     * @param methodNumPerPage
     * @param conditions
     * @param <T>
     * @return
     * @throws SQLException
     */
    public <T> List<T> getPageListResultSet(String tableName,String PK,int methodPageNum,int methodNumPerPage,Map<String,String> conditions) throws SQLException{
        int pageNum = methodPageNum==0?DEFAULT_PAGE_NUM:methodPageNum;
        int numPerPage = methodNumPerPage==0?DEFAULT_NUM_PER_PAGE:methodNumPerPage;
        List<T> list = null;
        DataSetOp dataSetOp = null;
        try {
           dataSetOp = new  DataSetOp();
            String PAGE_SQL_PREFIX = " SELECT * FROM (SELECT ROW_NUMBER() OVER(ORDER BY t1.ID DESC) AS ROW_NUM, t1.* FROM  ";
            String PAGE_SQL_END = " ) TT WHERE TT.ROW_NUM >? AND TT.ROW_NUM <= ? ";
            if(StringUtil.isNotBlank(PK)){
                PAGE_SQL_PREFIX = PAGE_SQL_PREFIX.replace("ID",PK);
            }
            StringBuffer sql = new StringBuffer(PAGE_SQL_PREFIX);
            sql.append(tableName).append(" t1 WHERE 1=1 ");
            //设置条件
            if(conditions!=null && conditions.size()>0){
                Set<String> key = conditions.keySet();
                for (Iterator it = key.iterator(); it.hasNext();) {
                    String column = (String) it.next();
                    //System.out.println(conditions.get(s));
                    StringBuffer cd = new StringBuffer(" and t1.");
                    cd.append(column).append("=‘").append(conditions.get(column)).append("‘ ");
                    sql.append(cd);
                }
            }
            sql.append(PAGE_SQL_END);
            System.out.println(sql);
            PreparedStatement ps = dataSetOp.getConnection().prepareStatement(sql.toString());
            ps.setInt(1, (pageNum - 1) * numPerPage);
            ps.setInt(2, pageNum*numPerPage);
            ResultSet rs = ps.executeQuery();
            T t = null;
            list = new ArrayList<T>();
            while (rs.next()) {
                t = rowMapper(rs);
                list.add(t);
            }
        } catch (DataException e) {
            e.printStackTrace();
        }finally{
            if(dataSetOp != null) dataSetOp.close();
        }
        return list;
    }
时间: 2024-08-22 00:11:09

使用模板方法模式简化JDBC操作的相关文章

使用Spring简化JDBC操作数据库

Spring的开发初衷是为了减轻企业级开发的复杂度,其对数据库访问的支持亦如此,使用Spring访问数据库能带来以下好处: 1.1     简化代码 使用原生的JDBC访问数据库,一般总是要执行以下步骤: 1)         获取数据库资源,例如连接等: 2)         准备并执行SQL,并处理返回结果 3)         释放数据库资源 4)         处理上述所有步骤出现的异常,处理异常的过程中也要捕获异常 典型的代码结构如下: public TestObj queryTes

使用Spring的jdbcTemplate进一步简化JDBC操作

先看applicationContext.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" xsi:schemaLocation="

Java Dao模式通过JDBC连接数据库的操作

Java程序访问数据库: 1.获取数据库厂商提供的驱动(jdbc接口的实现类) 如ojdbc14.jar——Oracle数据库驱动jar包 mysql-connector-java-5.1.8-bin.jar——MySQL数据库驱动jar包 自己去网上下载就行. 2.使用JDBC的API访问数据库 连接.SQL语句执行.结果 java.sql.Driver:各个数据库厂商需要实现该接口,驱动的标记 java.sql.Connection:封装和数据库的连接 java.sql.Statement:

8.4.3.1 模板方法模式

一般来说,模板方法模式能够定义算法或类的骨架,在以后填充缺失的部分,在具体的继承类中实现.基类定义的操作后来被填充,用来实现更复杂的操作.图 8.4 以图表形式显示了这一点. 图 8.4 基类包含抽象方法 PrimitiveOperation,用于实现 TemplateMethod.缺失部分由继承的类 ConcreteClass 填充. 模板方法中的抽象类对应于查询的表示(类 QueryDecision).需要由派生类提供的基本操作是检查方法,它有一个参数 Client,返回布尔值.模板方法是我

设计模式学习笔记之九:模板方法模式

现在我家里有一台铃木的小车锋驭和一台铃木的摩托车风暴1000,我要想把这两种类型的车都先跑起来再停下来,有一些步骤,并且这些步骤是有先后顺序的,那就是: 1. 打开车门 2. 启动发动机 3. 挂档 4. 走起 5. 刹车 6. 停车 OO设计原则之一就是分离可变和不变的部分并把可变的部分封装起来,我们来看一下以上两种类型的车,哪些步骤的实现是一样的,哪些是可变的.我们把不变的部分提取出来并放到超类中让所有子类共享其行为,同时我们把可变部分的具体实现延迟到子类中,让子类来自行决定如何实现. 1.

Android设计模式之命令模式、策略模式、模板方法模式

命令模式是其它很多行为型模式的基础模式.策略模式是命令模式的一个特例,而策略模式又和模板方法模式都是算法替换的实现,只不过替换的方式不同.下面来谈谈这三个模式. 命令模式 将一个请求封装为一个对象,从而使你可用不同的请求对客户进行参数化:对请求排队或记录请求日志,以及支持可撤消的操作. java中传递(注入)对象很容易,但是却不支持直接传递行为(即传递函数或者说传递方法),只能间接的通过传递(注入)一个对象,再调用它的行为来实现.如果把这样的行为抽取出来为一个类,称作命令类,它的具体实现都是命令

JAVA之旅(七)——final关键字 , 抽象类abstract,模板方法模式,接口interface,implements,特点,扩展

JAVA之旅(七)--final关键字 , 抽象类abstract,模板方法模式,接口interface,implements,特点,扩展 OK,我们继续学习JAVA,美滋滋的 一.final 我们来聊聊final这个关键字 final可以修饰类,方法和变量 final修饰的类不可以被继承 final修饰的方法不可以被覆盖 final修饰的变量是一个常量,只能被赋值一次 内部类只能访问被final修饰的局部变量 final,故名思意,就是最终的意思,由以上的五种特性,不过final的出现,也是有

面向对象编程思想-模板方法模式

一.引言 说到模板,顾名思义:就是样板,整体架构已经有了,你只需要填充自己的特定内容就可以了.如:简历模板,论文模板,PPT模板等 在软件设计中,模板方法模式与之很相似,下面请看我们今天要学习的模板方法模式 二.模板方法模式 定义:定义一个操作中的算法的骨架,而将一些步骤延迟到子类中.模板方法使得子类可以不改变一个算法的结构即可重定义该算法的某些特定步骤 下面结构图: 抽象模板角色(AbstractClass):在抽象类中定义一个或多个基本操作,每一个操作对应算法中一个步骤:同时提供一个模板方法

java设计模式 模板方法模式Template Method

设计模式(Design pattern)是一套被反复使用.多数人知晓的.经过分类编目的.代码设计经验的总结.使用设计模式是为了可重用代码.让代码更容易被他人理解.保证代码可靠性.毫无疑问,设计模式于己于他人于系统都是多赢的,设计模式使代码编制真正工程化,设计模式是软件工程的基石,如同大厦的一块块砖石一样.项目中合理的运用设计模式可以完美的解决很多问题,每种模式在现在中都有相应的原理来与之对应,每一个模式描述了一个在我们周围不断重复发生的问题,以及该问题的核心解决方案,这也是它能被广泛应用的原因.