首页 > 数据库 >使用反射简化批量保存sql语句

使用反射简化批量保存sql语句

时间:2023-03-07 11:13:02浏览次数:40  
标签:语句 return 批量 list List item sql null size

写批量保存的时候遇到实体类字段比较多的时候写起来非常的头疼,所以我想能不能通过程序自动获取拼接

思路:

1.通过反射获取实体类的所有字段

2.把字段拼接为id,user_name,user_age  和 #{item.id},#{iitem.userName},#{item.userAge}两种字符串

获得字符串的代码:

public static List<Field> getFields(Class<?> clazz) {
        List<Field> fieldList = new ArrayList<>(Lists.newArrayList(clazz.getDeclaredFields()));
        if (!(clazz.getSuperclass().isAssignableFrom(Object.class))) {
            fieldList.addAll(getFields(clazz.getSuperclass()));
        }
        return fieldList;
    }

    /**
     * @param clazz 数据实体类class 注意:字段名一定要驼峰命名
     * @param item  foreach item名,默认为item
     * 获得批量保存数据库字段拼接后的字段 (为数据库批量保存删除用)例如:top = id,user_name,user_age
     *                                   under = #{item.id},#{iitem.userName},#{item.userAge},
     **/
    public static Map<String,String> getTopAndUnder(Class<?> clazz,String item){
        Map<String, String> map = new HashMap<>();
        if(StringUtils.isBlank(item)){
            item = "item";
        }
        List<Field> fields = getFields(clazz);
        List<String> topColumns = new ArrayList<>();
        if(CollectionUtils.isEmpty(fields)){
            map.put("top",null);
            map.put("under",null);
            return map;
        }

        List<String> underColumns = new ArrayList<>();
        for (Field field : fields) {
            //是静态的字段就跳过
            if (Modifier.isStatic(field.getModifiers())) {
                continue;
            }
            underColumns.add("#{"+item + "." + field.getName() + "}");
            String s = toUnderScoreCase(field.getName());
            topColumns.add(s);
        }
        if(!CollectionUtils.isEmpty(topColumns)){
            String top = StringUtils.join(topColumns, ",");
            map.put("top",top);
        }else {
            map.put("top",null);
        }
        if(!CollectionUtils.isEmpty(underColumns)){
            String under = StringUtils.join(underColumns, ",");
            map.put("under",under);
        }else {
            map.put("top",null);
        }

        return map;
    }

**
 * 驼峰命名方法
 *
 * @return toCamelCase(" hello_world ") == "helloWorld"
 * toCapitalizeCamelCase("hello_world") == "HelloWorld"
 * toUnderScoreCase("helloWorld") = "hello_world"
 */
public static String toUnderScoreCase(String s) {
    if (s == null) {
        return null;
    }

    StringBuilder sb = new StringBuilder();
    boolean upperCase = false;
    for (int i = 0; i < s.length(); i++) {
        char c = s.charAt(i);

        boolean nextUpperCase = true;

        if (i < (s.length() - 1)) {
            nextUpperCase = Character.isUpperCase(s.charAt(i + 1));
        }

        if ((i > 0) && Character.isUpperCase(c)) {
            if (!upperCase || !nextUpperCase) {
                sb.append(SEPARATOR);
            }
            upperCase = true;
        } else {
            upperCase = false;
        }

        sb.append(Character.toLowerCase(c));
    }

    return sb.toString();
}

service层代码:

public Integer batchSave(List<User> list,Integer num) {
        if(CollectionUtils.isEmpty(list) || null == num || num <= 0){
            return 0;
        }
        Map<String, String> topAndUnder = getTopAndUnder(User.class,null);
        if(!CollectionUtils.isEmpty(topAndUnder)){
            String join = topAndUnder.get("top");
            String underColumn = topAndUnder.get("under");
            if(StringUtils.isBlank(join) || StringUtils.isBlank(underColumn)){
                return 0;
            }
            if(list.size() <= num){
                return userMapper.batchSave(join,underColumn,list);
            }else {
                //数据量大进行分割,自己把握
                List<List<User>> partition = ListUtils.partition(list, num);
                Integer i = null;
                for (List<User> user : partition) {
                    i = userMapper.batchSave(join,underColumn,user);
                }
                return i;
            }
        }else {
            return 0;
        }
    }

数组分割工具类ListUtils:

public class ListUtils {
    public static <T> List<List<T>> partition(final List<T> list, final int size) {
        if (list == null) {
            throw new NullPointerException("List must not be null");
        }
        if (size <= 0) {
            throw new IllegalArgumentException("Size must be greater than 0");
        }
        return new Partition<>(list, size);
    }

    private static class Partition<T> extends AbstractList<List<T>> {
        private final List<T> list;
        private final int size;

        private Partition(final List<T> list, final int size) {
            this.list = list;
            this.size = size;
        }

        @Override
        public List<T> get(final int index) {
            final int listSize = size();
            if (index < 0) {
                throw new IndexOutOfBoundsException("Index " + index + " must not be negative");
            }
            if (index >= listSize) {
                throw new IndexOutOfBoundsException("Index " + index + " must be less than size " +
                        listSize);
            }
            final int start = index * size;
            final int end = Math.min(start + size, list.size());
            return list.subList(start, end);
        }

        @Override
        public int size() {
            return (int) Math.ceil((double) list.size() / (double) size);
        }

        @Override
        public boolean isEmpty() {
            return list.isEmpty();
        }
    }

}

mapper层代码:

 /**
     * 批量保存
     * @param list 数据
     */
    Integer batchSave(@Param("stringColumn")String stringColumn,
                      @Param("underColumn")String underColumn,
                      @Param("list")List<User> list);
<insert id="batchSave">
        INSERT INTO t_user(#{stringColumn})
        VALUES 
        <foreach collection="list" item="item" separator=",">
            (#{underColumn})
        </foreach>
 </insert>

 

标签:语句,return,批量,list,List,item,sql,null,size
From: https://www.cnblogs.com/fan-King/p/17187365.html

相关文章

  • SQL标签库详解例子
    <%@pagelanguage="java"contentType="text/html;charset=UTF-8"pageEncoding="UTF-8"%><%@tagliburi="http://java.sun.com/jsp/jstl/sql"prefix="sql"%><%@tagli......
  • Mysql 主从复制和 GTID 复制
    1、安装主Mysql优化命令创建数据和日志存储目录1)安装Mysql​root@centos05~]#tarzxfmysql-8.0.32-el7-x86_64.tar.gz-C/usr/src/[root@centos05~]#mv/usr/src/m......
  • Sqlmap
    1.Sqlmap简介SQLMap是一个自动化的SQL注入工具,其主要功能是扫描、发现并利用给定URL的SQL注入漏洞,内置了很多绕过插件,支持的数据库是MySQL、Oracle、PostgreSQL、Micr......
  • MySQL 安装过程中踩过的坑
    1、用 grep'temporarypassword'/var/log/mysqld.log生成的初始密码老提示密码错误,只能直接发大招:       A、vi/etc/my.cnf在文件的[mysqld]内增加一行 ......
  • Java中如何解析SQL语句、格式化SQL语句、生成SQL语句?
    昨天在群里看到有小伙伴问,Java里如何解析SQL语句然后格式化SQL,是否有现成类库可以使用?之前TJ没有做过这类需求,所以去研究了一下,并找到了一个不过的解决方案,今天推荐给大家......
  • mysql 0点 弹窗 取消
         ......
  • postgresql + mybatis传入时间参数的问题
    在使用mybatis传入日期参数进行动态时间判断的时候,如果传入参数为String,使用mybatis时,在mapper中以下几种写法是错误的<iftest="query.beginDate!=nullandquer......
  • SQL语句
    MySQL是c/s架构第三方(图形化)工具:workbenchNavicatSQlyogphpmyadmin连接服务器配置信息:地址,端口号,用户名,密码常见的数据库:mysqloraclesql_server行:row   列:column......
  • MySQL中这14个必备神器,用过都说好
    前言:最近几年用MYSQL数据库挺多的,发现了一些非常有用的小玩意,今天拿出来分享到大家,希望对你会有所帮助。1.group_concat 在我们平常的工作中,使用groupby......
  • mysql中 Char 和 varchar 的区别?
    1、char的长度是固定不变,而varchar的长度是可变的例如值:abc类型char(10),存储值为:abc_______(abc+7个空格)类型varchar(10),存储值为:abc(自动缩短为3个字母的长......