zoukankan      html  css  js  c++  java
  • command模式应用总结

    最近写了一个分表查询的lib,封装了一些数据结构,可以简化对于分表查询的实现。这个问题主要体现在,对分表进行查询时,原有的单表查询需要进行修改,或者需要在内存中进行处理。修改单表的sql可能导致性能问题,原有的优化可能失效。内存处理则需要一些技巧,搞不好会把太多内容加载到内存中,导致内存被耗光。

    我的lib主要使用iterator的模式来解决数据库的读取的问题,每次只读取1000条,放在内存中,当iterator的next移动到缓冲区的尾部时,再次读取1000条,如此可以保证获得所有的数据。当然我们也可以采用双buffer的方式,一个用于提前读取,一个用于输出。不过现在还没这么做。

    虽然command模式不是lib的重点,但是这个模式却教会了我一些东西。因为最开始的时候,我并没有想到它。开始,我想的是查询分成几类:

    1. 查询结果做union all;

    2.查询结果做order by

    3. 查询结果做group by

    4. 查询结果去重

    我发现每个查询都有这样一些参数,一组表名,一个数据库查询的封装,如果需要排序的话,得要一个comparator,如果需要合并的话,得要一个MapReduce。

    最初的实现是:

    class QueryService{
      Iterator<T> query1(a,b);
      Iterator<T> query2(a,b,c);
      Iterator<T> query3(a,b,d);
    }

    后来发现参数太多,初始化比较麻烦,于是改成:

    X{
    a,b
    }
    X1 extends X{
    c
    }
    X2 extends X{
    d
    }
    class QueryService{
      Iterator<T> query1(X);
      Iterator<T> query2(X1);
      Iterator<T> query3(X2);
    }

    接着发现,这个设计缺乏扩展性,如果将来需要添加新的查询类型,或者想要换一种实现方式,就得修改整个query service。而且X X1 X2只有属性,太浪费了,没有实现封装的目的。更重要的,各个查询其实如果设置好上下文,调用方法都一样,返回值一样。这不就是command的用法吗。

    Cmd{
    Iterator run();
    }
    X implements Cmd{
    a,b
    }
    X1 extends X{
    c
    }
    X2 extends X{
    d
    }
    class QueryService{
      Iterator<T> query(Cmd);
    }

    这样上面的难题就迎刃而解了。为什么我一开始没想到呢。我想到了不同的种类的查询,过分关注他们的不同点,忽略了查询的共同点。所以以后工作中,一定要先抽取共性,再寻求个性。共性有利于整体考虑,个性有利于细化架构,发现新的机会。

  • 相关阅读:
    @RequestParam注解使用:Name for argument type [java.lang.String] not available, and parameter name information not found in class file either.
    cglib动态代理导致注解丢失问题及如何修改注解允许被继承
    springboot Autowired BeanNotOfRequiredTypeException
    git根据用户过滤提交记录
    不同包下,相同数据结构的两个类进行转换
    How to use Jackson to deserialise an array of objects
    jooq实践
    java如何寻找main函数对应的类
    Python--matplotlib
    Python 和 Scikit-Learn
  • 原文地址:https://www.cnblogs.com/alphablox/p/3036808.html
Copyright © 2011-2022 走看看