问题描述
SqlTransactionmyTrans;myTrans=myConnection.BeginTransaction();myCommand.Connection=myConnection;myCommand.Transaction=myTrans;try{//第一条SQL语句myCommand.CommandText="insertintodb_user(Id,UserPwd)values('111,'123456')";myCommand.ExecuteNonQuery();//第二条SQL语句myCommand.CommandText="insertintodb_user(Id,UserPwd)values('222,'123456')";myCommand.ExecuteNonQuery();myTrans.Commit();}catch(Exceptione){myTrans.Rollback();//这里有什么用呀??}finally{myConnection.Close();}问题描述:(1)如果两条SQL语句中第二条出问题,那么应该不会执行Commit语句,转而去执行myTrans.Rollback();第一条SQL中的数据不会插入.这个很容易理解.(2)但是我发现如果把myTrans.Rollback();注释掉,也就是不写回滚操作,第一条SQL中的数据也不会插入到表中.(3)也就是说写与不写RollBack()都一回事,只要打开了事务就可以了:myTrans=myConnection.BeginTransaction();.结论:也就是说.Net中提供的RollBack()方法根本就没用处.?请大家编程试试,不要乱说,省的让大家搞不明白...,我十分清楚事务的概念,请大家不要对这个解释.
解决方案
解决方案二:
开启事务后,如果没有Commit,就不会提交,因为报错后没有执行Commit
解决方案三:
你不写的话它自己就隐士的调用而已,,写了就显示的调用,仅此而已
解决方案四:
上家答非所问.不要乱回帖!
解决方案五:
哦.是上上家.
解决方案六:
不一定出现错误才要回滚可以是满足一定条件时需要回滚,执行RollBack()
解决方案七:
这个问题其实早就已经说过了,通过添加数据库监视,你会发现只要加了事物在执行SQL过程发生异常,默认状态下是回滚的,而且还能监视到事物回滚的事件,除非语句正常执行,而不管你是不是明显的设置了myTrans.Rollback();ADO.NET事务实际上是把事务上下文传递到数据库层,如果事务中发生一个错误,数据库会自动回滚。在你的错误处理代码中,每次调用Rollback()方法之前检查事务对象是否存在是一种良好的习惯。这样的一个例子是当一个死锁发生的同时,数据库正在执行自动回滚。
解决方案八:
引用3楼的回复:
上家答非所问.不要乱回帖!
你才在乱回帖。。。。你看懂了没有?????????
解决方案:
正常地写上using(varcon=GetConnection()){vartran=con.BeginTransaction();......tran.Commit();}
这就行了。用不着些什么Rollback!
解决方案:
引用楼主的回复:
也就是说.Net中提供的RollBack()方法根本就没用处.?
这是初学者的问题。专业的开人员应该结合.net源代码去学习,而不是“靠揣测.net而过活”。在SqlConnection被GC销毁时,会在Dispose方法中自动调用其Close方法。而这个Close做什么,你自己看吧。
解决方案:
引用楼主的回复:
也就是说.Net中提供的RollBack()方法根本就没用处.?
这是初学者的问题。专业的开人员应该结合.net源代码去学习,而不是“靠揣测.net而过活”。在SqlConnection被GC销毁时,会在Dispose方法中自动调用其Close方法。而这个Close做什么,你自己看吧。
解决方案:
大家还是没有回答到点子上,或者说跟我理解的是一样的.就是没必要有RollBack().你们做做测试,不要拿你们自以为的经验来回帖.要知道你们的经验都是复制了别人的.问题其实很简单:(1)如果开通了事务,并且出了异常,那就没有Commit,干嘛还要有RollBack()?,(2)如果没异常,那就commit了,RollBack()也没用.所有没必要RollBack(),或者说这个功能没用.所有大家最后把这个RollBack()功能解释清楚,千万别自以为是.
解决方案:
如果开通了事务,并且出了异常,那就没有Commit?你怎么知道没有提交?当你第一条数据正常,而异常出现在第二句的时候,那么第一条是能正常添加入库的,但是由于捕获了异常,那么数据库就自动回滚了,就造成了全部没有入库的假象(这可以通过监视来得到证明,至少自增ID的确是+了1个的,这就说明第一条的确曾经入库过)虽然我没研究过这其中的源码究竟是如何封装或者处理的,但是我们完全可以通过一些测试来查看处理过程,就像sp1234说的,SqlConnection被GC销毁时,会在Dispose方法中自动调用其Close方法。而这个Close做什么这些你得研究源码了,c#本身就高度抽象,高度封装,我们更在意的是这个东西它能做什么。个人看法。
解决方案:
引用8楼的回复:
正常地写上C#codeusing(varcon=GetConnection()){vartran=con.BeginTransaction();......tran.Commit();}这就行了。用不着些什么Rollback!
这个代码就是我遇到的问题,,我之前因为没有commit();然后数据插入就有问题了。。LZ这个代码的情况假如向下面啊:你的数据插入都完全正确,但在Try中出现异常,那么也会到catch中去。。这个也是有这样的需求的。。Commit()的作用了就是判断事物的正确与否,正确的话就插入数据,错误就rollback
解决方案:
我知道开启事务后,第一条SQL中数据会隐式地插入数据库中,这个可以在第一条SQL和第二条SQL之间,插入一条读取表中全部记录的SQL看到第一条SQL中的数据已经隐式地插入数据库中.但在数据库中没看到相应的记录,也就是说没提交.只是我不清楚,如果第二条SQL语句出现异常,把catch语句中的RollBack()也注释掉和不注释,都能够回滚.也就是说出了异常,那么就会自动执行这个RollBack().这在微软的MSDN中看到了这个解释.现在从大家的回复和微软的解释,可以得出如下结论:出现异常,会自动回滚.但是又有下述问题:(1)它自动回滚是发生在什么时候?难道发生异常,就回滚?这岂不是很荒谬,如果不是SQL异常,而是其它异常,我们肯定不会去回滚的,而是报其它异常就够了.(2)还有怎么就找不到取消自动回滚的语句,而采取手动回滚呢?例如像我例子中的显示回滚.
解决方案:
引用14楼的回复:
我知道开启事务后,第一条SQL中数据会隐式地插入数据库中,这个可以在第一条SQL和第二条SQL之间,插入一条读取表中全部记录的SQL看到第一条SQL中的数据已经隐式地插入数据库中.但在数据库中没看到相应的记录,也就是说没提交.只是我不清楚,如果第二条SQL语句出现异常,把catch语句中的RollBack()也注释掉和不注释,都能够回滚.也就是说出了异常,那么就会自动执行这个Ro……
问题1:你说的错误的.......sql语句没有错误那么就会插入的...假如你的catch中没有rollback();但是sql语句正确..但是在执行非sql的某个东西出现异常时.....还是会插入数据的.......这个就是问题2的所在也...
解决方案:
引用6楼的回复:
这个问题其实早就已经说过了,通过添加数据库监视,你会发现只要加了事物在执行SQL过程发生异常,默认状态下是回滚的,而且还能监视到事物回滚的事件,除非语句正常执行,而不管你是不是明显的设置了myTrans.Rollback();ADO.NET事务实际上是把事务上下文传递到数据库层,如果事务中发生一个错误,数据库会自动回滚。在你的错误处理代码中,每次调用Rollback()方法之前检查事务对象……
楼主自己没看懂吧,人家已经说的很清楚了
解决方案:
1.不管你做不做,.net框架都会帮你做,及时.net框架不做(断电),oracle(或其它)也会帮你做;2.事务回滚:当事务修改表中数据的时候,该数据修改前的值(即前影像)会存放在回滚段中,当用户回滚事务(ROLLBACK)时,ORACLE将会利用回滚段中的数据前影像来将修改的数据恢复到原来的值。
解决方案:
rollback()是有作用的。建议你问度娘事务处理的概念。rollback()就是说你的所有sql语句,要么全部执行,要么全部不执行。就像入库一样,入库了以后入库前的数量减少,库存量增加。若中间sql语句有一句出错了,没有用rollback的话,入库前的数量减少了,但库存量却没有增加。所以,语句必须要么全部执行,要么全部不执行。
解决方案:
完全可以认为,rollback是为了语义上的完整性定义的,一般写法只要启用事务了,记得commit就行begintransactioninsert(a)insert(b)rollbackinsert(c)commit这种用法少之又少(不提交a,b,只提交c)
解决方案:
事务挂起是消耗SQL资源的。。。。你显示的通知RollBack,能够立刻释放资源,而你如果等Frame自动来RollBack事务,万一Frame因为代码问题不能关闭连接了???那你这个资源就一直被占用???你可以试下不执行Close,然后用其它数据库连接去访问下相关表,确认下你的访问是否能够正常
解决方案:
Rollback()是数据回滚,你的代码是插入两条数据,如果其中一条插入失败,那么这两条数据都不会插入都数据库当中。举个例:你到银行开户,开户的时候中假设最少要存100块,这就相当有两个表,一个开户一个存款你开户几就是插入数据insertintot_uservalues(张三,12345678)(有个自动标识列,id=1000)insertintot_Bankvalues(1,1000,100,dataTime.Now());这两条数据是同时进行的假设你刚开完户第一条数据刚插入就停电了这时Rollback()就会出现,数据就会回滚,这样第一条数据就回滚就相当于没插入
解决方案:
新手,同问看了那么多的回复学习了但我还想问,如果是嵌套的try,两个tryusing(TransactionScopescope=newTransactionScope()){try{conn.Open();SqlCommandcmd_1=newSqlCommand(cmd_Text_1,conn);cmd_1.ExecuteNonQuery();try{SqlCommandcmd_2=newSqlCommand(cmd_Text_2,conn);cmd_2.ExecuteNonQuery();}catch(Exceptionex){thrownewException(ex.Message);}scope.Complete();}catch(Exceptionex){thrownewException(ex.Message);}finally{scope.Dispose();}}这样的话也还是直到scope.complete()才是执行sql语句的而默认的回滚,也是整个操作的回滚,是这样理解的么?
解决方案:
vartran=con.BeginTransaction();insert1insert2return;tran.commit();这种是不会提交数据的吧
解决方案:
没提交,自然不会插入了。
解决方案:
已经说的很清楚了并不是Rollback函数没用而是不需要你手动去调用,人家自己自动调用了而已