丢失数据(Lost Update)
在下表中,T1、T2、T3、T4表示时间顺序
-----------------------------------------------------------
用户 T1 T2 T3 T4
A X=40 X=X-30B X=40 X=X-20
-----------------------------------------------------------
假设用户A和B都读取X(X=40),然后分别把X减少30和20.用户A在T3把改后的X(X=10)写入数据库.随后,用户B在T4把改后的X(X=20)写入数据库.于是对用户A而言,他的修改在T4处丢失了.脏读数据(Dirty Read)
请看下表,
-----------------------------------------------------------
用户 T1 T2 T3 T4
A X=40 X=X+30 ROLLBACKB X=70
-----------------------------------------------------------
用户A在T2把X增加了30(尚未写入数据库),用户B在T3由数据缓存读出X=70.但用户A在T4
时撤消(Undo)了对X的修改,数据中仍维持X=40.但用户B已把数据(X=70)取走.不能重复读(Non-Repeatable Read)
--------------------------------------------------------------------------------------------
用户 T1 T2 T3 T4 T5 T6
A X=40 Y=30 X+Y=70 Z=30 X+Y+Z = 100
B X=40 X=X+20 COMMIT X=X-20
用户A、用户B分别读取X=40后,在T3用户取出Y=30并计算X+Y=70。在T4时用户B把 X增加20,并于T5把(X=60)
写入数据库。在T6时间,用户A取出Z(Z=30)并继续计算X+Y+Z=100。但如果用户A为进行核算而把X、Y、Z重读
一次再进行计算,却出现X+Y+Z = 120! (X已增加20)。
在下表中,T1、T2、T3、T4表示时间顺序
-----------------------------------------------------------
用户 T1 T2 T3 T4
A X=40 X=X-30B X=40 X=X-20
-----------------------------------------------------------
假设用户A和B都读取X(X=40),然后分别把X减少30和20.用户A在T3把改后的X(X=10)写入数据库.随后,用户B在T4把改后的X(X=20)写入数据库.于是对用户A而言,他的修改在T4处丢失了.脏读数据(Dirty Read)
请看下表,
-----------------------------------------------------------
用户 T1 T2 T3 T4
A X=40 X=X+30 ROLLBACKB X=70
-----------------------------------------------------------
用户A在T2把X增加了30(尚未写入数据库),用户B在T3由数据缓存读出X=70.但用户A在T4
时撤消(Undo)了对X的修改,数据中仍维持X=40.但用户B已把数据(X=70)取走.不能重复读(Non-Repeatable Read)
--------------------------------------------------------------------------------------------
用户 T1 T2 T3 T4 T5 T6
A X=40 Y=30 X+Y=70 Z=30 X+Y+Z = 100
B X=40 X=X+20 COMMIT X=X-20
用户A、用户B分别读取X=40后,在T3用户取出Y=30并计算X+Y=70。在T4时用户B把 X增加20,并于T5把(X=60)
写入数据库。在T6时间,用户A取出Z(Z=30)并继续计算X+Y+Z=100。但如果用户A为进行核算而把X、Y、Z重读
一次再进行计算,却出现X+Y+Z = 120! (X已增加20)。
解决方案 »
- 请问Delphi怎样读取WORD的内容,以及怎样判定是表格,还是图片,以及文字的字体,字号,颜色等?
- dephi,java,.net,学哪一个比较好。
- 如何设置dbedit组件的格式
- 为何我使用ADOConnection,ADOTable,DataSource导入EXCEL数据到DBGRID时,
- 不知如何是好????
- 连接 mysql 中文问题
- 只有高手才能解决这个问题了。。焦急等待中。。。。
- delphi socket 写server代码,最多能连多少个客户机
- 明天就是圣诞节了,在此祝远方的兄弟姐妹们节日快乐,天天都有个好的心情
- ApplyUpdates(0)成功保存后问题
- 如何删除二进制流文件中的某条记录(小难),马上给分
- 怎么在字符串列表中假如图片?Tlistbox?
其实Non-Repeatable Read是有行锁的。
解决办法很简单:
1.采用存储过程更新。
create procedure change_x @a integer
as
begin
update yourtab set x = x - a
end
即可保证
2.如果一定要将x读到客户端
update yourtable set x=x-a where x=70
假如你读的客户端x是70
这样,你判断是否有更新@@RowCount>0,表示没人修改过x,修改成功
如果没有修改@@RowCount=0表示你读的数据已经脏了。
3.其实很多开发工具直接支持这样操作
如:Delphi,如果用Post更新,你可以设定TDataBase中的隔离级别,或
TQuery中的UpdateMode
有关问题请参见:
http://www.microsoft.com/china/msdn/technic/develop/database/12