+ // Returns the number of rows inserted
+ public int insert(Connection con, Table table, Object[][] values) throws SQLException
+ {
+ int count = 0;
+ int pendingValues = 0;
+
+ String sql = insertSql(table);
+
+ try (PreparedStatement ps = con.prepareStatement(sql))
+ {
+ for (int row = 0; row < values.length; ++row) {
+ Object[] data = values[row];
+
+ assert(null != data);
+ assert(data.length == table.getNumColumns());
+
+ for (int col = 0; col < data.length; ++col) {
+ ps.setObject(col + 1, data[col]);
+ pendingValues++;
+ }
+ ps.addBatch();
+
+ int rowsFlushed = checkFlushBatch(ps, pendingValues, false);
+ if (rowsFlushed > 0) {
+ count += rowsFlushed;
+ pendingValues = 0;
+ }
+ }
+
+ count += checkFlushBatch(ps, pendingValues, true);
+ }
+
+ return count;
+ }
+
+ int checkFlushBatch(PreparedStatement ps, int pendingValues, boolean forceFlush) throws SQLException
+ {
+ int count = 0;
+
+ if (forceFlush || (pendingValues >= PENDING_LIMIT))
+ {
+ int[] updateCounts = ps.executeBatch();
+ for (int i = 0; i < updateCounts.length; ++i) {
+ if (updateCounts[i] > 0) {
+ count += updateCounts[i];
+ }
+ }
+ }
+
+ return count;
+ }
+
+ String insertSql(Table table) {
+ StringBuilder sb = new StringBuilder("INSERT INTO ");
+ sb.append(table.getName())
+ .append(" VALUES (");
+
+ for (int i = 0; i < table.getNumColumns(); ++i) {
+ if (i > 0) {
+ sb.append(",");
+ }
+ sb.append("?");
+ }
+ sb.append(")");
+
+ return sb.toString();
+ }
+