阅读 dbutils 源码(二)

阅读 dbutils 源码(二)

RowProcessor 接口

  • Object[] toArray(ResultSet rs) throws SQLException;
  • <T> T toBean(ResultSet rs, Class<? extends T> type) throws SQLException;
  • <T> List<T> toBeanList(ResultSet rs, Class<? extends T> type) throws SQLException;
  • Map<String, Object> toMap(ResultSet rs) throws SQLException;

这个接口很容易理解,就是将结果集中的数据转成Object数组、泛型T、泛型T集合或Map键值对。

BasicRowProcessor 实现 RowProcessor 接口

toArray方法的实现:

    public Object[] toArray(final ResultSet rs) throws SQLException {
        //结果集的字段名称、类型以及数目等表格所必须具备的信息
        final ResultSetMetaData meta = rs.getMetaData();
        //字段总数
        final int cols = meta.getColumnCount();
        final Object[] result = new Object[cols];
        for (int i = 0; i < cols; i++) {
            //ResultSet取值从1开始,你知道的。
            result[i] = rs.getObject(i + 1);
        }
        return result;
    }

toMap方法的实现:

    public Map<String, Object> toMap(final ResultSet rs) throws SQLException {
        final ResultSetMetaData rsmd = rs.getMetaData();
        final int cols = rsmd.getColumnCount();
        //不区分大小写的map,指定initialCapacity即初始容量
        final Map<String, Object> result = createCaseInsensitiveHashMap(cols);
        for (int i = 1; i <= cols; i++) {
            //获取别名
            String columnName = rsmd.getColumnLabel(i);
            //别名为空时
            if (null == columnName || 0 == columnName.length()) {
                //直接使用列名
                columnName = rsmd.getColumnName(i);
            }
            //列名与值对应的map
            result.put(columnName, rs.getObject(i));
        }
        return result;
    }

toBeantoBeanList方法,在这个类中并没有实现,默认是直接调用BasicRowProcessor类对应的方法,对于BasicRowProcessor类的toBeantoBeanList等方法,后面再做解释。

CaseInsensitiveHashMap 忽略大小写的 HashMap

内部用一个HashMap存储转换为小写的key与原key的映射:

private final Map<String, String> lowerCaseMap = new HashMap<>();

取数据:

        public Object get(final Object key) {
            //通过小写key获取原key,拿原key取到值
            final Object realKey = lowerCaseMap.get(key.toString().toLowerCase(Locale.ENGLISH));
            return super.get(realKey);
        }

存数据:

        public Object put(final String key, final Object value) {
            //先将小写key与原key存到lowerCaseMap,如果已经存在则返回被覆盖的oldKey
            final Object oldKey = lowerCaseMap.put(key.toLowerCase(Locale.ENGLISH), key);
            //如果oldKey为空,返回null,否则返回移除被覆盖的值并返回
            final Object oldValue = super.remove(oldKey);
            //放入新key和value
            super.put(key, value);
            /*
            举例:先存aBc=1然后存abC=2,小写key都为abc,所以必然是要覆盖的。
            按上面的代码执行:
            lowerCaseMap[abc=aBc] this[aBc=1]
            oldKey='aBc',
            oldValue=1,
            put('abC',2),
            aBc被覆盖了,所以返回被覆盖的值1
            lowerCaseMap[abc=abC] this[aBc=2]
             */
            return oldValue;
        }

附上我的github地址,dbutils源码和我自己加的注解。

猜你喜欢

转载自blog.csdn.net/m0_37659871/article/details/81391006