将 ArrayList 转换为 mysql 在 Java 中插入参数
Convert ArrayList to mysql insert parameters in Java
我卡住了。我拒绝长时间停留,所以我正在寻求帮助。我想要做的是获取一个我从另一个数据库的 select 语句中检索的结果集,将其放入 ArrayList,然后将数组列表转换为 Java 中的插入准备语句。
** 更新 **
问题是我得到一个 "java.sql.SQLException: Parameter index out of range (6 > number of parameters, which is 5)." ,这意味着它接收到 6 个参数而不是 5 个,我看不出这是怎么回事。由于在调试器中我正在观察值是否正确更新,但我的逻辑现在不正确。
我 运行 调试器发现我只是将所有值转储到第一个参数中。我明白我需要做什么。这是将ArrayList结果拆分到insert语句的各个参数中。我的大脑死了。一天结束了,这是我的最后一块拼图,所以我可以继续前进。我只是不知道该怎么做。感谢您的帮助!
这就是我的 ArrayList 结果。
[800-0022-08, 0025, 2015-09-30, 600040, 115]
[800-0022-08, 0024, 2015-09-30, 600040, 115]
[800-0022-08, 0008, 2015-09-30, 600040, 115]
[800-0022-08, 0036, 2015-09-30, 600040, 115]
[800-0022-08, 0035, 2015-09-30, 600040, 115]
[800-0022-08, 0034, 2015-09-30, 600040, 115]
代码如下
ResultSet rs = (ResultSet) stmt.executeQuery(query);
ResultSetMetaData rsmd = (ResultSetMetaData) rs.getMetaData();
int numberOfColumns = rsmd.getColumnCount();
int rowCount = 1
ArrayList <String[]> result = new ArrayList<>();
while (rs.next()) {
System.out.println("Row " + rowCount + ": ");
String[] row = new String[numberOfColumns];
for (i = 1; i < numberOfColumns + 1; i++) {
System.out.print(" Column " + i + ": ");
System.out.println(rs.getString(i);
row[i - 1] = rs.getString(i);
}
result.add(row);
System.out.println("");
rowCount++;
}
String Connection = "CONNECTIONSTRING";
String UserName = "USERNAME";
String Password = "PASSWORD";
String MySQLQuery = "INSERT INTO serial (MTSER_CODE, MTSER_SERIAL, MTSER_RECDATE, MTSER_WO, MTSER_WOSUF)" + "VALUES (?,?,?,?,?)";
String Driver = "org.gjt.mm.mysql.Driver";
Class.forName(Driver);
java.sql.Connection MyConnection = (java.sql.Connection) DriverManager.getConnection(Connection, UserName, Password);
java.sql.PreparedStatement preparedStmt;
preparedStmt = MyConnection.prepareStatement(MySQLQuery);
// ** UPDATED FOR LOOP **
for (String[] arr : result) {
try (java.sql.PreparedStatement preparedStmt = MyConnection.prepareStatement(MySQLQuery)) {
for (int q = 0; q < arr.length; q++) {
preparedStmt.setString(q + 1, arr[0]);
preparedStmt.setString(q + 2, arr[1]);
preparedStmt.setString(q + 3, arr[2]);
preparedStmt.setString(q + 4, arr[3]);
preparedStmt.setString(q + 5, arr[4]);
}
preparedStmt.execute();
} catch (SQLException e) {
e.printStackTrace();
}
}
The Insert statement after an iteration looks like this: INSERT INTO serial (MTSER_CODE, MTSER_SERIAL, MTSER_RECDATE, MTSER_WO, MTSER_WOSUF)" + "VALUES ([800-0022-08, 0025, 2015-09-30, 600040, 115],** Not Specified **,** Not Specified **,** Not Specified **,** Not Specified **)
尝试这样的事情:
for (String[] arr : result) {
try (PreparedStatement preparedStmt = MyConnection.prepareStatement(MySQLQuery);) {
for (int i = 0; i < arr.length; i++) {
preparedStmt.setString(i + 1, arr[i]);
}
preparedStmt.execute();
} catch (SQLException e) {
e.printStackTrace();
}
}
这样做是为 result
列表中的每个 String
数组创建一个新的 PreparedStatement
,并使用数组中的值设置此语句的值。
像这样的大量插入应该使用批处理,确保批次不会太大。
您还应确保清理资源。
try (Connection conn = DriverManager.getConnection(url, userName, password);
PreparedStatement stmt = conn.prepareStatement(sql)) {
int rowCount = 0;
for (String[] row : result) {
for (int i = 0; i < 5; i++) // hardcoded 5 since SQL has 5 markers
stmt.setString(i + 1, row[i]);
stmt.addBatch();
if (++rowCount % 1000 == 0)
stmt.executeBatch();
}
if (rowCount % 1000 != 0)
stmt.executeBatch(); // execute last batch
}
你的问题在这里:
for (int q = 0; q < arr.length; q++) {
preparedStmt.setString(q + 1, arr[0]);
preparedStmt.setString(q + 2, arr[1]);
preparedStmt.setString(q + 3, arr[2]);
preparedStmt.setString(q + 4, arr[3]);
preparedStmt.setString(q + 5, arr[4]);
}
您正在循环 - 如果数组大小为 5,在最后一次迭代中 q = 4
,那么您将设置为 q + 5
,即 9
!
要么不循环:
preparedStmt.setString(1, arr[0]);
preparedStmt.setString(2, arr[1]);
preparedStmt.setString(3, arr[2]);
preparedStmt.setString(4, arr[3]);
preparedStmt.setString(5, arr[4]);
或每次迭代调用一次 setString
循环:
for (int q = 0; q < arr.length; q++) {
preparedStmt.setString(q + 1, arr[q]);
}
我卡住了。我拒绝长时间停留,所以我正在寻求帮助。我想要做的是获取一个我从另一个数据库的 select 语句中检索的结果集,将其放入 ArrayList,然后将数组列表转换为 Java 中的插入准备语句。
** 更新 ** 问题是我得到一个 "java.sql.SQLException: Parameter index out of range (6 > number of parameters, which is 5)." ,这意味着它接收到 6 个参数而不是 5 个,我看不出这是怎么回事。由于在调试器中我正在观察值是否正确更新,但我的逻辑现在不正确。
我 运行 调试器发现我只是将所有值转储到第一个参数中。我明白我需要做什么。这是将ArrayList结果拆分到insert语句的各个参数中。我的大脑死了。一天结束了,这是我的最后一块拼图,所以我可以继续前进。我只是不知道该怎么做。感谢您的帮助!
这就是我的 ArrayList 结果。
[800-0022-08, 0025, 2015-09-30, 600040, 115]
[800-0022-08, 0024, 2015-09-30, 600040, 115]
[800-0022-08, 0008, 2015-09-30, 600040, 115]
[800-0022-08, 0036, 2015-09-30, 600040, 115]
[800-0022-08, 0035, 2015-09-30, 600040, 115]
[800-0022-08, 0034, 2015-09-30, 600040, 115]
代码如下
ResultSet rs = (ResultSet) stmt.executeQuery(query);
ResultSetMetaData rsmd = (ResultSetMetaData) rs.getMetaData();
int numberOfColumns = rsmd.getColumnCount();
int rowCount = 1
ArrayList <String[]> result = new ArrayList<>();
while (rs.next()) {
System.out.println("Row " + rowCount + ": ");
String[] row = new String[numberOfColumns];
for (i = 1; i < numberOfColumns + 1; i++) {
System.out.print(" Column " + i + ": ");
System.out.println(rs.getString(i);
row[i - 1] = rs.getString(i);
}
result.add(row);
System.out.println("");
rowCount++;
}
String Connection = "CONNECTIONSTRING";
String UserName = "USERNAME";
String Password = "PASSWORD";
String MySQLQuery = "INSERT INTO serial (MTSER_CODE, MTSER_SERIAL, MTSER_RECDATE, MTSER_WO, MTSER_WOSUF)" + "VALUES (?,?,?,?,?)";
String Driver = "org.gjt.mm.mysql.Driver";
Class.forName(Driver);
java.sql.Connection MyConnection = (java.sql.Connection) DriverManager.getConnection(Connection, UserName, Password);
java.sql.PreparedStatement preparedStmt;
preparedStmt = MyConnection.prepareStatement(MySQLQuery);
// ** UPDATED FOR LOOP **
for (String[] arr : result) {
try (java.sql.PreparedStatement preparedStmt = MyConnection.prepareStatement(MySQLQuery)) {
for (int q = 0; q < arr.length; q++) {
preparedStmt.setString(q + 1, arr[0]);
preparedStmt.setString(q + 2, arr[1]);
preparedStmt.setString(q + 3, arr[2]);
preparedStmt.setString(q + 4, arr[3]);
preparedStmt.setString(q + 5, arr[4]);
}
preparedStmt.execute();
} catch (SQLException e) {
e.printStackTrace();
}
}
The Insert statement after an iteration looks like this:
INSERT INTO serial (MTSER_CODE, MTSER_SERIAL, MTSER_RECDATE, MTSER_WO, MTSER_WOSUF)" + "VALUES ([800-0022-08, 0025, 2015-09-30, 600040, 115],** Not Specified **,** Not Specified **,** Not Specified **,** Not Specified **)
尝试这样的事情:
for (String[] arr : result) {
try (PreparedStatement preparedStmt = MyConnection.prepareStatement(MySQLQuery);) {
for (int i = 0; i < arr.length; i++) {
preparedStmt.setString(i + 1, arr[i]);
}
preparedStmt.execute();
} catch (SQLException e) {
e.printStackTrace();
}
}
这样做是为 result
列表中的每个 String
数组创建一个新的 PreparedStatement
,并使用数组中的值设置此语句的值。
像这样的大量插入应该使用批处理,确保批次不会太大。
您还应确保清理资源。
try (Connection conn = DriverManager.getConnection(url, userName, password);
PreparedStatement stmt = conn.prepareStatement(sql)) {
int rowCount = 0;
for (String[] row : result) {
for (int i = 0; i < 5; i++) // hardcoded 5 since SQL has 5 markers
stmt.setString(i + 1, row[i]);
stmt.addBatch();
if (++rowCount % 1000 == 0)
stmt.executeBatch();
}
if (rowCount % 1000 != 0)
stmt.executeBatch(); // execute last batch
}
你的问题在这里:
for (int q = 0; q < arr.length; q++) {
preparedStmt.setString(q + 1, arr[0]);
preparedStmt.setString(q + 2, arr[1]);
preparedStmt.setString(q + 3, arr[2]);
preparedStmt.setString(q + 4, arr[3]);
preparedStmt.setString(q + 5, arr[4]);
}
您正在循环 - 如果数组大小为 5,在最后一次迭代中 q = 4
,那么您将设置为 q + 5
,即 9
!
要么不循环:
preparedStmt.setString(1, arr[0]);
preparedStmt.setString(2, arr[1]);
preparedStmt.setString(3, arr[2]);
preparedStmt.setString(4, arr[3]);
preparedStmt.setString(5, arr[4]);
或每次迭代调用一次 setString
循环:
for (int q = 0; q < arr.length; q++) {
preparedStmt.setString(q + 1, arr[q]);
}