VERSION 5.00 Begin VB.Form Form1 Caption = "Form1" ClientHeight = 1935 ClientLeft = 60 ClientTop = 345 ClientWidth = 3600 LinkTopic = "Form1" ScaleHeight = 1935 ScaleWidth = 3600 StartUpPosition = 3 '窗口缺省 Begin VB.CommandButton Command3 Caption = "与COLLECTION对象运行效率比较" Height = 495 Left = 960 TabIndex = 2 Top = 1320 Width = 1575 End Begin VB.CommandButton Command2 Caption = "哈希表遍历测试" Height = 495 Left = 960 TabIndex = 1 Top = 720 Width = 1575 End Begin VB.CommandButton Command1 Caption = "哈希表" Height = 495 Left = 960 TabIndex = 0 Top = 120 Width = 1575 End End Attribute VB_Name = "Form1" Attribute VB_GlobalNameSpace = False Attribute VB_Creatable = False Attribute VB_PredeclaredId = True Attribute VB_Exposed = False Private Sub Command1_Click() ' Dim cHash As clsHashLK Dim i As Long Set cHash = New clsHashLK cHash.AlloMem 7000 For i = 1 To 2500 cHash.Add i,i * 10 + i Next i For i = 1 To 2500 cHash.Add i,-(i * 10 + i) Next i Debug.Print cHash.Item(11) Debug.Print cHash.Item(-27500) Debug.Print cHash.Item(5500) Debug.Print cHash.IsKeyExist(1),cHash.IsKeyExist(2200) Set cHash = Nothing End Sub Private Sub Command2_Click() ' Dim cHash As clsHashLK Dim i As Long Dim datOne As Long,keyOne As Long,blEndTrav As Boolean Dim strOne As String,lngOne As Long Set cHash = New clsHashLK For i = 1 To 15 cHash.Add i,i * 2 Next i blEndTrav = False cHash.startTraversal datOne = cHash.NextItem(lngOne,strOne,keyOne,blEndTrav) i = 0 Do Until blEndTrav Debug.Print keyOne; "->"; datOne,i = i + 1: If i Mod 5 = 0 Then Debug.Print "" datOne = cHash.NextItem(lngOne,blEndTrav) Loop Debug.Print "" Set cHash = Nothing End Sub Private Sub Command3_Click() ' Command3.Enabled = False Dim cHash As clsHashLK Dim col As Collection Dim datOne As Long,blEndTrav As Boolean Dim sngTimer As Single Dim i As Long sngTimer = Timer Set cHash = New clsHashLK cHash.AlloMem 70000 For i = 1 To 50000 cHash.Add i,i * 10 + i Next i Debug.Print "哈希表插入数据结束,耗时:"; Timer - sngTimer; "秒" sngTimer = Timer Set col = New Collection For i = 1 To 50000 col.Add i,CStr(i * 10 + i) Next i Debug.Print "COLLECTION插入数据结束,耗时:"; Timer - sngTimer; "秒" sngTimer = Timer For i = 1 To 50000 datOne = cHash.Item(i * 10 + i) Next i Debug.Print "哈希表按键访问数据结束,耗时:"; Timer - sngTimer; "秒" sngTimer = Timer With col For i = 1 To 50000 datOne = .Item(CStr(i * 10 + i)) Next i End With Debug.Print "COLLECTION按键访问数据结束,耗时:"; Timer - sngTimer; "秒" sngTimer = Timer cHash.startTraversal datOne = cHash.NextData(blEndTrav) i = 1 Do Until blEndTrav datOne = cHash.NextData(blEndTrav) i = i + 1 Loop Debug.Print "哈希表遍历数据结束,耗时:"; Timer - sngTimer; "秒",i sngTimer = Timer With col For i = 1 To 50000 datOne = .Item(i) Next i End With Debug.Print "COLLECTION遍历数据结束,耗时:"; Timer - sngTimer; "秒",i Set col = Nothing Set cHash = Nothing Command3.Enabled = True End Sub
VERSION 1.0 CLASS BEGIN MultiUse = -1 'True Persistable = 0 'NotPersistable DataBindingBehavior = 0 'vbNone DataSourceBehavior = 0 'vbNone MTSTransactionMode = 0 'NotAnMTSObject END Attribute VB_Name = "clsHashLK" Attribute VB_GlobalNameSpace = False Attribute VB_Creatable = True Attribute VB_PredeclaredId = False Attribute VB_Exposed = False Option Explicit Private Type Hs_DataType Key As Long Data As Long DataLong As Long DataString As String Used As Byte End Type Private lMem() As Hs_DataType,lMemCount As Long,lMemUsedCount As Long Private lMem2() As Hs_DataType,lMemCount2 As Long,lMemUsedCount2 As Long Private mTravIdxCurr As Long Private Const mcIniMemSize As Long = 10 Private Const mcMaxItemCount As Long = 214748364 Private Const mcExpandMaxPort As Single = 0.75 Private Const mcExpandCountThres As Long = 10000 Private Const mcExpandCountThresMax As Long = 10000000 Private Const mcExpandBigPer As Long = 1000000 Private Const mcExpandMem2Per As Long = 10 Private Const mcSeqMax As Long = 5 Public Function Add(ByVal Data As Long,ByVal Key As Long,Optional ByVal DataLong As Long,Optional ByVal DataString As String,_ Optional ByVal RaiseErrorIfNotHas As Boolean = True) As Boolean ' Dim lngIdx As Long If lMemUsedCount + lMemUsedCount2 > mcMaxItemCount Then If RaiseErrorIfNotHas Then Err.Raise 7 Add = False Exit Function End If If IsKeyExist(Key) Then If RaiseErrorIfNotHas Then Err.Raise 5 Add = False Exit Function End If lngIdx = AlloMemIndex(Key) If lngIdx > 0 Then With lMem(lngIdx) .Data = Data .DataLong = DataLong .DataString = DataString .Key = Key .Used = 1 End With lMemUsedCount = lMemUsedCount + 1 Else With lMem2(-lngIdx) .Data = Data .DataLong = DataLong .DataString = DataString .Key = Key .Used = 1 End With lMemUsedCount2 = lMemUsedCount2 + 1 End If mTravIdxCurr = 0 Add = True End Function Public Function Item(ByVal Key As Long,Optional ByVal RaiseErrorIfNotHas As Boolean = True) As Long ' Dim lngIdx As Long lngIdx = FindMemIndex(Key) If lngIdx = 0 Then If RaiseErrorIfNotHas Then Err.Raise 5 Item = 0 Exit Function ElseIf lngIdx > 0 Then Item = lMem(lngIdx).Data Else Item = lMem2(-lngIdx).Data End If End Function Public Function DataLong(ByVal Key As Long,Optional ByVal RaiseErrorIfNotHas As Boolean = True) As Long ' Dim lngIdx As Long lngIdx = FindMemIndex(Key) If lngIdx = 0 Then If RaiseErrorIfNotHas Then Err.Raise 5 DataLong = 0 Exit Function ElseIf lngIdx > 0 Then DataLong = lMem(lngIdx).DataLong Else DataLong = lMem2(-lngIdx).DataLong End If End Function Public Function DataString(ByVal Key As Long,Optional ByVal RaiseErrorIfNotHas As Boolean = True) As String ' Dim lngIdx As Long lngIdx = FindMemIndex(Key) If lngIdx = 0 Then If RaiseErrorIfNotHas Then Err.Raise 5 DataString = "" Exit Function ElseIf lngIdx > 0 Then DataString = lMem(lngIdx).DataString Else DataString = lMem2(-lngIdx).DataString End If End Function Public Function Remove(ByVal Key As Long,Optional ByVal RaiseErrorIfNotHas As Boolean = True) As Boolean ' Dim lngIdx As Long lngIdx = FindMemIndex(Key) If lngIdx = 0 Then If RaiseErrorIfNotHas Then Err.Raise 5 Remove = False Exit Function ElseIf lngIdx > 0 Then With lMem(lngIdx) .Used = 0 .Key = 0 End With lMemUsedCount = lMemUsedCount - 1 Else Dim i As Long For i = -lngIdx To lMemUsedCount2 - 1 lMem2(i) = lMem(i + 1) Next i lMemUsedCount2 = lMemUsedCount2 - 1 End If mTravIdxCurr = 0 Remove = True End Function Private Function AlloMemIndex(ByVal Key As Long,Optional ByVal CanExpandMem As Boolean = True) As Long ' Const cMaxNumForSquare As Long = 46340 Dim idxMod As Long,idxSq As Long Dim idxModRev As Long,idxSqRev As Long Dim lngCount As Long Dim keyToCalc As Long keyToCalc = Key If keyToCalc < 0 Then keyToCalc = 0 - keyToCalc lngCount = lMemUsedCount + lMemUsedCount2 ' 1 idxMod = keyToCalc Mod lMemCount + 1 If lMem(idxMod).Used = 0 Then AlloMemIndex = idxMod: Exit Function ' 2 If keyToCalc <= cMaxNumForSquare Then idxSq = (keyToCalc * keyToCalc) Mod lMemCount + 1 Else idxSq = Sqr(keyToCalc) Mod lMemCount + 1 End If If lMem(idxSq).Used = 0 Then AlloMemIndex = idxSq: Exit Function ' 3 idxModRev = lMemCount - idxMod + 1 If lMem(idxModRev).Used = 0 Then AlloMemIndex = idxModRev: Exit Function ' 4 idxSqRev = lMemCount - idxSq + 1 If lMem(idxSqRev).Used = 0 Then AlloMemIndex = idxSqRev: Exit Function ' 5 If CanExpandMem And lngCount > mcExpandMaxPort * lMemCount Then ExpandMem AlloMemIndex = AlloMemIndex(Key,CanExpandMem) Exit Function End If Dim lngRetIdx As Long Dim idxMdSta As Long,idxMdEnd As Long idxMdSta = idxMod - mcSeqMax idxMdEnd = idxMod + mcSeqMax lngRetIdx = AlloSeqIdx(idxMdSta,idxMod - 1) If lngRetIdx > 0 Then AlloMemIndex = lngRetIdx: Exit Function lngRetIdx = AlloSeqIdx(idxMod + 1,idxMdEnd) If lngRetIdx > 0 Then AlloMemIndex = lngRetIdx: Exit Function Dim lngSqSta As Long,lngSqEnd As Long lngSqSta = idxSq - mcSeqMax: lngSqEnd = idxSq + mcSeqMax If lngSqSta < 1 Then lngSqSta = 1 If lngSqEnd > lMemCount Then lngSqEnd = lMemCount If lngSqEnd < idxMdSta Then lngRetIdx = AlloSeqIdx(lngSqSta,lngSqEnd) If lngRetIdx > 0 Then AlloMemIndex = lngRetIdx: Exit Function ElseIf lngSqEnd <= idxMdEnd Then If lngSqSta < idxMdSta Then lngSqEnd = idxMdSta - 1 lngRetIdx = AlloSeqIdx(lngSqSta,lngSqEnd) If lngRetIdx > 0 Then AlloMemIndex = lngRetIdx: Exit Function Else lngSqSta = 0: lngSqEnd = 0 End If Else If lngSqSta > idxMdEnd Then lngRetIdx = AlloSeqIdx(lngSqSta,lngSqEnd) If lngRetIdx > 0 Then AlloMemIndex = lngRetIdx: Exit Function ElseIf lngSqSta >= idxMdSta Then lngSqSta = idxMdEnd + 1 lngRetIdx = AlloSeqIdx(lngSqSta,lngSqEnd) If lngRetIdx > 0 Then AlloMemIndex = lngRetIdx: Exit Function Else lngRetIdx = AlloSeqIdx(lngSqSta,idxMdSta - 1) If lngRetIdx > 0 Then AlloMemIndex = lngRetIdx: Exit Function lngRetIdx = AlloSeqIdx(idxMdEnd + 1,lngSqEnd) If lngRetIdx > 0 Then AlloMemIndex = lngRetIdx: Exit Function End If End If If lMemUsedCount2 + 1 > lMemCount2 Then lMemCount2 = lMemCount2 + mcExpandMem2Per ReDim Preserve lMem2(1 To lMemCount2) End If AlloMemIndex = -(lMemUsedCount2 + 1) End Function Private Function AlloSeqIdx(ByVal fromIndex As Long,ByVal toIndex As Long) As Long ' Dim i As Long,fCt As Long If fromIndex <= 0 Then fromIndex = 1 If toIndex > lMemCount Then toIndex = lMemCount For i = fromIndex To toIndex If lMem(i).Used = 0 Then AlloSeqIdx = i: Exit Function Next i AlloSeqIdx = 0 End Function Private Sub ExpandMem() ' Dim lngCount As Long,lngPreMemCount As Long lngCount = lMemUsedCount + lMemUsedCount2 If lngCount < lMemCount Then lngCount = lMemCount lngPreMemCount = lMemCount If lngCount < mcExpandCountThres Then lngCount = lngCount * 2 ElseIf lngCount < mcExpandCountThresMax Then lngCount = lngCount * 3 / 2 Else lngCount = lngCount + mcExpandBigPer End If lMemCount = lngCount ReDim Preserve lMem(1 To lMemCount) ReLocaMem lngPreMemCount End Sub Private Sub ReLocaMem(ByVal preMemCountTo As Long) ' Dim memUsed() As Hs_DataType,lngUsedCount As Long Dim i As Long ReDim memUsed(1 To preMemCountTo + lMemUsedCount2) lngUsedCount = 0 lMemUsedCount = 0 For i = 1 To preMemCountTo If lMem(i).Used Then lngUsedCount = lngUsedCount + 1 memUsed(lngUsedCount) = lMem(i) End If Next i For i = 1 To lMemUsedCount2 lngUsedCount = lngUsedCount + 1 memUsed(lngUsedCount) = lMem2(i) Next i ReDim lMem(1 To lMemCount) Erase lMem2 lMemCount2 = 0 lMemUsedCount2 = 0 lMemUsedCount = 0 Dim lngIdx As Long For i = 1 To lngUsedCount lngIdx = AlloMemIndex(memUsed(i).Key,False) If lngIdx > 0 Then lMem(lngIdx) = memUsed(i) lMem(lngIdx).Used = 1 lMemUsedCount = lMemUsedCount + 1 Else lMem2(-lngIdx) = memUsed(i) lMem2(-lngIdx).Used = 1 lMemUsedCount2 = lMemUsedCount2 + 1 End If Next i mTravIdxCurr = 0 End Sub Public Function IsKeyExist(ByVal Key As Long) As Boolean ' Dim lngIdx As Long lngIdx = FindMemIndex(Key) IsKeyExist = (lngIdx <> 0) End Function Public Sub startTraversal() ' mTravIdxCurr = 1 End Sub Public Function NextItem(Optional ByRef rDataLong As Long,Optional ByRef rDataString As String,Optional ByRef rKey As Long,_ Optional ByRef bRetNotValid As Boolean = False) As Long ' Dim lngIdx As Long lngIdx = TraversalGetNextIdx If lngIdx > 0 Then With lMem(lngIdx) NextItem = .Data rDataLong = .DataLong rDataString = .DataString rKey = .Key End With ElseIf lngIdx < 0 Then With lMem2(-lngIdx) NextItem = .Data rDataLong = .DataLong rDataString = .DataString rKey = .Key End With Else bRetNotValid = True Exit Function End If End Function Public Function NextData(Optional ByRef bRetNotValid As Boolean = False) As Long ' Dim lngIdx As Long lngIdx = TraversalGetNextIdx If lngIdx > 0 Then NextData = lMem(lngIdx).Data ElseIf lngIdx < 0 Then NextData = lMem2(-lngIdx).Data Else bRetNotValid = True Exit Function End If End Function Public Function NextDataLong(Optional ByRef bRetNotValid As Boolean = False) As Long ' Dim lngIdx As Long lngIdx = TraversalGetNextIdx If lngIdx > 0 Then NextDataLong = lMem(lngIdx).DataLong ElseIf lngIdx < 0 Then NextDataLong = lMem2(-lngIdx).DataLong Else bRetNotValid = True End If End Function Public Function NextDataString(Optional ByRef bRetNotValid As Boolean = False) As String ' Dim lngIdx As Long lngIdx = TraversalGetNextIdx If lngIdx > 0 Then NextDataString = lMem(lngIdx).DataString ElseIf lngIdx < 0 Then NextDataString = lMem2(-lngIdx).DataString Else bRetNotValid = True Exit Function End If End Function Public Function NextKey(Optional ByRef bRetNotValid As Boolean = False) As Long ' Dim lngIdx As Long lngIdx = TraversalGetNextIdx If lngIdx > 0 Then NextKey = lMem(lngIdx).Key ElseIf lngIdx < 0 Then NextKey = lMem2(-lngIdx).Key Else bRetNotValid = True Exit Function End If End Function Public Function GetDataArray(retData() As Long) As Long ' Dim lngCount As Long Dim i As Long,j As Long lngCount = lMemUsedCount + lMemUsedCount2 If lngCount <= 0 Then GetDataArray = 0: Exit Function ReDim retData(1 To lngCount) j = 1 For i = 1 To lMemCount If lMem(i).Used Then retData(j) = lMem(i).Data j = j + 1 End If Next i For i = 1 To lMemUsedCount2 If lMem2(i).Used Then retData(j) = lMem2(i).Data j = j + 1 End If Next i GetDataArray = lngCount End Function Public Function GetDataLongArray(retDataLong() As Long) As Long ' Dim lngCount As Long Dim i As Long,j As Long lngCount = lMemUsedCount + lMemUsedCount2 If lngCount <= 0 Then GetDataLongArray = 0: Exit Function ReDim retDataLong(1 To lngCount) j = 1 For i = 1 To lMemCount If lMem(i).Used Then retDataLong(j) = lMem(i).DataLong j = j + 1 End If Next i For i = 1 To lMemUsedCount2 If lMem2(i).Used Then retDataLong(j) = lMem2(i).DataLong j = j + 1 End If Next i GetDataLongArray = lngCount End Function Public Function GetDataStringArray(retDataString() As String) As Long ' Dim lngCount As Long Dim i As Long,j As Long lngCount = lMemUsedCount + lMemUsedCount2 If lngCount <= 0 Then GetDataStringArray = 0: Exit Function ReDim retDataString(1 To lngCount) j = 1 For i = 1 To lMemCount If lMem(i).Used Then retDataString(j) = lMem(i).DataString j = j + 1 End If Next i For i = 1 To lMemUsedCount2 If lMem2(i).Used Then retDataString(j) = lMem2(i).DataString j = j + 1 End If Next i GetDataStringArray = lngCount End Function Public Function GetKeyArray(retKeys() As Long) As Long ' Dim lngCount As Long Dim i As Long,j As Long lngCount = lMemUsedCount + lMemUsedCount2 If lngCount <= 0 Then GetKeyArray = 0: Exit Function ReDim retKeys(1 To lngCount) j = 1 For i = 1 To lMemCount If lMem(i).Used Then retKeys(j) = lMem(i).Key j = j + 1 End If Next i For i = 1 To lMemUsedCount2 If lMem2(i).Used Then retKeys(j) = lMem2(i).Key j = j + 1 End If Next i GetKeyArray = lngCount End Function Public Sub Clear() ' Erase lMem Erase lMem2 lMemCount = 0: lMemUsedCount = 0 lMemCount2 = 0: lMemUsedCount2 = 0 lMemCount = mcIniMemSize ReDim lMem(1 To lMemCount) lMemUsedCount = 0 lMemCount2 = 0 lMemUsedCount2 = 0 mTravIdxCurr = 0 End Sub Public Sub AlloMem(ByVal memSize As Long) ' If memSize <= lMemUsedCount Or memSize > mcMaxItemCount Then Exit Sub Dim lngPreMemCount As Long lngPreMemCount = lMemCount lMemCount = memSize ReDim Preserve lMem(1 To lMemCount) ReLocaMem lngPreMemCount End Sub Private Function FindMemIndex(ByVal Key As Long) As Long ' Const cMaxNumForSquare As Long = 46340 Dim idxMod As Long,idxSqRev As Long Dim i As Long Dim keyToCalc As Long keyToCalc = Key If keyToCalc < 0 Then keyToCalc = 0 - keyToCalc ' 1 idxMod = keyToCalc Mod lMemCount + 1 If lMem(idxMod).Used And lMem(idxMod).Key = Key Then FindMemIndex = idxMod Exit Function End If ' 2 If keyToCalc <= cMaxNumForSquare Then idxSq = (keyToCalc * keyToCalc) Mod lMemCount + 1 Else idxSq = Sqr(keyToCalc) Mod lMemCount + 1 End If If lMem(idxSq).Used And lMem(idxSq).Key = Key Then FindMemIndex = idxSq Exit Function End If ' 3 idxModRev = lMemCount - idxMod + 1 If lMem(idxModRev).Used And lMem(idxModRev).Key = Key Then FindMemIndex = idxModRev Exit Function End If ' 4 idxSqRev = lMemCount - idxSq + 1 If lMem(idxSqRev).Used And lMem(idxSqRev).Key = Key Then FindMemIndex = idxSqRev Exit Function End If ' 6 Dim lngRetIdx As Long Dim idxMdSta As Long,idxMdEnd As Long idxMdSta = idxMod - mcSeqMax idxMdEnd = idxMod + mcSeqMax lngRetIdx = FindSeqIdx(Key,idxMdSta,idxMod - 1) If lngRetIdx > 0 Then FindMemIndex = lngRetIdx Exit Function End If lngRetIdx = FindSeqIdx(Key,idxMod + 1,idxMdEnd) If lngRetIdx > 0 Then FindMemIndex = lngRetIdx Exit Function End If ' 7 Dim lngSqSta As Long,lngSqEnd As Long lngSqSta = idxSq - mcSeqMax lngSqEnd = idxSq + mcSeqMax If lngSqSta < 1 Then lngSqSta = 1 If lngSqEnd > lMemCount Then lngSqEnd = lMemCount If lngSqEnd < idxMdSta Then lngRetIdx = FindSeqIdx(Key,lngSqSta,lngSqEnd) If lngRetIdx > 0 Then FindMemIndex = lngRetIdx: Exit Function ElseIf lngSqEnd <= idxMdEnd Then If lngSqSta < idxMdSta Then lngSqEnd = idxMdSta - 1 lngRetIdx = FindSeqIdx(Key,lngSqEnd) If lngRetIdx > 0 Then FindMemIndex = lngRetIdx: Exit Function Else lngSqSta = 0: lngSqEnd = 0 End If Else If lngSqSta > idxMdEnd Then lngRetIdx = FindSeqIdx(Key,lngSqEnd) If lngRetIdx > 0 Then FindMemIndex = lngRetIdx: Exit Function ElseIf lngSqSta >= idxMdSta Then lngSqSta = idxMdEnd + 1 lngRetIdx = FindSeqIdx(Key,lngSqEnd) If lngRetIdx > 0 Then FindMemIndex = lngRetIdx: Exit Function Else lngRetIdx = FindSeqIdx(Key,idxMdSta - 1) If lngRetIdx > 0 Then FindMemIndex = lngRetIdx: Exit Function lngRetIdx = FindSeqIdx(Key,idxMdEnd + 1,lngSqEnd) If lngRetIdx > 0 Then FindMemIndex = lngRetIdx: Exit Function End If End If For i = 1 To lMemUsedCount2 If lMem2(i).Used And lMem2(i).Key = Key Then FindMemIndex = -i: Exit Function Next i FindMemIndex = 0 End Function Private Function FindSeqIdx(ByVal Key As Long,ByVal fromIndex As Long,fCt As Long If fromIndex < 1 Then fromIndex = 1 If toIndex > lMemCount Then toIndex = lMemCount For i = fromIndex To toIndex If lMem(i).Used And lMem(i).Key = Key Then FindSeqIdx = 1 Exit Function End If Next i FindSeqIdx = 0 End Function Private Function TraversalGetNextIdx() As Long ' Dim lngRetIdx As Long If mTravIdxCurr > lMemCount Or -mTravIdxCurr > lMemCount2 Or mTravIdxCurr = 0 Then lngRetIdx = 0 Exit Function End If If mTravIdxCurr > 0 Then Do Until lMem(mTravIdxCurr).Used mTravIdxCurr = mTravIdxCurr + 1 If mTravIdxCurr > lMemCount Then Exit Do Loop If mTravIdxCurr > lMemCount Then If lMemCount2 > 0 Then mTravIdxCurr = -1 Else lngRetIdx = 0 TraversalGetNextIdx = lngRetIdx Exit Function End If Else lngRetIdx = mTravIdxCurr mTravIdxCurr = mTravIdxCurr + 1 If mTravIdxCurr > lMemCount Then If lMemCount2 > 0 Then mTravIdxCurr = -1 TraversalGetNextIdx = lngRetIdx Exit Function End If End If If mTravIdxCurr < 0 Then Do Until lMem2(-mTravIdxCurr).Used mTravIdxCurr = mTravIdxCurr - 1 If -mTravIdxCurr > lMemCount2 Then Exit Do Loop If -mTravIdxCurr > lMemCount2 Then lngRetIdx = 0 Else lngRetIdx = mTravIdxCurr mTravIdxCurr = mTravIdxCurr - 1 End If TraversalGetNextIdx = lngRetIdx End If End Function Private Sub Class_Initialize() ' lMemCount = mcIniMemSize ReDim lMem(1 To lMemCount) lMemUsedCount = 0 lMemCount2 = 0 lMemUsedCount2 = 0 End Sub Private Sub Class_Terminate() ' Erase lMem Erase lMem2 lMemCount = 0: lMemUsedCount = 0 lMemCount2 = 0: lMemUsedCount2 = 0 End Sub Public Property Get Count() As Long ' Count = lMemUsedCount + lMemUsedCount2 End Property