VB.NET Declare语句
本文是看了网上很多零碎的知识点总结而成,要感谢广大网友的智慧 Declare语句 用于在模块级别中声明对动态链接库 (DLL) 中外部过程的引用。 语法 1 [Public|Private]DeclareSubnameLib"libname"[Alias"aliasname"] [([arglist])] 语法 2 [Public|Private]DeclareFunctionnameLib"libname"[Alias"aliasname"] [([arglist])] [Astype] Declare语句的语法包含下面部分:
arglist参数的语法以及语法各个部分如下: [Optional] [ByVal|ByRef] [ParamArray]varname[( )] [Astype]
说明 对Function过程而言,过程的数据类型决定其返回值的数据类型。可以在arglist之后使用As子句来指定函数返回值的数据类型。在arglist中,可以使用As子句来指定任何传给该过程的参数的数据类型。不单可以指定为任何标准数据类型,还可以在arglist中指定As Any来禁止类型检查,从而允许将任意数据类型传递给该过程。 空圆括号表示该Sub或Function过程没有参数,且 Visual Basic 应确保不会传递任何参数。在下面的示例中, Declare Sub First Lib "MyLib" () 如果带参数表,则每次调用该过程时都要检查参数的个数和类型。在下面的示例中, Declare Sub First Lib "MyLib" (X As Long) 注意在Declare语句的参数表中不能有定长的字符串;只有变长的字符串才能传给过程。定长的字符串可以作为过程参数使用,但在传递前都要被转换为变长的字符串。 注意当所调用的外部过程需要一个值为 0 的字符串时,就要使用vbNullString常数。该常数与零长度字符串 ("") 是不相同的。 关于VB.NET使用Alias子句: Declare语句中的Alias子句是一个可选的部分,用户可以通过它所标识的别名对动态 库中的函数进行引用。例如,在下面的语句中,声明了一个在VB中名为MyFunction的函数,而它在动态库Mydll.dll中最初的名字是MyFunctionX。
需要注意的是,Alias子句中的函数名是大小写敏感的,也就是说,必须与函数在生成时的声明(如在C源文件中的声明)一致。这是因为32位动态库与16位动态库不同,其中的函数名是区分大小写的。同样道理,如果没有VB.NET使用Alias子句,那么在 Function(或Sub)后的函数名也是区分大小写的。
通常在以下几种情况时需要VB.NET使用Alias子句: 1.处理使用字符串的系统Windows API过程 如果调用的系统Windows API过程要使用字符串,那么声明语句中必须增加一个Alias 子句,以指定正确的字符集。包含字符串的系统Windows API函数实际有两种格式:ANSI和Unicode(关于ANSI和Unicode两种字符集的区别将在后面详细阐述)。因此,在Windows头文件中,每个包含字符串的函数都同时有ANSI版本和Unicode版本。例如,下面是SetWindowText函数的两种C语言描述。可以看到,第一个描述将函数定义为SetWindowTextA,尾部的"A" 表明它是一个ANSI函数:
第二个描述将它定义为 SetWindowTextW, 尾部的"W" 表明它是一个 Unicode 函数: 因为两个函数实际的名称都不是"SetWindowText",要引用正确的函数就必 须增加一个Alias子句: 应当注意,对于VB中使用的系统WindowsAPI函数,应该指定函数的ANSI版本,因为只 有WindowsNT才支持Unicode版本,而Windows95不支持这个版本。仅当应用程序只运行 在WindowsNT平台上的时候才可以使用Unicode版本。 2.函数名是不标准的名称 有时,个别的DLL过程的名称不是有效的标识符。例如,它可能包含了非法的字符(如连字符),或者名称是VB的关键字(如GetObject)。在这种情况下,可以使用Alias关键字。例如,操作环境DLLs中的某些过程名以下划线开始。尽管在VB标识符中允许使用标识符,但是下划线不能作为标识符的第一个字符。为了使用这种过程,必须先声明一个名称合法的过程,然后VB.NET使用Alias子句引用过程的真实名称: 在上例中,lopen是VB中使用的过程名称。而_lopen则是动态连接库中可以识别的名 称。 3.使用序号标识DLL过程 除了使用名称之外,还可以使用序号来标识DLL过程。某些动态连接库中不包含过程的名称,在声明它们包含的过程时必须使用序号。同使用名称标识的DLL过程相比,如果使用序号,在最终的应用程序中消耗的内存将比较少,而且速度会快些。但是,一个具体的API的序号在不同的操作系统中可能是不同的。例如GetWindowsDirectory在Win95下的序号为432,而在WindowsNT4.0下为338。总而言之,如果希望应用程序能够在不同的操作系统下运行,那么最好不要使用序号来标识API过程。如果过程不属于API,或者应用程序使用的范围很有限,那么使用序号还是有好处的。 要使用序号来声明DLL过程,Alias子句中的字符串需要包含过程的序号,并在序号的 前面加一个数字标记字符(#)。例如,Windowskernel中的GetWindowsDirectory函数的序 号为432;可以用下面的语句来声明该DLL过程: 在这里,可以使用任意的合法名称作为过程的名称,VB将用序号在DLL中寻找过程。 为了得到要声明的过程的序号,可以使用Dumpbin.exe等实用工具(Dumpbin.exe是Microsoft VisualC++提供的一个实用工具,它的使用说明可以参见VC的文档)。利用Dumpbin,可以提取出.dll文件中的各种信息,例如DLL中的函数列表,它们的序号以及与代码有关的其它信息。 要声明一个DLL过程,首先需要在代码窗口的"通用(General)"部分增加一个VB.NET Declare语句。如果该过程返回一个值,应将其声明为Function: DeclareFunctionpublicnameLib"libname"[Alias"alias"] [([[ByVal]variable[Astype] [,[ByVal]variable[Astype]]...])]AsType 如果过程没有返回值,可将其声明为Sub: DeclareSubpublicnameLib"libname" [Alias"alias"] [([[ByVal]variable[Astype] [,[ByVal]variable[Astype]]...])] 缺省情况下,在标准模块中声明的DLL过程,可以在应用程序的任何地方调用它。在其它类型的模块中定义的DLL过程则是模块私有的,必须在它们前面声明Private关键字,以示区分。下面分别介绍声明语句的各个组成部分。 VB.NET Declare语句中的Lib子句用来告诉Visual Basic如何找到包含过程的.dll文件。 如果引用的过程属于Windows核心库(User32、Kernel32或GDI32),则可以不包含文件扩展名,如: DeclareFunctionGetTickCountLib"kernel32"Alias"GetTickCount"()AsLong 对于其它动态连接库,可以在Lib子句指定文件的路径: DeclareFunctionlzCopyLib"c:windowslzexpand.dll"_ (ByValSAsInteger,ByValDAsInteger)AsLong 如果未指定libname的路径,Visual Basic将按照下列顺序查找该文件: 下表中列出了常用的操作系统环境库文件。 动态链接库描述 以上介绍VB.NET Declare语句对于Windows的系统API函数,可以利用VB提供的工具API Viewer查找某一函数及其相 关数据结构和常数的声明,并复制到自己的程序中。 (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |