jdbc大批量数据导入mysql和sqlserver,最快速方法

1. mysql大批量导入:

使用load的方法最快
但是我们知道,load只能load文件,但是如果我们想load内存里面的一些数据怎么办呢,可以参考这篇文章
https://blog.csdn.net/seven_3306/article/details/9237495
不写文件,同时LOAD的方法,用的是setLocalInfileInputStream方法

方法如下:

    public void prepareBatchInputStreamExecute(String loadSql, InputStream inputStream){
        getConn();
        try (PreparedStatement preparedStatement = conn.prepareStatement(loadSql);){
            conn.setAutoCommit(false);
            if (preparedStatement.isWrapperFor(com.mysql.jdbc.Statement.class)) {
                com.mysql.jdbc.PreparedStatement mysqlStatement =
                        preparedStatement.unwrap(com.mysql.jdbc.PreparedStatement.class);
                mysqlStatement.setLocalInfileInputStream(inputStream);
                int result = mysqlStatement.executeUpdate();
                conn.commit();
            }
        }catch (Exception e){
            e.printStackTrace();
        }
    }

其中loadSql为:

"LOAD DATA LOCAL INFILE 'no-used.txt' IGNORE INTO TABLE tableName (id,name,xxx)"

其中的no-used.txt是没有用的,写什么名字都可以,但是又必须要有,这种速度是最快的方式。
注意:mysql5.7可以用这种方式,mysql8的API有些改变

2. sqlserver大批量导入

使用SQLServerBulkCopy的方式是最快的
主要代码如下

  1. 获取虚拟的表: CachedRowSetImpl
    /**
     * 获取空的CachedRowSet对象
     * 其中BaseDao为最常见的JDBC操作,这里就不贴出,相信大家看的懂
     * @throws
     */
    public CachedRowSetImpl getCachedRowSet() throws SQLException {
        //查询出空值用于构建CachedRowSetImpl对象以省去列映射的步骤
        ResultSet rs = dbHelper.getResultSet("select * from "+tableName+" where 1=0",null);
        CachedRowSetImpl crs = new CachedRowSetImpl();
        crs.populate(rs);
        //获取crs以后关闭数据库连接
//        baseDao.closeResource();
        return crs;
    }

  1. 往虚拟的缓存表里面插入数据
    /**
     * 向CachedRowSet对象插入一条数据
     * 循环调用这一个方法,将想插入数据库的数据先插入到CachedRowSet对象里
     * @param crs
     * @param
     * @return
     * @throws SQLException
     */
    public CachedRowSetImpl insertIntoCachedRowSet(CachedRowSetImpl crs,String[] aa) throws SQLException{
        //移动指针到“插入行”,插入行是一个虚拟行
        crs.moveToInsertRow();
        //更新虚拟行的数据
        for (int i = 0; i < aa.length; i++) {
            crs.updateString("v"+(i), aa[i]);
        }
        //插入虚拟行
        crs.insertRow();
        //移动指针到当前行
        crs.moveToCurrentRow();
        return crs;
    }

  1. 使用SQLServerBulkCopy来批量插入数据
    /**
     * 使用BulkCopy和RowSet进行批量插入
     * @param crs
     * @param batchSize
     */
    public void insertBatch(CachedRowSetImpl crs,int batchSize)throws SQLException {
        SQLServerBulkCopyOptions copyOptions = new SQLServerBulkCopyOptions();
        copyOptions.setKeepIdentity(true);
        copyOptions.setBatchSize(batchSize);
        copyOptions.setUseInternalTransaction(false);
        SQLServerBulkCopy bulkCopy = new SQLServerBulkCopy(dbHelper.getConn());
        bulkCopy.setBulkCopyOptions(copyOptions);
        bulkCopy.setDestinationTableName(tableName);
        bulkCopy.writeToServer(crs);
        crs.close();
        bulkCopy.close();
    }

其中dbhelper.getConn()返回的是jdbc对数据库的一个连接

Connection

获取连接的时候,mysql和sqlserver还有点小区别


if("mysql".contains(sqlserverOrMysql.toLowerCase())){
    sDriverName = "com.mysql.jdbc.Driver";
    sDBUrl = "jdbc:mysql://" + serverIp +":"+port+ "/"+ dbName +"?useUnicode=true&characterEncoding=utf8&useServerPreparedStmts =true";
    Class.forName(sDriverName);
    conn = DriverManager.getConnection(sDBUrl, sUser, sPwd);
}
else if("sqlserver".contains(sqlserverOrMysql.toLowerCase())){
    sDriverName = "com.microsoft.sqlserver.jdbc.SQLServerDriver";
    sDBUrl = "jdbc:sqlserver://" + serverIp+":"+port + ";DatabaseName=" + dbName;
    Class.forName(sDriverName);
    conn = DriverManager.getConnection(sDBUrl+";user="+sUser+";password="+sPwd);
}

3. python导入mysql

用executemany方法,
估计sqlserver也是这个
,参考文章 Python MySQL Insert Data

你可能感兴趣的:(java,数据库)