我遇到一个问题: A表中有关键字feild1 
事务开始 
delete From A where A.field1=1 
Insert into A(Field1) values(1) 
事务提交 这段sql正确吗?我的意思是在同一个事务中,数据库表的数据会被先删除掉吗? 
我的程序中是执行失败,提示关键字重复。 
有无大侠讲解一下

解决方案 »

  1.   


    --测试环境
    create table table1(id int primary key)
    insert table1 select 1
    union  all    select 2
    --查看表
    select * from table1
    --操作A(执行错误后,事务没有回滚)
    begin tran
    delete From table1 where id=1 
    Insert into A(Field1) values(3) --事务没有回滚
    commit tran
    --操作B(执行错误后,事务回滚)
    BEGIN TRY
    begin tran//创建还原点
    delete From table1 where id=1 
    Insert into A(Field1) values(3) 
    commit tran//提交数据
    END TRY
    BEGIN CATCH
      ROLLBACK//遇到问题,捕获后回滚到还原点
    END CATCH
      

  2.   


      con1.BeginTrans;
      try
         with qry1 do
         begin
           close;
           sql.clear;
           sql.Text:='delete From table1 where id=1 ;Insert into table1(Field1) values(3)';
           ExecSQL;
         end;
         con1.CommitTrans;
      except
         con1.RollbackTrans;
      end;
      

  3.   

    在同一个事物中的SQL语句A,B
    必须都成功才能提交,否则就会回滚。
    如果只有A成功或者B成功都是会回滚的,意思是你的A,B语句不会对数据库产生任何影响。不过建表语句和TRUNCATE语句不受事务控制。
      

  4.   

    我要问的不是出错怎么处理,而是在一个事务中,删除了一个关键字=1的记录,再插入一条关键字=1的记录,逻辑上是否正确?即再insert的时候会不会说关键字重复?
      

  5.   

     
    程序的執行都是由上至少的,肯定是先被刪除再執行插入。  你如果想這兩個操作必須同時完成,可翠加上事務去處理,代碼如下:
    begin tran
    delete From A where A.field1=1 
    Insert into A(Field1) values(1) 
    commit Tran
      

  6.   

    是正确的,事务只是为了保证数据的完整性,简单的理解是要么都执行成功,要么都不成功出错回滚到执行前的状态。你的代码中确定表field1是关键字吗。
    create table tmp(id int primary key);
    insert into tmp values(1);
    insert into tmp values(2);
    insert into tmp values(1);(所影响的行数为 1 行)
    (所影响的行数为 1 行)服务器: 消息 2627,级别 14,状态 1,行 1
    违反了 PRIMARY KEY 约束 'PK__tmp__1FCDBCEB'。不能在对象 'tmp' 中插入重复键。
    语句已终止。procedure TForm1.Button1Click(Sender: TObject);
    begin
      adoconnection1.BeginTrans;
      try
        with adoquery1 do
        begin
          close;
          sql.text := ' delete from tmp where id=1';
          ExecSql;
          sql.Text := ' insert into tmp values(1)';
          ExecSql;
          sql.Text := ' insert into tmp values(3)';
          ExecSql;
        end;
        adoconnection1.CommitTrans;
        showmessage('ok');
      except
        adoconnection1.RollbackTrans;
      end;
    end;我利用的sqlserver来测试的。