Использование пакетных команд SQL с MySQL JDBC - PullRequest
1 голос
/ 12 октября 2011

Я пытаюсь найти лучший способ заставить MySQL использовать пакетные обновления.

Я создаю, скажем, 10000 записей.Каждая запись должна быть вставлена ​​в БД следующим образом:

for 1 to 10000
 1) insert into table1
 2) get auto increment id from table1 (call it table1ID)
 3) use table1ID to insert into table2
next

Я не вижу простого способа пакетирования этого сценария.Может быть, пакет table1 вставьте 10000 раз, затем получите все идентификаторы таблицы, затем еще один пакет из 10000 вставок в table2.Но тогда я должен убедиться, что все мои вставки совпадают.Для каждой вставки в table1 мне нужна правильная вставка в table2.

Ответы [ 3 ]

1 голос
/ 09 декабря 2011

Вот пример того, как я делаю это в очень большом пакетном файле SQL:

  • Сначала я вставляю значение без родителя
  • Я помню последний идентификатор вставки
  • Я использую его для вставки подкатегорий, и в качестве последнего вставленного идентификатора указываем idparent.

Это очень близко к тому, что вы хотите сделать:

insert into category (idparent,description) values (NULL, 'Mycat');
set @lt=LAST_INSERT_ID();
insert into category (idparent,description) values
    (@lt, 'MySubCat'),
    (@lt, 'MyOtherSubCat');

Надеюсь, это поможет.

1 голос
/ 13 октября 2011

Нет способа пакетной вставки строк и получения соответствующих идентификаторов (из столбца автоинкремента).Вы должны вставить один за другим в цикл, сохранить все идентификаторы в списке, а затем выполнить пакетную вставку / обновление / любую таблицу 2.

В вашем примере это 10000 + 1 операций с БДЭто значительное улучшение по сравнению с 20 000 операций.

0 голосов
/ 30 июля 2015

Вы можете использовать следующий подход ... Выполните тестирование перед использованием, потому что getGeneratedKeys () в Statement, потому что это зависит от используемого драйвера. Приведенный ниже код протестирован на Maria DB 10.0.12 и Maria JDBC driver 1.2 Maria DB 10 построена поверх MySQL 5.6, поэтому должна работать и с MySQL.

Помните, что увеличение размера партии повышает производительность только до некоторой степени ... для моей установки увеличение размера партии свыше 500 фактически снижало производительность.

public Connection getConnection(boolean autoCommit) throws SQLException {
    Connection conn = dataSource.getConnection();
    conn.setAutoCommit(autoCommit);
    return conn;
}

private void testBatchInsert(int count, int maxBatchSize) {
    String querySql = "insert into batch_test(keyword) values(?)";
    try {
        Connection connection = getConnection(false);
        PreparedStatement pstmt = null;
        ResultSet rs = null;
        boolean success = true;
        int[] executeResult = null;
        try {
            pstmt = connection.prepareStatement(querySql, Statement.RETURN_GENERATED_KEYS);
            for (int i = 0; i < count; i++) {
                pstmt.setString(1, UUID.randomUUID().toString());
                pstmt.addBatch();
                if ((i + 1) % maxBatchSize == 0 || (i + 1) == count) {
                    executeResult = pstmt.executeBatch();
                }
            }
            ResultSet ids = pstmt.getGeneratedKeys();
            for (int i = 0; i < executeResult.length; i++) {
                ids.next();
                if (executeResult[i] == 1) {
                    System.out.println("Execute Result: " + i + ", Update Count: " + executeResult[i] + ", id: "
                            + ids.getLong(1));
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
            success = false;
        } finally {
            if (rs != null) {
                rs.close();
            }
            if (pstmt != null) {
                pstmt.close();
            }
            if (connection != null) {
                if (success) {
                    connection.commit();
                } else {
                    connection.rollback();
                }
                connection.close();
            }
        }
    } catch (SQLException e) {
        e.printStackTrace();
    }
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...