SQLRPGLE中执行INSERT语句插入数据时如何同步获取记录数
SQLRPGLE中INSERT操作同步获取插入记录数的实现方案
该需求完全可实现,不需要在INSERT执行后额外运行COUNT语句统计。你最初答复的事后COUNT方案不仅在大表场景下性能很差,在多用户并发写入、事务隔离级别限制的场景下,统计结果还会包含非本次操作插入的记录,准确性无法保证。
方案1:直接读取SQL通信区(SQLCA)内置计数字段(最常用)
SQLRPGLE的SQL预编译器会自动维护SQL通信区结构,每执行完一条SQL语句,DB2 for i会自动将本次语句实际处理的记录数写入SQLERRD(3)字段,INSERT语句执行完成后直接读取该字段即可拿到准确的插入行数,不需要额外执行任何SQL查询。
该方案支持所有INSERT场景:单行VALUES插入、多行VALUES批量插入、基于SELECT子查询的批量插入均可正确统计。
示例代码:
DCL-S INSERT_SUCCESS_CNT INT(10); // 执行目标INSERT语句 EXEC SQL INSERT INTO MYLIB/TARGET_FILE (COL1, COL2, COL3) SELECT S_COL1, S_COL2, S_COL3 FROM MYLIB/SOURCE_FILE WHERE FILTER_CONDITION = '1'; // 直接读取本次INSERT的成功插入行数 INSERT_SUCCESS_CNT = SQLERRD(3); // 后续可直接基于该值做业务判断,比如判断是否有数据插入、写入操作日志等 IF INSERT_SUCCESS_CNT = 0; // 无符合条件数据插入的对应处理逻辑 ENDIF;
注意点:
- 该字段统计的是当前会话、当前刚执行的这条INSERT语句实际成功落库的行数,不会受其他会话写入操作影响,不存在并发统计偏差
- 如果INSERT过程中触发了唯一键冲突、约束校验失败、触发器回滚等情况,该字段只会统计最终插入成功的记录数,结果准确
方案2:使用标准SQL诊断语句获取(兼容性更好)
如果需要更贴合通用SQL标准的写法,也可以在INSERT执行完成后立刻通过GET DIAGNOSTICS语句获取行数,在IBM i 7.1及以上版本均支持,效果和读取SQLERRD(3)完全一致:
DCL-S INSERT_SUCCESS_CNT INT(10); // 执行INSERT语句 EXEC SQL INSERT INTO MYLIB/TARGET_FILE (COL1, COL2) VALUES('A', 'B'); // 通过诊断区拿行数 EXEC SQL GET DIAGNOSTICS :INSERT_SUCCESS_CNT = ROW_COUNT;
注意:不要在INSERT和读取计数的语句之间插入其他SQL操作,否则
SQLERRD(3)和诊断区的ROW_COUNT值会被后续SQL语句的执行结果覆盖,导致计数错误。
内容的提问来源于stack exchange,提问作者Kunal Roy
相关产品推荐
相关产品推荐

