------------------------------------------------------------ 本文相关代码: -----------------------BitEx.Bas---------------------------- Option Explicit '说明---------------------------------------- '这是一个增强 vb 的位操作功能的模块,主要包含 '有左右移位,取字节,字节连接等通用例程 '兼容性:VB5.0 ,6.0 '-------------------------------------------- '作者:刘琦 ,2005-1-11 '个人主页:http://LQweb.crcoo.com 'e-Mail:liuqi5521@hotmail.com 'api函数 拷贝内存 Private Declare Sub CopyMemory Lib "KERNEL32" Alias "RtlMoveMemory" _ (Destination As Any, Source As Any, ByVal Length As Long) '-----------------------下面这些例程实现整型变量的拆分,合并操作------------- Public Function Con(ByVal HiByte As Byte, ByVal LoByte As Byte) As Integer '把两个字节 (Byte) 连成一个字 (word) 'INPUT-------------------------------------------------------------------- 'HiByte 参与连结的高字节 'LoByte 参与连结的低字节 'OUTPUT------------------------------------------------------------------- '返回值 连结的结果 'Last updated by Liu Qi 2004-3-20. Dim iRet As Integer '用到的函数 varptr() 说明:取一个变量的地址。 CopyMemory ByVal VarPtr(iRet), LoByte, 1 CopyMemory ByVal VarPtr(iRet) + 1, HiByte, 1 Con = iRet End Function Public Function ConWord(ByVal HiWord As Integer, ByVal LoWord As Integer) As Long '把两个字(Word)连成一个双字(DWord) 'INPUT-------------------------------------------------------------------- 'HiWord 参与连结的高位字 'LoWord 参与连结的低位字 'OUTPUT------------------------------------------------------------------- '返回值 连结的结果 'Last updated by Liu Qi 2004-3-20. Dim lRet As Long CopyMemory ByVal VarPtr(lRet), LoWord, 2 CopyMemory ByVal VarPtr(lRet) + 2, HiWord, 2 ConWord = lRet End Function Public Function Hi(ByVal Word As Integer) As Byte '取一个字(Word)的高字节(Byte) 'INPUT------------------------------------------- 'Word 字(Word) 'OUTPUT------------------------------------------ '返回值 Word参数的高字节 'Last updated by Liu Qi 2004-3-20. Dim bytRet As Byte CopyMemory bytRet, ByVal VarPtr(Word) + 1, 1 Hi = bytRet End Function Public Function Lo(ByVal Word As Integer) As Byte '取一个字(Word)的低字节(Byte) 'INPUT------------------------------------------- 'Word 字(Word) 'OUTPUT------------------------------------------ '返回值 Word参数的低字节 'Last updated by Liu Qi 2004-3-20. Dim bytRet As Byte CopyMemory bytRet, ByVal VarPtr(Word), 1 Lo = bytRet End Function Public Function HiWord(ByVal DWord As Long) As Integer '取一个双字(DWord)的高位字 'INPUT------------------------------------------- 'DWord 双字 'OUTPUT------------------------------------------ '返回值 DWord参数的高位字 'Last updated by Liu Qi 2004-3-20. Dim intRet As Integer CopyMemory intRet, ByVal VarPtr(DWord) + 2, 2 HiWord = intRet End Function Public Function LoWord(ByVal DWord As Long) As Integer '取一个双字(DWord)的低位字 'INPUT------------------------------------------- 'DWord 双字 'OUTPUT------------------------------------------ '返回值 DWord参数的低位字 'Last updated by Liu Qi 2004-3-20. Dim intRet As Integer CopyMemory intRet, ByVal VarPtr(DWord), 2 LoWord = intRet End Function '-------------------------下面这些例程实现整形变量的移位------------------- Public Function ShLB(ByVal Byt As Byte, Optional ByVal BitsNum As Long = 1) As Byte '字节的左移函数 'INPUT----------------------------- 'Byt 源操作数 'BitsNum 移位的位数 'OUTPUT---------------------------- '返回值 移位结果 'last updated by Liu Qi 2004-3-23 Dim i& For i = 1 To BitsNum Byt = ShLB_By1Bit(Byt) Next i ShLB = Byt End Function Public Function ShRB(ByVal Byt As Byte, Optional ByVal BitsNum As Long = 1) As Byte '字节的右移函数 'INPUT----------------------------- 'Byt 源操作数 'BitsNum 移位的位数 'OUTPUT---------------------------- '返回值 移位结果 'last updated by Liu Qi 2004-3-23 Dim i& For i = 1 To BitsNum Byt = ShRB_By1Bit(Byt) Next i ShRB = Byt End Function Private Function ShLB_By1Bit(ByVal Byt As Byte) As Byte '把字节左移一位的函数,为 ShlB 服务. 'INPUT----------------------------- 'Byt 源操作数 'OUTPUT---------------------------- '返回值 移位结果 'last updated by Liu Qi 2004-3-23 '(Byt And &H7F): 屏蔽最高位. *2:左移一位 ShLB_By1Bit = (Byt And &H7F) * 2 'ShlB_By1Bit = Byt * 2'溢出测试 End Function Private Function ShRB_By1Bit(ByVal Byt As Byte) As Byte '把字节右移一位的函数,为 ShrB 服务. 'INPUT----------------------------- 'Byt 源操作数 'OUTPUT---------------------------- '返回值 移位结果 'last updated by Liu Qi 2004-3-24 '/2:右移一位 ShRB_By1Bit = Fix(Byt / 2) End Function Public Function ShLW(ByVal Word As Integer, Optional ByVal BitsNum As Long = 1) As Integer '字的左移函数 'INPUT------------------------------- 'Word 源操作数 'BitsNum 移位的位数 'OUTPUT------------------------------ '返回值 移位结果 'last updated by Liu Qi 2004-3-24 Dim i& For i = 1 To BitsNum Word = ShLW_By1Bit(Word) Next i ShLW = Word End Function Public Function ShRW(ByVal Word As Integer, Optional ByVal BitsNum As Long = 1) As Integer '字的右移函数 'INPUT------------------------------- 'Word 源操作数 'BitsNum 移位的位数 'OUTPUT------------------------------ '返回值 移位结果 'last updated by Liu Qi 2004-3-24 Dim i& For i = 1 To BitsNum Word = ShRW_By1Bit(Word) Next i ShRW = Word End Function Private Function ShLW_By1Bit(ByVal Word As Integer) As Integer '把一个字左移一位的函数 'INPUT------------------------------- 'Word 源操作数 'OUTPUT------------------------------ '返回值 移位结果 'last updated by Liu Qi 2004-3-24 Dim HiByte As Byte, LoByte As Byte '把字拆分为字节 HiByte = Hi(Word): LoByte = Lo(Word) '把高字节左移一位,保证把低字节的最高位移入高字节的最低位 HiByte = ShLB_By1Bit(HiByte) Or IIf((LoByte And &H80) = &H80, &H1, &H0) LoByte = ShLB_By1Bit(LoByte) '低字节左移一位 '把移位后的字节再重新组合成字 ShLW_By1Bit = Con(HiByte, LoByte) End Function Private Function ShRW_By1Bit(ByVal Word As Integer) As Integer '把一个字右移一位的函数 'INPUT------------------------------- 'Word 源操作数 'OUTPUT------------------------------ '返回值 移位结果 'last updated by Liu Qi 2004-3-27 Dim HiByte As Byte, LoByte As Byte '把字拆分为字节 HiByte = Hi(Word): LoByte = Lo(Word) '低字节右移一位,保证把高字节的最低位移入低字节的最高位 LoByte = ShRB_By1Bit(LoByte) Or IIf((HiByte And &H1) = &H1, &H80, &H0) '把高字节右移一位, HiByte = ShRB_By1Bit(HiByte) '把移位后的字节再重新组合成字 ShRW_By1Bit = Con(HiByte, LoByte) End Function Public Function ShLD(ByVal DWord As Long, Optional ByVal BitsNum As Long = 1) As Long '把一个双字左移的函数 'INPUT------------------------------- 'DWord 源操作数 'BitsNum 移位的位数 'OUTPUT------------------------------ '返回值 移位结果 'last updated by Liu Qi 2004-3-28 Dim i& For i = 1 To BitsNum DWord = ShLD_By1Bit(DWord) Next i ShLD = DWord End Function Public Function ShRD(ByVal DWord As Long, Optional ByVal BitsNum As Long = 1) As Long '把一个双字右移的函数 'INPUT------------------------------- 'DWord 源操作数 'BitsNum 移位的位数 'OUTPUT------------------------------ '返回值 移位结果 'last updated by Liu Qi 2004-3-28 Dim i& For i = 1 To BitsNum DWord = ShRD_By1Bit(DWord) Next i ShRD = DWord End Function Public Function ShLD_By1Bit(ByVal DWord As Long) As Long '把一个双字左移一位的函数,为 ShlD() 服务 'INPUT------------------------------- 'DWord 源操作数 'OUTPUT------------------------------ '返回值 移位结果 'last updated by Liu Qi 2004-3-29 Dim iHiWord%, iLoWord% '把双字拆分为两个单字 iHiWord = HiWord(DWord): iLoWord = LoWord(DWord) '高位字左移一位,要把低位字的最高位移到高位字的最低位 iHiWord = ShLW_By1Bit(iHiWord) Or IIf((iLoWord And &H8000) = &H8000, &H1, &H0) '低位字左移一位 iLoWord = ShLW_By1Bit(iLoWord) ShLD_By1Bit = ConWord(iHiWord, iLoWord) '重新连接成双字返回结果 End Function Public Function ShRD_By1Bit(ByVal DWord As Long) As Long '把一个双字右移一位的函数,为 ShrD() 服务 'INPUT------------------------------- 'DWord 源操作数 'OUTPUT------------------------------ '返回值 移位结果 'last updated by Liu Qi 2004-3-29 Dim iHiWord%, iLoWord% '把双字拆分为两个单字 iHiWord = HiWord(DWord): iLoWord = LoWord(DWord) '把低位字右移一位,要把高位字的最低位移到低位字的最高位 iLoWord = ShRW_By1Bit(iLoWord) Or IIf((iHiWord And &H1) = &H1, &H8000, &H0) '把高位字右移一位 iHiWord = ShRW_By1Bit(iHiWord) ShRD_By1Bit = ConWord(iHiWord, iLoWord) '重新连接成双字返回结果 End Function Public Function ShLB_C_By1Bit(ByVal Byt As Byte) As Byte '把字节<<循环>>左移一位的函数.C 表示 Cycle,循环 'INPUT----------------------------- 'Byt :源操作数 'OUTPUT---------------------------- '返回值 : 移位结果 'last updated by Liu Qi 2004-8-8 '(Byt And &H7F): 屏蔽最高位. *2:左移一位 ShLB_C_By1Bit = ((Byt And &H7F) * 2) Or IIf((Byt And &H80) = &H80, &H1, &H0) End Function Public Function ShRB_C_By1Bit(ByVal Byt As Byte) As Byte '把字节<<循环>>右移一位的函数。 'INPUT----------------------------- 'Byt :源操作数 'OUTPUT---------------------------- '返回值 : 移位结果 'last updated by Liu Qi 2004-8-8 '(Byt And &H7F): 屏蔽最高位. *2:左移一位 ShRB_C_By1Bit = Fix(Byt / 2) Or IIf((Byt And &H1) = &H1, &H80, &H0) End Function Public Function U2F(ByVal UnsignedLong As Long) As Double '把一个长整形按照无符号数转化成一个浮点数值 If (UnsignedLong And &H80000000) = &H80000000 Then '如果最高位(符号位)为1, '则把它的屏蔽符号位后的值加上最高位无符号表示法的权值(权值校正) U2F = (UnsignedLong And &H7FFFFFFF) + 2 ^ 31 Else '如果最高位为 0,则不需特殊处理 U2F = UnsignedLong End If End Function Public Function F2U(ByVal Float As Double) As Long '把一个浮点数值按照无符号数转化成一个长整形 If Float > 2 ^ 32 - 1 Or Float < 0 Then '无符号数不能容纳的值 Err.Raise 6 '引发溢出错误 ElseIf Float > &H7FFFFFFF Then '最高位为1,则先屏蔽最高位以顺利完成向整形的转化,最后再把最高位的1添上 F2U = CLng(Float - 2 ^ 31) Or &H80000000 Else '如果最高位为 0,则不需特殊处理 F2U = Float End If End Function Public Function UAdd(ByVal UnsignedLong1 As Long, ByVal UnsignedLong2 As Long) As Long '把VB中的长整形按照无符号加法相加 UAdd = F2U(U2F(UnsignedLong1) + U2F(UnsignedLong2)) End Function Public Function UDif(ByVal UnsignedLong1 As Long, ByVal UnsignedLong2 As Long) As Long '把VB中的长整形按照无符号减法相减 UDif = F2U(U2F(UnsignedLong1) - U2F(UnsignedLong2)) End Function ----------------------------------------------------------------- -------------------------------FastBit.Bas----------------------- Option Explicit '----------------------------------------------------- '这个模块使用安全数组技术实现了以下六个函数的Fast版本: 'Hi(),Lo(),HiWord(),LoWord(),Con(),ConWord() '经试验,Fast版本的函数性能提高1倍以上 '----------------------------------------------------- '作者:刘琦 ,2005-1-11 '个人主页:http://LQweb.crcoo.com 'e-Mail:liuqi5521@hotmail.com Private Type SafeArray1d '1维数组的 SafeArray 定义 cDims As Integer '维数 fFeatures As Integer '标志 cbElements As Long '单个元素的字节数 clocks As Long '锁定计数 pvData As Long '指向数组元素的指针 cElements As Long '维定义,该维的元素个数 Lbound As Long '该维的下界 End Type Private Declare Sub CopyMemory Lib "KERNEL32" Alias "RtlMoveMemory" (Destination As Any, Source As Any, ByVal Length As Long) Private Declare Sub ZeroMemory Lib "KERNEL32" Alias "RtlZeroMemory" (dest As Any, ByVal numBytes As Long) Private Declare Function VarPtrArray Lib "msvbvm60.dll" _ Alias "VarPtr" (ptr() As Any) As Long Const FADF_AUTO = &H1 Const FADF_FIXEDSIZE = &H10 Private m_lSharedLong As Long '要被共享的长整形变量 Private m_aiIntsInLong() As Integer '要共享长整形变量的地址空间的整形数组 Private m_SA1D_IntArr As SafeArray1d '整形数组的SafeArray结构 Private m_iSharedInt As Integer '要被共享的整形变量 Private m_aBytesInInt() As Byte '要共享整形变量的地址空间的字节数组 Private m_SA1D_ByteArr As SafeArray1d '字节数组的SafeArray结构 '位操作前初使化动作,主要是初使化,如果不进行初使化,将会出现不可预计错误 Public Sub BitOperatorInit() With m_SA1D_IntArr .cDims = 1 '维数:1维 .fFeatures = 17 '标志:Auto or FixedSize .cbElements = 2 '元素大小:2个字节 .clocks = 0 .pvData = VarPtr(m_lSharedLong) '使数组的数据指针指向长整形变量m_lSharedLong .cElements = 2 '元素个数:2个 .Lbound = 0 '下界:0 End With '使数组变量m_aiIntsInLong指向我们自己创建的 SafeArray1d 结构 CopyMemory ByVal VarPtrArray(m_aiIntsInLong), VarPtr(m_SA1D_IntArr), 4 With m_SA1D_ByteArr .cDims = 1 '维数:1维 .fFeatures = 17 '标志:Auto or FixedSize .cbElements = 1 '元素大小:1个字节 .clocks = 0 .pvData = VarPtr(m_iSharedInt) '使数组的数据指针指向整形变量m_iSharedInt .cElements = 2 '元素个数:2个 .Lbound = 0 '下界:0 End With '使数组变量m_aBytesInInt指向我们自己创建的 SafeArray1d 结构 CopyMemory ByVal VarPtrArray(m_aBytesInInt), VarPtr(m_SA1D_ByteArr), 4 End Sub Public Sub BitOperatorEnd() '释放资源,程序结束前一定要调用 '把数组变量m_aiIntsInLong指向 0,既 C 语言中的 NULL CopyMemory ByVal VarPtrArray(m_aiIntsInLong), 0&, 4 '把数组变量m_aBytesInInt指向 0,既 C 语言中的 NULL CopyMemory ByVal VarPtrArray(m_aBytesInInt), 0&, 4 End Sub '-----------------------下面这些例程实现整型变量的拆分,合并操作,Fast版本------------- Public Function fastCon(ByVal HiByte As Byte, ByVal LoByte As Byte) As Integer '把两个字节 (Byte) 连成一个字 (word) 'INPUT-------------------------------------------------------------------- 'HiByte 参与连结的高字节 'LoByte 参与连结的低字节 'OUTPUT------------------------------------------------------------------- '返回值 连结的结果 'Last updated by Liu Qi 2004-3-20. m_aBytesInInt(1) = HiByte m_aBytesInInt(0) = LoByte fastCon = m_iSharedInt End Function Public Function fastConWord(ByVal HiWord As Integer, ByVal LoWord As Integer) As Long '把两个字(Word)连成一个双字(DWord) 'INPUT-------------------------------------------------------------------- 'HiWord 参与连结的高位字 'LoWord 参与连结的低位字 'OUTPUT------------------------------------------------------------------- '返回值 连结的结果 'Last updated by Liu Qi 2004-3-20. m_aiIntsInLong(1) = HiWord m_aiIntsInLong(0) = LoWord fastConWord = m_lSharedLong End Function Public Function fastHi(ByVal Word As Integer) As Byte '取一个字(Word)的高字节(Byte) 'INPUT------------------------------------------- 'Word 字(Word) 'OUTPUT------------------------------------------ '返回值 Word参数的高字节 'Last updated by Liu Qi 2004-3-20. m_iSharedInt = Word fastHi = m_aBytesInInt(1) End Function Public Function fastLo(ByVal Word As Integer) As Byte '取一个字(Word)的低字节(Byte) 'INPUT------------------------------------------- 'Word 字(Word) 'OUTPUT------------------------------------------ '返回值 Word参数的低字节 'Last updated by Liu Qi 2004-3-20. m_iSharedInt = Word fastLo = m_aBytesInInt(0) End Function Public Function fastHiWord(ByVal DWord As Long) As Integer '取一个双字(DWord)的高位字 'INPUT------------------------------------------- 'DWord 双字 'OUTPUT------------------------------------------ '返回值 DWord参数的高位字 'Last updated by Liu Qi 2004-3-20. m_lSharedLong = DWord fastHiWord = m_aiIntsInLong(1) End Function Public Function fastLoWord(ByVal DWord As Long) As Integer '取一个双字(DWord)的低位字 'INPUT------------------------------------------- 'DWord 双字 'OUTPUT------------------------------------------ '返回值 DWord参数的低位字 'Last updated by Liu Qi 2004-3-20. m_lSharedLong = DWord fastLoWord = m_aiIntsInLong(0) End Function -------------------------------------------------------------- ---------------------------modShiftBitByte.bas---------------] Option Explicit '这是为字节类型变量提供快速的移位操作的模块,可以使用本模块中的快表实现高速的移位运算 '这是纯VB实现的,不需要任何DLL '需要 BitEx.Bas '刘琦,作于2005-1-26 Const MAX_BYTE = &HFF& '下面是移位表 Public g_aShLB() As Byte '字节左移的快表,第1维是待移位的字节,第2维是移位位数 Public g_aShRB() As Byte '字节右移的快表,第1维是待移位的字节,第2维是移位位数 '------------------------------------------------------------------------------------ Public Function IsInitialized() As Boolean '判断是否已经初始化过移位表的函数 On Error GoTo hanlder g_aShLB(1, 1) = g_aShLB(1, 1) IsInitialized = True '没出错,说明初始化过了 Exit Function hanlder: IsInitialized = False '出错说明还没有初始化 End Function Public Sub ShiftBitByteInit() '初始化移位表 If IsInitialized Then Exit Sub ' 如果已经初始化过了,不必再初始化了 '分配空间 ReDim g_aShLB(0 To MAX_BYTE, 1 To 7) As Byte '左移表 ReDim g_aShRB(0 To MAX_BYTE, 1 To 7) As Byte '右移表 Dim i As Long, j As Long For i = 0 To MAX_BYTE For j = 1 To 7 g_aShLB(i, j) = ShLB(i, j) g_aShRB(i, j) = ShRB(i, j) Next j Next i End Sub Public Sub DestoryShiftBitByteTable() '销毁字节类型的移位表,以释放内存 ReDim g_aShLB(0) Erase g_aShLB ReDim g_aShRB(0) Erase g_aShRB End Sub ------------------------------------------------------- ---------------------------SafeArray.bas-------------------------- '*************************************************************** ' (c) Copyright 2000 Matthew J. Curland ' ' This file is from the CD-ROM accompanying the book: ' Advanced Visual Basic 6: Power Techniques for Everyday Programs ' Author: Matthew Curland ' Published by: Addison-Wesley, July 2000 ' ISBN: 0-201-70712-8 ' http://www.PowerVB.com ' ' You are entitled to license free distribution of any application ' that uses this file if you own a copy of the book, or if you ' have obtained the file from a source approved by the author. You ' may redistribute this file only with express written permission ' of the author. ' ' This file depends on: ' References:(不再需要VBoostTypes6.olb,可直接在任何地方使用) ' VBoostTypes6.olb (VBoost Object Types (6.0))' ' Files: ' None ' Minimal VBoost conditionals: ' None ' Conditional Compilation Values: ' None ' ' This file is discussed in Chapter 2. '*************************************************************** '*************************************************************** '说明:这个模块是 Matthew J. Curland 的作品,我根据自己的实际需要 '作了一些微小的改动(不再需要VBoostTypes6.olb,可直接在任何地方使用) ',添加了中文的注释。 ' '使用这个模块,可以像 C 语言一样用数组访问任意的内存位置 '作者:刘琦 ,2005-1-11 '个人主页:http://LQweb.crcoo.com 'e-Mail:liuqi5521@hotmail.com '*************************************************************** Option Explicit Public Type SafeArray1d '1维数组的 SafeArray 定义 cDims As Integer '维数 fFeatures As Integer '标志 cbElements As Long '单个元素的字节数 clocks As Long '锁定计数 pvData As Long '指向数组元素的指针 cElements As Long '维定义,该维的元素个数 Lbound As Long '该维的下界 End Type Private Declare Sub CopyMemory Lib "KERNEL32" Alias "RtlMoveMemory" (Destination As Any, Source As Any, ByVal Length As Long) Private Declare Sub ZeroMemory Lib "KERNEL32" Alias "RtlZeroMemory" (dest As Any, ByVal numBytes As Long) Public Declare Function VarPtrArray Lib "msvbvm60.dll" _ Alias "VarPtr" (ptr() As Any) As Long Public Const FADF_AUTO = &H1 Public Const FADF_FIXEDSIZE = &H10 Public Sub ShareMemoryViaArray(ByVal ArrayPtr As Long, _ ByVal MemPtr As Long, SA1D As SafeArray1d, _ ByVal ElemByteLen As Long, ByVal ElemCount As Long) 'INPUT--------------------------------------------------------------------- 'ByVal ArrayPtr As Long 指向数组变量的指针,用 VarPtrArray(数组名)获取 'ByVal MemPtr As Long 指向要借用的内存块的指针(就是起始地址)。 'SA1D As SafeArray1d 通过引用传递来的SafeArray1d结构变量 'ByVal ElemByteLen As Long 指出数组要使用的元素大小 'ByVal ElemCount As Long 指出数组要使用的元素个数 ' 'OUTPUT-------------------------------------------------------------------- 'N/A '前条件-------------------------------------------------------------------- '要求数组变量必须是未分配的 '后条件-------------------------------------------------------------------- 'N/A With SA1D 'cbElements is optional because this is a 1 element array, 'so cbElements is not needed to walk the array. If Erase 'is called on an array with .cbElements = 0, VB will still 'free all pointer types, but non-pointer types will not get 'zeroed out. Note that the compiler calculates the length 'of a structure at compile time, so LenB(MyStruct(0)) is 'valid regardless of whether or not MyStruct is actually allocated. .cbElements = ElemByteLen '元素大小 .cDims = 1 '维数 'This means that if the 'array goes out of scope, then the pointed 'to memory will be cleaned, but no attempt 'will be made to free the array pointer 'or descriptor. .fFeatures = FADF_AUTO Or FADF_FIXEDSIZE '特征 .pvData = MemPtr '指向要借用的内存块 .cElements = ElemCount '元素个数 .Lbound = 0 ' 下界 End With '把 SafeArray 结构的首地址赋给数组变量 CopyMemory ByVal ArrayPtr, VarPtr(SA1D), 4 End Sub Public Sub UnshareMemory(ByVal ArrayPtr As Long) 'INPUT--------------------------------------------------------------------- 'ByVal ArrayPtr As Long 指向数组变量的指针,用 VarPtrArray(数组名)获取 ' 'OUTPUT-------------------------------------------------------------------- 'N/A '前条件-------------------------------------------------------------------- '要求数组变量必须是用ShareMemoryViaArray分配的,不能用于VB分配的数组 '后条件-------------------------------------------------------------------- 'N/A ''把数组变量的值置为0 ZeroMemory ByVal ArrayPtr, 4 End Sub ------------------------------------------------------------------ ------------------------------ ShiftBitInt16.bas ----------------- Option Explicit '这是为Integer类型变量提供超高速移位运算的模块,由于Integer类型的范围较大,比较占内存,所以 '用的是动态表,用时分配,用完可以尽快销毁。(还有个好处,可以避免忘记初始化数组) '这是纯VB版的,与原来那个需要DLL的版本相比,使用更方便。 '刘琦,作于2005-1-26 '需要:BitEx10.Bas SafeArray.Bas modShiftBitByte.Bas '另外:使用这两个快表一定要注意一点,要做一个长整形无符号扩展之后再查表,不然会出错,像这样: 'g_aShL16(SomeInt and &HFFFF&,1) '为什么?对最高位为1的Integer,VB会把它解释为一个负值,做了长整形扩展,VB才会把它理解为一个正值, '由于数组无法接受负值索引,所以我们是用Integer的无符号值来造表 '所以说,查表的时候当然要用Integer的无符号值来查表 '整形变量的移位表---------------------------------------------------------------------------------------- Public g_aShL16() As Integer Public g_aShR16() As Integer '-------------------------------------------------------------------------------------------------------- Public Const MAX_UINT16 = &HFFFF& 'max unsigned int16,注意:这是一个用Long存储的65535,无符号字的最大值 Private m_iSharedInt As Integer '地址空间要被共享的长整形 Private m_aBytesInInt() As Byte '要共享长整形地址空间的字节数组 Private m_SA1D As SafeArray1d '安全数组结构 Public Sub InitShL16Table() '初始化左移表,(为啥和右移表分开呢?按需分配,省内存,需要哪个分配哪个。) Dim i As Long, j As Long If ShiftLeftTableIsInitialized Then Exit Sub '如果左移表已经初始化过了,就退出 ShiftBitByteInit '初始化字节类型的移位表 modSafeArray.ShareMemoryViaArray VarPtrArray(m_aBytesInInt), VarPtr(m_iSharedInt), m_SA1D, _ 1, 2 '共享内存 If VarPtr(m_iSharedInt) <> VarPtr(m_aBytesInInt(0)) Then MsgBox "共享内存失败!" ReDim g_aShL16(0 To MAX_UINT16, 1 To 15) '为移位表分配空间,0-ffff,1-15 For i = 0 To MAX_UINT16 For j = 1 To 15 g_aShL16(i, j) = ShL16_Internal(LoWord(i), j) Next j Next i UnshareMemory VarPtrArray(m_aBytesInInt) '取消共享的内存 End Sub Public Sub DestroyShL16Table() '销毁左移表,释放内存 ReDim g_aShL16(0) Erase g_aShL16 End Sub Public Sub InitShR16Table() '初始化右移表 Dim i As Long, j As Long If ShiftRightTableIsInitialized Then Exit Sub '如果右移表已经初始化过了,那么退出 ShiftBitByteInit '初始化字节类型的移位表 modSafeArray.ShareMemoryViaArray VarPtrArray(m_aBytesInInt), VarPtr(m_iSharedInt), m_SA1D, _ 1, 2 '共享内存 If VarPtr(m_iSharedInt) <> VarPtr(m_aBytesInInt(0)) Then MsgBox "共享内存失败!" ReDim g_aShR16(0 To MAX_UINT16, 1 To 15) '为移位表分配空间,0-ffff,1-15 For i = 0 To MAX_UINT16 For j = 1 To 15 g_aShR16(i, j) = ShR16_Internal(LoWord(i), j) Next j Next i UnshareMemory VarPtrArray(m_aBytesInInt) '取消共享的内存 End Sub Public Sub DestroyShR16Table() '销毁右移表,释放内存 ReDim g_aShR16(0) Erase g_aShR16 End Sub Public Function ShL16_Internal(ByVal Word As Integer, Optional ByVal BitNum As Long = 1) As Integer '字的左移函数,速度一般,仅供内部使用,用来初始化移位表还可以,用在实际运算中就毫无优势可言了。 'INPUT------------------------------- 'Word 源操作数 'BitsNum 移位的位数 'OUTPUT------------------------------ '返回值 移位结果 m_iSharedInt = Word '把待移位的值赋给被共享的整形 If BitNum = 8 Then '如果等于8,直接把低字节搬到高字节去就OK了 m_aBytesInInt(1) = m_aBytesInInt(0) m_aBytesInInt(0) = 0 ElseIf BitNum > 8 Then '如果大于8,那么就先移8位,再移剩下的 m_aBytesInInt(1) = m_aBytesInInt(0) m_aBytesInInt(0) = 0 m_aBytesInInt(1) = g_aShLB(m_aBytesInInt(1), BitNum - 8) Else '小于8 '把高字节左移,并把低字节相应的位移到高字节上 m_aBytesInInt(1) = g_aShLB(m_aBytesInInt(1), BitNum) Or g_aShRB(m_aBytesInInt(0), 8 - BitNum) '低字节左移 m_aBytesInInt(0) = g_aShLB(m_aBytesInInt(0), BitNum) End If '返回结果 ShL16_Internal = m_iSharedInt End Function Private Function ShR16_Internal(ByVal Word As Integer, Optional ByVal BitNum As Long = 1) As Integer '字的右移函数,仅供内部使用 'INPUT------------------------------- 'Word 源操作数 'BitsNum 移位的位数 'OUTPUT------------------------------ '返回值 移位结果 m_iSharedInt = Word '把待移位的值赋给被共享的整形 If BitNum = 8 Then '如果移位位数等于8,右移8位就等价于直接把高字节搬到低字节,高字节清零 m_aBytesInInt(0) = m_aBytesInInt(1) m_aBytesInInt(1) = 0 ElseIf BitNum > 8 Then '如果移位位数大于8,那么先右移8位,在把低字节右移剩下的位数 m_aBytesInInt(0) = m_aBytesInInt(1) m_aBytesInInt(1) = 0 m_aBytesInInt(0) = g_aShRB(m_aBytesInInt(0), BitNum - 8) Else '小于8 '低字节右移,并把高字节相应的位移动到低字节 m_aBytesInInt(0) = g_aShRB(m_aBytesInInt(0), BitNum) Or g_aShLB(m_aBytesInInt(1), 8 - BitNum) '高字节右移 m_aBytesInInt(1) = g_aShRB(m_aBytesInInt(1), BitNum) End If ShR16_Internal = m_iSharedInt End Function Private Function ShiftLeftTableIsInitialized() As Boolean '判断左移表是否已经初始化过的函数,初始化过返回真,没有初始化返回假 On Error GoTo handler g_aShL16(1, 1) = g_aShL16(1, 1) ShiftLeftTableIsInitialized = True Exit Function handler: ShiftLeftTableIsInitialized = False End Function Private Function ShiftRightTableIsInitialized() As Boolean '判断右移表是否已经初始化过的函数,初始化过返回真,否则返回假 On Error GoTo handler g_aShR16(1, 1) = g_aShR16(1, 1) ShiftRightTableIsInitialized = True Exit Function handler: ShiftRightTableIsInitialized = False End Function -----------------------------------------------------------------