WEB开发网
开发学院软件开发VB VB“变态”用法之高效字串指针类 阅读

VB“变态”用法之高效字串指针类

 2006-02-27 21:09:55 来源:WEB开发网   
核心提示:使用VB里的字串类型String有两大不足:第一、它的分配是由VB运行时控制,我们不能将其分配在指定内存处;第二,VB“变态”用法之高效字串指针类,任何一次对字串的赋值操作都要进行内存重新分配,要实现高效、灵活的字串处理,对于普通的数值类型变量的指针没有什么Hack的必要,但是它关系到一个有用的技术,我们必须克服这两大
使用VB里的字串类型String有两大不足:第一、它的分配是由VB运行时控制,我们不能将其分配在指定内存处;第二,任何一次对字串的赋值操作都要进行内存重新分配。要实现高效、灵活的字串处理,我们必须克服这两大不足。

对于第一个问题,通过修改String变量里放着的BSTR描述符指针可以实现;对于第二个问题,可以用Mid语句(注意是语句而不是函数)来赋值。不详细讲了,直接看下面的这个类:
  

OptionExplicit

'********************************************************

'clsBSTR.cls

'作者:熊超ID:AdamBear2002年3月18日

'http://www.csdn.net/Author/AdamBear

'你可以自由使用本类模块,不过请保留本声明

'********************************************************

PRivateDeclareSubCopyMemoryLib"kernel32"Alias"RtlMoveMemory"(DestinationAsAny,SourceAsAny,ByValLengthAsLong)

'不要直接对sString赋值(可以用MID语句),将其设为公有仅为提高效率。

PubliCSStringAsString'BSTR描述符指针

PrivatepStrAsLong'BSTR地址

PrivatenMaxLenAsLong'BSTR最大字节数


  '让本字串指向特定地址

PublicSubAttach(AddrAsLong,OptionalnLenAsLong)

pStr=Addr

'修改BSTR描述符指针,使其指向Addr

CopyMemoryByValVarPtr(sString),Addr,4

IfIsMissing(nLen)ThenExitSub

'设定最大字串字节数

nMaxLen=nLen

EndSub

'还原本字串原BSTR描述符

PublicSubDetach()

 CopyMemoryByValVarPtr(sString),0&,4

EndSub

'让本字串指向源字串

PublicSubAttachStr(sStrAsString)

 AttachStrPtr(sStr),LenB(sStr)

EndSub

'data为缺省属性

PublicPropertyLetdata(sValAsString)

 DimcAsLong

 c=LenB(sVal)

 '超过最大字串数,抛出错误。

 Ifc>nMaxLenThenErr.RaisevbObjectError 3000,"CString::LetData","溢出"

 '写字串长度

 CopyMemoryByVal(pStr-4),c,4

 '写字串

 Mid(sString,1)=sVal

EndProperty

'可以通过公有变量sString来读字串,效率更高

PublicPropertyGetdata()AsString

 data=sString

EndProperty

PrivateSubClass_Terminate()

 CallDetach

EndSub


  用法如下,假设我们已通过VitualAlloc,HeapAlloc,MapViewOfFile这样的内存管理API得到了一个4k个字节的可读写的内存地址baseAddr:

DimsShareAsNewclsBSTR

'留下前4个字节用于BSTR保存字串字节数

sShare.Attach(baseAddr 4,4096-4)

'下面的字串"Test"会直接写到baseAddr 4字节处

sShare="Test"

DimyAsString

'读字串时可以用sString属性或缺省属性

y=sShare.sString

'用AttachStr方法Attach到一个字串。

'必须要先Detach

sShare.Detach

sShare.AttachStr(y)

sShare="Hahaha"

Debug.Printy

'一旦AttachStr到字串y后,对sShare的修改就相当于对y的修改。

'并且以后对y的修改也只能用Mid语句

Mid(y,1)="xxxxx"

'不能直接赋值,这样VB会将原来y所指(也是sShare所指)内存释放,

'重新分配y。这样在访问sShare时会出错。

'y="Test"

使用这个类有几个需要注意的地方。

1、读字串时可以用sString属性来读,更快。

读sShare有两种方法,一种是用缺省属性Data来读,一种是直接用sString属性来读。用sString属性不重新分配内存,要快得多。

2、不要直接给sString赋值,应使用缺省的data属性来赋值。

之所以把sString属性暴露出来,是为了效率和方便。我们可以用Mid语句对其进行修改,但不要直接用"="来赋值。

3、注意Attach的第二个参数,表示字串的最大字节数,不要让它超过已经分配的内存。

4、用AttachStr将本字串对象Attach到某个字串(比如上面的y)上后,不能再对这个字串y重新赋值,也不能将其传递到会对其重新赋值的过程。

这么多需要注意的问题,用起来岂不是更不方便。的确,用它的之前要考虑是不是必须的。因为建立这个类也一样有开销。所以还有一个需要注意的问题:

5、它主要的应用还是在于将字串安放在指定内存处。虽然它也可以让同一个进程内几个的字串达到共享的目的,但是如果只是两三个很小的字串这样时做反而慢了。

后计:

数组指针和字串指针我们已经谈过了,对于普通的数值类型变量的指针没有什么Hack的必要,但是它关系到一个有用的技术,下篇文章再谈。

->

Tags:VB 变态 用法

编辑录入:爽爽 [复制链接] [打 印]
赞助商链接