使用demo1
String sql="insert into test (id,boolean) values(?,?);";
PreparedStatement pstmt;
int[] i;
try {
pstmt = (PreparedStatement) conn.prepareStatement(sql);
for(int j = 0; j < 2; j++){
pstmt.setInt(1, j);
pstmt.setBoolean(2, true);
pstmt.addBatch();
}
i = pstmt.executeBatch();
conn.commit();
pstmt.clearBatch();
pstmt.close();
conn.close();
} catch ...
使用demo2
sql = "insert into typetest (id,docblob) values(?,?)";
pstmt = (PreparedStatement) conn.prepareStatement(sql);
pstmt.setInt(1, person.getId());
pstmt.setBlob(2, new ByteArrayInputStream(data));
pstmt.addBatch(); //将pstmt中的预处理语句和参数拷贝至新的队列中,等待执行
i = pstmt.executeBatch();
pstmt.clearBatch();
JDBC源码角度分析其实现
PGjdbc暂不支持 pstmt.addBatch(String)
1、pstmt.addBatch();
如果是第一次执行,对batchStatements 和 batchParameters 初始化
分别copy并add preparedParameters 和 preparedQuery.query至 batchStatements 和 batchParameters里面。
2、pstmt.executeBatch();
a、
if(batchParameters != null && batchParameters.size() > 1 && m_prepareThreshold > 0){//这个条件有什么用? 执行代码块有何作用?
this.preparedQuery.increaseExecuteCount(m_prepareThreshold);
}
b、super.executeBatch();
检查连接是否关闭;
清除之前的警告;
如果batchParameters.size() <= 1|| !(preparedQuery.query instanceof BatchedQuery) 返回,否则 xxx
使用函数内部参数获取全局变量batchParameters 和 batchStatements 的 值,并clear全局变量
设置flag的值,设置选项
使用执行器执行sql语句,同时启动计时器
执行sql过程见附1
c、返回值
返回一个int[], 标记着每条sql语句执行后影响的行数
3、pstmt.clearBatch()
clear batchParameters 以及 batchStatements
附1:JDBC执行SQL的步骤
在执行器执行sql语句前,
会先发送一个 begin Transaction:
根据AutoSave参数来决定是否需要添加savepoint
然后挨个执行sql语句,
然后jdbc发送 sync命令,即意为同步,将数据写入磁盘 并接收从服务端传来的数据
退出函数时ErrorHandler判断是否存在错误,若存在错误 执行 rollback 回退至savepoint
最终通过conn.commit()提交