批量更新
命令格式
当执行大量的 Insert\Update\Delete 语句时,通过调用 VDN 的 Batch 指令,可以集中提交,大幅度提高执行速度:互联网下最高为直连的 30 倍。
语法 VesnCommand <Batch 指令> {NoChangeError;}{Package;} {rows=语句数量;}
| 参数 | 必须 | 说明 |
|---|---|---|
| VesnCommand | 必须 | 指令语法前缀,区分大小写 |
| Batch指令 | 必须 | Batch Begin: 通知VDN开始批量执行,这之间的Insert\Update\Delete语句都不会提交到服务器。 Batch Options:位于Begin和End指令之间,指定之后执行SQL语句的特性(明细见下表) Batch End:通知VDN开始向服务器提交语句。 |
| NoChangeError | 可选 | 当更新语句影响数据条数为0时,返回 Row changed between retrieve and update. 错误 |
| Package | 可选 | 如果有该参数,指令到服务器端将批量执行,执行速度更快,否则指令到服务器端后依然按照客户端的形式单条执行。 主指令使用Package后,Batch Options指令将无效 注:只有在没有该参数的情况下才能准确返回错误行数,该参数仅适用于SQLSERVER(V2016.10.1.1版本后支持) |
| rows | 可选 | 当提前可以预知语句数据量时,指定rows参数,这样当最后一条语句时VDN会开始提交这批语句,并返回信息,这样就不需要执行Batch End语句了。例如:rows=dw_1.modifiedcount( )+dw_1.deletedcount( ) |
| Identity | 可选 | 要执行的批量更新语句包含自增序列(Identity Column)(V2018.3.1.10之后支持) |
| Encrypt | 可选 | 当链接串参数指定了加密,批量更新默认也是不进行加密的,除非在这里使用Encrypt参数 |
然后通过 EXECUTE IMMEDIATE 调用该语句
注:如果 DataWidnow 使用批量提交,错误将会在最后一条语句返回。DisableBind=0 不能使用批量更新。
如果 DataWindow 的 Update 属性中 Key Modification 中选择的 Use Delete then Insert 时不要使用该方法,选择方法二
Commit 或者 Rollback 会清空没有执行的 Batch 语句。
选项指令(V2018.3.1.10 之后支持),通过选项指令可以按组设定要执行的语句的特性。
语法 语法 VesnCommand Batch Options {Scope=来源名称;} {Identity;}
| 参数 | 必须 | 说明 |
|---|---|---|
| Scope | 可选 | 自定下面要执行语句的来源名称。这个Scope将在发生错误时出现在错误信息中。便于区分语句来源,相当于给SQL语句进行了分组执行 示例: VesnCommand Batch Options Scope=dw_1 |
| Identity | 可选 | 指定该组SQL语句包含自增序列(Identity Column) 通过选项指令指定的Identity可以按组设定,既这组SQL语句包含SQL语句,另外一组不SQL语句包含。如果Identity在Begin指令中则代表本次执行所有语句都包含,不可取消。 |
| Package | 可选 | 如果有该参数,指令到服务器端将批量执行,执行速度更快,否则指令到服务器端后依然按照客户端的形式单条执行。 注:只有在没有该参数的情况下才能准确返回错误行数,该参数仅适用于SQLSERVER Scope配合错误信息中将包括Scope指定的名称 (V2019.1.1.2版本后支持) |
方法一、定量更新
指定语句数量

代码:
string ls_batch
dw_1.accepttext()
ls_batch="VesnCommand Batch Begin NoChangeError rows="+string(dw_1.modifiedcount( )+dw_1.deletedcount( ))
EXECUTE IMMEDIATE :ls_batch;
if dw_1.update() =1 then
addinf("Update成功:" +string(sqlca.SQLNRows))
else
showerror()
end if或者可以在 Datawindow 的UpdateStart函数里执行该语句。

代码
String ls_batch
Int li_i,li_count
Boolean lb_ident = False
//如果有Identity列不能使用批量更新
li_count = Integer(This.Describe("DataWindow.column.count"))
For li_i = 1 To li_count
If This.Describe("#"+String(li_i)+".Identity") = 'yes' Then
lb_ident = True
Exit
End If
Next
//批量处理指令
If lb_ident = False Then
ls_batch = "VesnCommand Batch Begin NoChangeError rows="+String(this.ModifiedCount( )+this.DeletedCount( ))
Execute Immediate :ls_batch;
End If方法二、范围更新
不指定语句数量,通过 VesnCommand Batch End;指令提交语句。

代码
EXECUTE IMMEDIATE "VesnCommand Batch Begin";
insert....;
update....;
delete....;
dw.update(true,false)
insert....;
..........
EXECUTE IMMEDIATE "VesnCommand Batch End";
if sqlca.sqlcode=0 then
dw.resetUpdate()
addinf("Update成功" +string(sqlca.SQLNRows))
Commit;
else
MessageBox("错误",sqlca.SQLErrText)
Rollback;
end if或者带上 Package 选项
EXECUTE IMMEDIATE "VesnCommand Batch Begin Package";
insert....;
update....;
delete....;
dw.update(true,false)
insert....;
..........
EXECUTE IMMEDIATE "VesnCommand Batch End";
if sqlca.sqlcode=0 then
dw.resetUpdate()
addinf("Update成功" +string(sqlca.SQLNRows))
Commit;
else
MessageBox("错误",sqlca.SQLErrText)
Rollback;
end if