对sql的查询语句做成对象式,简单实现。Where部分

最近比较懒,所以进度很慢很慢。

在此之前我已经有对sql查询语句的包装,连接地址:http://7041393.blog.51cto.com/7031393/1680736

sql的包装先定义了一个简单的接口

package net.zz.zjf.plugin;   
 /**     
* Created by ZaoSheng on 2015/7/15.    
*/   
 public interface SQLParams {   
    String toFormatSQL();    
    String toSQL();    
}

这个接口暂时就两个方法。toSQL()这个方法用来生成条件参数为":property"的sql,而toFormatSQL()是用来生成条件参数为"?"的sql,这里如果是hibernate的话建议试用toSQL()。

对此我对之前的QueryParams进行了一个扩展,对具体sql进行拆分成具体对象。这里我就先讲讲我where的实现。

在使用where 需要用到两个枚举

第一个AndOr,这个枚举类很简单吧,不想在对此解释了。

package net.zz.zjf.plugin;

/**
 * Created by ZaoSheng on 2015/8/5.
 */
public enum AndOr {
    AND{
        @Override
        public String toMatchString(String propertyName, String pattern) {
            return String.format(" and %s %s ", propertyName, pattern);
        }
    }, OR{
        @Override
        public String toMatchString(String propertyName, String pattern) {
            return String.format(" or %s %s ", propertyName, pattern);
        }
    }, NUL{
        @Override
        public String toMatchString(String propertyName, String pattern) {
            return String.format(" %s %s ", propertyName, pattern);
        }
    };
    public abstract String toMatchString(String propertyName, String pattern);
}

接下来Restriction这个类在之前那篇文章里面提到过的枚举类,只是对现需求进行一个扩展。一样不进行解释。

package net.zz.zjf.plugin;

/**
 * Created by ZaoSheng on 2015/7/30.
 */
public enum Restriction {

    /**
     * 等于查询(from Object o where o.property = ?)
     */
    EQ {
        public String toMatchString(String pattern) {
            return "= :" + pattern;
        }
    },

    /**
     * 非等于查询(from Object o where o.property <> ?)
     */
    NE {
        public String toMatchString(String pattern) {
            return "<> :" + pattern;
        }
    },

    /**
     * 大于等于查询(from Object o where o.property >= ?)
     */
    GE {
        public String toMatchString(String pattern) {
            return ">= :" + pattern;
        }

    },

    /**
     * 大于查询(from Object o where o.property > ?)
     */
    GT {
        @Override
        public String toMatchString(String pattern) {
            return "> :" + pattern;
        }
    },

    /**
     * 小于等于查询(from Object o where o.property <= ?)
     */
    LE {
        @Override
        public String toMatchString(String pattern) {
            return "<= :" + pattern;
        }
    },

    /**
     * 小于查询(from Object o where o.property < ?)
     */
    LT {
        @Override
        public String toMatchString(String pattern) {
            return "< :" + pattern;
        }
    },
    /**
     * 两个值之间查询(from Object o where o.property between ? and ?)
     */
    BETWEEN {
        @Override
        public String toMatchString(String pattern) {
            return String.format("%s between :%s1 and :%s2", pattern, pattern, pattern);
        }
    },

    /**
     * 包含查询(from Object o where o.property in(?,?,?))
     */
    IN {
        @Override
        public String toMatchString(String pattern) {
            return String.format("in (:%s)" , pattern);
        }
    },

    /**
     * 非包含查询(from Object o where o.property not in(?,?,?))
     */
    NIN {
        @Override
        public String toMatchString(String pattern) {
            return String.format("not in ( :%s )" , pattern);
        }
    },

    /* *
     * 左模糊查询(from Object o where o.property like %?)
     */
    LLIKE {
        @Override
        public String toMatchString(String pattern) {
            return "%" + pattern;
        }
    },

   /* *
     * 右模糊查询(from Object o where o.property like ?%)
     */
    RLIKE {
        @Override
        public String toMatchString(String pattern) {
            return pattern + ‘%‘;
        }
    },

   /* *
     * 模糊查询(from Object o where o.property like %?%)
     */
    LIKE {
        @Override
        public String toMatchString(String pattern) {
            return ‘%‘ + pattern + ‘%‘;
        }
    },
   /* *
     * 模糊查询(from Object o where o.property  is null)
     */
    NULL {
        @Override
        public String toMatchString(String pattern) {
            return  pattern + " is null";
        }
    },
   /* *
     * 模糊查询(from Object o where o.property is not null)
     */
   NOTNULL  {
        @Override
        public String toMatchString(String pattern) {
            return  pattern + " is not null";
        }
    };

    public abstract String toMatchString(String pattern);
    }

这里对where的解释,我就直接把代码贴出来,讲一些解释在代码里面写注释吧(因为本人表达能力不是很好)!

package net.zz.zjf.plugin;

import java.lang.reflect.Array;
import java.util.*;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 * Created by ZaoSheng on 2015/8/5.
 */
public class Where implements SQLParams{
    //用于存放第一个条件的名
    private String first = null;
    /*这里存放所有的where需要用到的东西。wheres的key是property名,value主要分为三部分
    *value主要分为三部分,value[0]用来存放property的值,在BETWEEN的情况下value[0]是数组
    *数组长度为2。value[1]存放AndOr,value[2]存放具体的where操作,比如 ">",">=","like","in"
    *等操作。
    */
    private Map<String, Object[]> wheres = new HashMap<String, Object[]>();
    //这个对象用来存放具体的属性值attrs的key是sql中":property"中的"property",value是对应的值
    private Map<String, Object> attrs = new HashMap<String, Object>();
    //这个集合不一定有值,在执行toFormatSQL方法后才会有值。存放的值依次对应sql中的第几个"?"
    private List<Object> paras = new ArrayList<Object>();

    public Where() {

    }
    
    public Where(String propertyName, Object value, AndOr andor, Restriction restriction) {
        first = propertyName;
       add(propertyName, value, andor, restriction);
    }

    public Where(String propertyName, Object value, AndOr andor) {
        this(propertyName, value, andor, Restriction.EQ);
    }

    public Where(String propertyName, Object value, Restriction restriction) {
        this(propertyName, value, AndOr.NUL, restriction);
    }

    public Where(String propertyName, Object value) {
        this(propertyName, value, Restriction.EQ);
    }

    public Map<String, Object[]> getWheres() {
        return wheres;
    }

    public Map<String, Object> getAttrs() {
        return attrs;
    }

    public List<Object> getParas() {
        return paras;
    }

    public Where and(String propertyName, Object value, Restriction restriction) {
        add(propertyName, value, AndOr.AND, restriction);
        return this;
    }

    public Where and(String propertyName, Object value) {
        return and(propertyName, value, Restriction.EQ);
    }

    public Where or(String propertyName, Object value, Restriction restriction) {
        add(propertyName, value, AndOr.OR, restriction);
        return this;
    }

    public Where or(String propertyName, Object value) {
        return or(propertyName, value, Restriction.EQ);
    }

    protected void add(String key, Object value, AndOr andor, Restriction restriction) {
        if (null == value || "".equals(value)) {
            if (key.equals(first))
            {
                first = null;
            }
            wheres.remove(key);
        } else {
            wheres.put(key, new Object[]{value, andor, restriction});
        }

    }

    public String toSQL() {
        if (wheres.isEmpty()) return "";
        StringBuilder sb = new StringBuilder();
        if (null != first)  setSql(first, wheres.get(first), sb );

        for (String key : wheres.keySet()) {
            if (key.equals(first))  continue;

            Object[] objects = wheres.get(key);
            setSql(key, objects, sb);

        }
        return sb.toString();
    }
    
    /**
    *这个方法之所以提取出来是因为能更好的在多个地方引用(应该用代码重构的方式来讲的,可惜我不会讲).
    */
    private void setSql(String key, Object[] objects, StringBuilder sb)
    {
        AndOr andOr = (AndOr) objects[1];
        Restriction restriction = (Restriction)objects[2];
        switch (restriction) {
            case LIKE:
            case LLIKE:
            case RLIKE:
                sb.append(andOr.toMatchString(key, "like :" + key));
                attrs.put(key, restriction.toMatchString(objects[0].toString()));
                break;
            case NULL:
            case NOTNULL:
                sb.append(andOr.toMatchString("", restriction.toMatchString(key)));
                break;
            case BETWEEN:
                sb.append(andOr.toMatchString(key, restriction.toMatchString(key)));
                Object[] value = (Object[]) objects[0];
                attrs.put(String.format("%s1", key),  value[0]);
                attrs.put(String.format("%s2", key),  value[1]);
                break;
            default:
                sb.append(andOr.toMatchString(key, restriction.toMatchString(key)));
                attrs.put(key, objects[0]);
        }
    }

    @Override
    public String toFormatSQL() {
        return  toFormatSQL(toSQL(), attrs, paras);
    }

    /**
     * @param whereSQL
     * @param attrs
     * @param values
     * @return
     */
    public static String toFormatSQL(String whereSQL, Map<String, Object> attrs, List<Object> values) {
        Matcher matcher = Pattern.compile(":(\\w+)").matcher(whereSQL);
        String rexp = null;
        while (matcher.find()) {
            String group = matcher.group(1);
            Object ov = attrs.get(group);
            if (ov instanceof List) {
                StringBuilder sb = new StringBuilder();
                List vs = (List) ov;
                for (Object v : vs) {
                    sb.append("?,");
                    values.add(v);
                }
                sb.deleteCharAt(sb.length() - 1);
                rexp = sb.toString();

            } else {
                values.add(ov);
                rexp = "?";
            }
            whereSQL = whereSQL.replace(String.format(":%s", group), rexp);
        }
        return whereSQL;
    }

    @Override
    public String toString() {
        return toFormatSQL();
    }

    public static void main(String[] args) {
        Calendar c = new GregorianCalendar();

        Where where = new Where("name", "张三");
        where.or("class", 2);
        where.and("sex", true);
        where.and("age", new Integer[]{1,10}, Restriction.BETWEEN);
        List<Object> ids = new ArrayList<Object>();
        ids.add(4);
        ids.add(3);
        where.and("id", ids, Restriction.IN);
        System.out.println(where.toString());

        for (Object value :where.getParas())
        {
            System.out.print(String.format("%s ", value));
        }

    }
}

写完发现NULL与NOTNULL没办法用,只需就这个对象简单的更改就可以使用。懒点下次更改吧。

差不多就是这样子吧,本人小菜一枚,表达能力也不是很好。请大神们见谅。初学者还有很多要学的,请大神多指教。

继续对JFinal的Model部分包装一下,github地址:https://github.com/cnzzs/zjf

时间: 2024-10-14 06:09:15

对sql的查询语句做成对象式,简单实现。Where部分的相关文章

对sql的查询语句做成对象式,简单实现。查询参数实现一

这里我就不想多说应该能看懂代码的都应该知道什么意思了. 这个类暂时应该就是这样子了. package net.zz.zjf.plugin; import java.util.*; import java.util.regex.Matcher; import java.util.regex.Pattern; /**  * Created by ZaoSheng on 2015/7/15.  */ public class QueryParams {     private Integer page

MySQL 抓取SQL慢查询语句

当MySQL服务器出现异常(慢),首先要考虑是否因,SQL语句引起数据库慢,如果情况比较紧急,我们就要立刻 SHOW FULL PROCESSLIST; 去查看,但我建议大家使用-e参数,采用非交互的方式,因为这样可以使用grep等命令,对结果进行过滤,更方便直观的看到结果 一.抓SQL慢查询语句的方法,有2种: 1,临时紧急抓取 通过SHOW FULL PROCESSLIST; 的方式,执行几次,有相同语句,就可能是SQL慢查询语句: SHOW FULL PROCESSLIST; #查看MyS

python 3 mysql sql逻辑查询语句执行顺序

python 3 mysql sql逻辑查询语句执行顺序 一 .SELECT语句关键字的定义顺序 SELECT DISTINCT <select_list> FROM <left_table> <join_type> JOIN <right_table> ON <join_condition> WHERE <where_condition> GROUP BY <group_by_list> HAVING <havin

SQL模糊查询语句

SQL模糊查询语句: SQL模糊查询,使用like比较字,加上SQL里的通配符,请参考以下: 1.LIKE'Mc%' 将搜索以字母 Mc 开头的所有字符串(如 McBadden). 2.LIKE'%inger' 将搜索以字母 inger 结尾的所有字符串(如 Ringer.Stringer). 3.LIKE'%en%' 将搜索在任何位置包含字母 en 的所有字符串(如 Bennet.Green.McBadden). 4.LIKE'_heryl' 将搜索以字母 heryl 结尾的所有六个字母的名称

如何在SQL Server查询语句(Select)中检索存储过程(Store Procedure)的结果集?

如何在SQL Server查询语句(Select)中检索存储过程(Store Procedure)的结果集?(2006-12-14 09:25:36) 与这个问题具有相同性质的其他描述还包括:如何在SQL Server存储过程中获取另一存储过程的执行结果记录集?如何在存储过程中检索动态SQL语句的执行结果?如何实现类似SELECT * FROM (EXEC procedure_name @parameters_var) AS datasource ... 的功能?procedure_

mysql第四篇--SQL逻辑查询语句执行顺序

mysql第四篇--SQL逻辑查询语句执行顺序 一.SQL语句定义顺序 SELECT DISTINCT <select_list> FROM <left_table> <join_type> JOIN <right_table> ON <join_condition> WHERE <where_condition> GROUP BY <group_by_list> HAVING <having_condition&g

sql的基础语句-sql的查询语句select

SQL查询语句介绍--select语句 1.简单的select查询语句 1.1 查行 SQL> select * from emp; 1.2 查列 SQL> select empno,ename from emp; 1.3 关联查询 oracle的语法: select  a.*,b.*  from emp a,dept b where a.deptno=b.deptno; 通用的语法: select  a.*,b.* from emp a join dept b on(a.deptno = b

SQL Server SQL高级查询语句小结(转)

--select select * from student; --all 查询所有 select all sex from student; --distinct 过滤重复 select distinct sex from student; --count 统计 select count(*) from student; select count(sex) from student; select count(distinct sex) from student; --top 取前N条记录 s

常见的SQL Server查询语句

// 备注:这里列出一些使用频率比较高的SQL语句语法,以便他日查询和使用 SQL语句由命令.子句.运算符和统计函数组成. 一. 命令  1. 数据定义命令: CREATE: 建立新的数据表.字段和索引表: DROP: 从数据库删除数据表或索引: ALTER: 增加或修改字段属性: 2. 数据操作命令: SELECT: 找出满足条件的记录: INSERT: 增加记录或合并两个数据表: UPDATE: 更新满足条件的记录: DELETE: 删除满足条件的记录: 二. 子句  FROM: 指定数据表