急急急!!!!!!关于多表的数据修改问题。(50分)

  • 主题发起人 主题发起人 brilliant83
  • 开始时间 开始时间
B

brilliant83

Unregistered / Unconfirmed
GUEST, unregistred user!
[green]请问如何对多个表进行同时的修改,用Table还是Query?

讲的具体一点,最好给出例子,谢谢[/green]。
 
方法有多种,列举其中之一:
procedure TForm1.BitBtn1Click(Sender: TObject);
begin
query1.SQL.Clear;
query1.SQL.Add('update table1 set tb1field1=:tb1field1,tb2field2=:tb1field2 where ...');
query1.SQL.Add('update table2 set tb2field1=:tb2field1,tb2field2=:tb2field2 where ...');
.......
query1.ParamByName('tb1field1').AsString:='???';
query1.ParamByName('tb1field2')...
query1.ParamByName('tb2field1')...
....
query1.ExecSQL;
---------------
(注:为了保持报表更新的一致性,建议在系统中使用自定义(带事务处理的)queryExecSQL过程,
这样在执行类似QUERY更新时,无需单独实施事物处理。)
end;
 
用存储过程最好!
这样可以保证数据的完备性。要不全部修改成功,要不全部失败。
而且根据你的需要,用存储过程可以大大降低网络上的数据传输量。
 
>>请问如何对多个表进行同时的修改,用Table还是Query?
肯定用QUERY了,前面的不行。建议你用ADODATASET,这是很好的选择。一般不用你作
特殊的处理,它能自动更新多表的关联,但你自己要处理 事物 trans
 
请教 wumeng大侠:
前面的哪里不行啊? 呵呵)
 
在你执行execsql语句之前,你可以尝试看一下query1.sql.text,你就知道错误的所在了。
你的query1.sql.text中应该包含了两部分的update操作。
如果用query来操作,应该是下面的流程:
bcommit := true;//bool型变量,用来控制最后是提交还是回滚
database.starttrans;
with query1 do
begin
try
Close;
finally
end;
query1.text := '...';//只能是对其中一个表
try
execsql;
except
//...
bcommit := false;
end;
try
Close;
finally
end;
query1.text := '...';//再对另一个表进行操作
try
execsql;
except
//...
bcommit := false;
end;
end;
if bcommit then
database.commit
else
database.rollback;
 
to armyjiang 大侠:
说实在的,我没有查到证明您的观点完全正确的依据,前面的方法我已经测试过,事实上是完全可行的
而且十分方便有效,有兴趣的话您可以在 BDE+SYBASE11.9的环境下试一下,想听您的高见。谢谢!
 
>> 前面的哪里不行啊? 呵呵)
>>请问如何对多个表进行同时的修改,用Table还是Query?
肯定用QUERY了,前面的不行。

指的是TABLE不行呀?!它在QUERY的前面嘛。。。:)
 
to smallbs:
我不习惯使用sybase,但是应该是相同的吧!
如果按照你那样的操作,在执行execsql之前,query1.sql.text为下面的内容:
update table1 set tb1field1=:tb1field1,tb2field2=:tb1field2 where ...update
table2 set tb2field1=:tb2field1,tb2field2=:tb2field2 where ...
我不清楚你如何能够在sybase中保证这样语句的正确执行?
或者是你在第一个update语句中包含了行分隔符(;),如果是这样的话,估计在sybase
中是可行的。
但是如果这样写的话实在不利于程序的调试,你说呢?
 
to armyjiang:
这个帖子为我们提供了讨论的机会,得谢谢喽主了
对于 update table1...和 update table2....的内容完全可以在设计期间写好在query的sql里面,
以后在数据更新时直接用query1.ParamByName赋值就行了,所以调试起来更方便。
另外SYBASE对多个UPDATE的处理无需特殊的分隔符,只要分行写就行了,这样的写法对于其他数据库也许不行,
可正象你所说的,如果在多个UPDATE语句之间加上(;)、(go)或其他被认可的分隔符是否可行呢?
 
to smallbs:
我说的不利于调试的意思是:如果在更新数据库的过程中出现了差错,那么按照你
的表示方式来测试的话会麻烦些,而按照我所写的方式可以实现单步跟踪。
另外,对于sybase来说,既然支持这种方式,是否可以理解为我可以不用很关心数据库
的事务处理?我只要将应该在一个事务内完成的动作以这样的格式来写,那么就根本是一个
事务中的事情了。
公司里的数据库服务器趴下了,暂时没法试,不过估计是有问题。
 
使用自定义的queryExecSQL过程(带事务处理功能)取代query.ExecSQL,
2年来还没有发现问题哦
 
>>使用自定义的queryExecSQL方法(带事务处理功能)取代query.ExecSQL,
>>2年来还没有发现问题哦

能不能把源码或思路贴出来???
 
procedure QueryExecSQL(Query:TQuery);
begin
database.StartTransaction;
try
query.ExecSql;
database.Commit;
except
database.Rollback;
end;
end;
就是这个意思,有问题吗?
 
有意思!
这叫“自定义的queryExecSQL方法”吗?
和我前面所贴的源码意思是完全一样的。只是你这边用的是sybase数据库,可以合并成一个
query的一次运行,而我所贴的源码是考虑到要使用多次query的结果。我只能在最后再判断
是commit还是rollback了。
当然,再啰嗦一些,从第二个try开始,就可以先判断标志的值,如果标志已经被置位,就
不必再执行了,直接转到外层去做rollback。
 
哈哈!!! 如果有20表同时更新,照你那样的写法是不是很麻烦呢?
总而言之,你也没有发现我错误(不行)的地方,这是本次讨论的主题。
谢谢你,也许我们以后会成为好朋友的,拜拜!
 
谢谢各位的作答,我是个初学者,希望大家能够多帮帮我,如何入门Delphi?
 
to smallbs:
这次就到这里,下次有机会再聊!

to brilliant83:
你的要求有点过分了,还是到其他栏目去开题讨论“如何入门Delphi”吧!
 
好的,谢谢大家了
 
多人接受答案了。
 
后退
顶部