分类:
2009-10-11 11:16:56
来源:cww 在VB所用的MDB数据库来说,锁定可以分成 1.整个数据库的层级 以独占方式开启(OpenDatabase的第二个叁数为true表示Exclusive Mode) Dim db As Database Set db = OpenDatabase("f:\vbprg\chart", True) '独占方式Open Database 如果成功了,别人也就没有办法与你共用该Database 2.锁定Table的层级 在OpenRecordset 时设定第三个叁数为dbDenyRead + dbDenyWrite 便可以防上他人 同时开启该Table,而使用这种Table Lock,其第二个叁数只能是dbOpenTable或是 dbOpenDynaset,而dbOpenDynamic、dbOpenSnapshot等则不能使用Table Lock 如下,产生一个独占的rs RecordSet。 Set rs = db.OpenRecordset(TableName, dbOpenTable, dbDenyRead + dbDenyWrite) 3.锁定Page的层级,这又分 a.悲观锁定 'RS 是 RecordSet物件的引用 RS.LockEdit = True 时是悲观的锁定,也就是说,如果RecordSet物件下.Edit方法成功时,便会将该 Record所在的Page加以锁定,一直到.Update/.CancelUpdate 才解锁。底下有一 个Function RecordEdit(recst As Recordset, Optional ntimes) As Boolean 用在悲观的锁定,ntime表示尝试锁定多少次,超过次数後才失败传回False。 b.乐观的锁定 RS.LockEdit = False 当RecordSet物件下.Edit的方法後,并没有Lock该Page,直到下.Update时才Lock 之後立即解锁,这个方式的特性是,在.Edit之後如果同一笔Record已被他人先修 改过,那麽我们下的.Update方法会有错误,此时配合On Error的方式,再下一次 .Update的方法,来更动成我们所要的内容。另外有一个Function RecordUpdate(recst As Recordset, Optional ntimes) As Boolean 用在乐观的锁定,ntime表示尝试Update多少次,超过次数後才失败传回False。 一个Page内会有一笔以上的Record,所以PageLock时,在同一个Page下的所有Record都 会被Lock住,而Access的数据库没有办法做到Record Lock这和XBase有所不同;那有没 有可能一笔Record超过一个Page,而变成Page Lock时并没有Lock住该笔Record的全部, 我想,这应不可能,因为一笔Record的最大长度有限制,超过时根本没有办法建立该 Table,而Binary/Meno 之类的大量资料,并不是和其他的这些资料放在一起。
'开启一个表格,db:表格所在的Database引用, rs 传回该表格的RecordSet 'TableName表格名称,ExclusiveMode:是否独占开启。 Public Function OpenTable(db As Database, rs As Recordset, ByVal TableName As String, ByVal ExclusiveMode As Boolean) As Boolean Dim i As Integer On Error GoTo ErrHandler OpenTable = True If ExclusiveMode Then Set rs = db.OpenRecordset(TableName, dbOpenTable, dbDenyRead + dbDenyWrite) Else Set rs = db.OpenRecordset(TableName, dbOpenTable) End If Exit Function ErrHandler: OpenTable = False End Function '用在悲观的锁定,ntime表示尝试锁定多少次,超过次数後才失败传回False Public Function RecordEdit(recst As Recordset, Optional ntimes) As Boolean Dim i As Integer i = 0 If IsMissing(ntimes) Then ntimes = 5 End If On Error Resume Next Do While True Err.Clear recst.Edit If Err.Number <> 0 Then If ntimes <> 0 Then If i < ntimes Then i = i + 1 Else RecordEdit = False Exit Do End If End If Else RecordEdit = True Exit Do End If Loop End Function '用在乐观的锁定,ntime表示尝试Update多少次,超过次数後才失败传回False Public Function RecordUpdate(recst As Recordset, Optional ntimes) As Boolean Dim i As Integer i = 0 If IsMissing(ntimes) Then ntimes = 5 End If On Error Resume Next Do While True Err.Clear recst.Update If Err.Number <> 0 Then If ntimes <> 0 Then If i < ntimes Then i = i + 1 Else RecordUpdate = False Exit Do End If End If Else RecordUpdate = True Exit Do End If Loop End Function |