java - 复杂的字段条件判断解析

 前年老妖 发布于 2022-10-26 11:58

应用场景简化描述

现在有个用户Person,包含int age, BigDecimal money,java.util.Date accessTime等字段,对应于用户表person:

年龄(age : int) 资产 (money : number) 入网日期 (accessTime : date)
20 100.00 2017-03-24
20 150.00 2016-05-07
21 300.00 2015-04-03
21 240.00 2015-07-15
22 300.00 2014-12-21
21 300.00 2014-12-21

另外,有一张条件表,condition:

字段名(fieldName : varchar) 运算符(oper : varchar) 阈值 (threshold : varchar )
age = 21
money > 280.05
accessTime > 2015-05-31

条件表condition用来配置过滤用户person的条件,表示要过滤出

  • 年龄等于21岁

  • 资产大于280.05

  • 入网日期在 2015-06-01之后

的所有用户。

其中,oper可取的值有 = , < , > , >= , <= , in , between

如果oper为inbetween, 则阈值为多个,用逗号隔开。

问题

现在,对于不同的字段,在条件表condition里都是varchar类型,而在person表中,却有不同的类型。

而且,条件表里的条件是从web系统页面上,由用户配置的;也就是说,条件的个数不确定,配置的字段,运算符,阈值也都是不确定的。

问: 如何才能使用java代码,先将所有用户以及条件查出来,然后遍历每个用户,对于每个用户,遍历每个条件,怎样才能正确的判断该用户通过所有的条件检查,得出通过条件筛选的用户列表?(上边的场景是实际场景简化后的,请不要给出拼接sql,通过sql过滤的答案)


是不是可以把person的记录生成xml文件,条件生成xsd文件,用xsd去校验xml ??

3 个回答
  • 感觉你这个condition表没什么用啊?仅仅是存储数据?如果临时的直接用json传过来就好了,如果你要持久存储的话,起码要个admin_id什么的,来标记下是谁的筛选条件。感觉效率不如直接扔到redis好点。

    看你用的是Java,不过我习惯用PHP,就用PHP简单描述下我的思路吧...

    写一个Filter类处理condition转换为sql

    class Filter {
        public function doFilter() {
            //1. 获取登录的admin_id
            //2. 获取筛选条件
            /**
             * 数据格式例子为: [
             *    'field' => 'age';, 
             *    'type'  => 'compare',
             *    'ext'   => '>',
             *    'value' => '2'
             * ]
             */
            foreach($conditions as $condition) {
                // 根据type获取对应的$conditionHandle
                $conditionHandle::parse($condition);
            }
        }
    }
    
    // Condition接口
    interface Condition {
        // 解析数据,返回sql片段和需要填充的数据(此处使用PDO预处理,减少SQL注入)
        static function parse($data);
    }
    
    // ConditionHandle
    namespace Condition;
    class Compare implements Condition {
        // 执行流程
        public static function parse($data) {
            ...
            return [
                'sql' => 'age > ?',
                'params' => [ 2 ]
            ];
        }
    }

    手写的,语法错误请忽略...

    2022-10-27 00:56 回答
  • 你用户表有多大,还全部查出来。

    正规做法都是拼sql查吧。。。

    更高级的做法应该是自定义领域特定语言,然后转sql吧,反正不可能是用xml过滤。

    2022-10-27 00:56 回答
  • 如果不用sql的话,可以考虑使用责任链模式,将所有数据获取出来放到linkedlist里面,
    然后写个过滤器来过滤集合里面的内容,每一个条件可以相当于一个过滤器

    2022-10-27 00:56 回答
撰写答案
今天,你开发时遇到什么问题呢?
立即提问
热门标签
PHP1.CN | 中国最专业的PHP中文社区 | PNG素材下载 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有