在图书馆能找到的关于VBScript的书,大部分都是05年、03年。这本是09年,但是,依然太旧太旧。
日新月异,还是不要学习VBScript,去学习其他语言吧。
以下是我觉得值得一记的地方,与诸兄共勉。
强制转换类型
varTest = CLng(12)
这就是告诉VBScript要确保该变量的子类型是Long
当运行不符合数据类型的情况时:
varTest = CInt("Hello")
会产生一个运行的错误:“Type Mismatch”。
Is函数
IsNumeric()函数可检查用户是否输入了有效的数字
IsDate()同理
一个通用的原则:永远都不要盲目地信任或假设外部数据——比如数据库、文件、网页、尤其是用户输入的数据
在从数据库或某些函数获取数据时,要注意NULL值
strCustomerName = "" & rsCustomers.Fields("Name").Value
这里演示的技巧时VBScript中您学到的最有用的技巧之一。这个技巧可以有效地利用VBScript的隐式类型转换,避免因Null值而产生的问题和错误信息。用“空字符串”("")附加到来自Name数据库项的值。空字符串与Null连接在一起,结果是空字符串;而空字符串跟有效字符串连接在一起,结果还是这个字符串,所以这是一个双赢的解决办法:若这个值是NULL,那就修复了;如果不是NULL,则保持原样。
为什么要用Set <variable> = Nothing销毁一个对象
在您真正用到对象时您就会知道其中的好处,因为销毁对象实际上就是释放对象所占用的内存。对象占用的内存要比普通变量大得多。所以保留不必要的对象可能导致致命的内存错误,其中的原因过于复杂,在此不做深究。应该养成所有的对象在用完后立即将其设为Nothing的好习惯。
ReDim Preserve可更改数组的维度与大小
ReDim Preserve astrPhoneList(2,1)
astrPhoneList(0, 1) = "Carter"
astrPhoneList(1, 1) = "Ron"
astrPhoneList(2, 1) = "305-555-2514"
ReDim Preserve astrPhoneList(2,2)
astrPhoneList(0, 2) = "Davis"
astrPhoneList(1, 2) = "Miles"
astrPhoneList(2, 2) = "212-555-5314"
astrPhoneList(0, 1) = "Carter"
astrPhoneList(1, 1) = "Ron"
astrPhoneList(2, 1) = "305-555-2514"
ReDim Preserve astrPhoneList(2,2)
astrPhoneList(0, 2) = "Davis"
astrPhoneList(1, 2) = "Miles"
astrPhoneList(2, 2) = "212-555-5314"
使用Preserve关键字,只能改变数组最后一个维度的大小。如果试图改变其他维度的大小,而不是最后一个维度,VBScript会生成一个运行时错误。这就是为什么在使用二维数组时,最好将第一维视为列,第二维视为行。在设计时,您通常会知道数组中会有多少列,因此大多数情况下都不会去改变列数。
UBound可返回数组行数或列数
UBound(astray, 2)返回行数,意思是第二个维度
UBound(astray, 1)返回列数,即第一个维度。
关于调用函数的规则
msg=MsgBox("请确认您输入的数据是否正确!",&H123,"数据检查")
或
MsgBox "请确认您输入的数据是否正确!",&H123,"数据检查"
或
Call MsgBox("请确认您输入的数据是否正确!",&H123,"数据检查")
关于Exit Sub和Exit Function
这里没有使用Exit Sub,而是用了Else语句。这里的设计原则就是过程只能有一个退出点,这就是过程结尾的隐藏退出点。从定义就能看出,有Exit语句的过程或函数必然有多个退出点,很多程序员都认为这是糟糕的设计。这个原则的出发点就在于多个退出点更易于产生错误而且难于理解。
不要太担心您的代码是否符合某些理想的设计——尤其是在这样小规模的简单脚本中。更重要的考虑是Exit Sub和Exit Function的使用会破坏脚本的逻辑流程。因为它们是用于终止逻辑流程,并且会在代码中产生跳跃,过度地使用会导致逻辑混乱,容易产生错误。这就是为什么有些人反对使用这些语句的原因。
关于传址与传值
Sub ByRefByValExample(ByRef lngFirst, ByVal lngSecond)
lngFirst = lngFirst + 1
lngSecond = lngSecond + 1
End Sub
执行这过程后,lngA的值会发生改变,lngB不会。
我想,这就是传址与传值。过程 不会有返回值,如果想要改变什么,便只好改变地址了。
文字常量和具名常量
"Hello",#08/31/69#,true,这些是文字常量
具名常量类似于变量,它也是内存中存放数据的地址的名称。不同之处在于,顾名思义,它是一个常量,在运行时不能修改。
用Const语句定义常量。
Const GREETING ="Hello there, "
Const语句定义了名为GREETING的具名常量。常量的名称全部大写,这是一种广泛接受的具名常量命名方式。将常量名称定义为全大写就更容易将其与变量区分开,变量通常都是小写的或大小写混合的。另外,因为常量通常全都是大写字母,常量名称中的不同单词是以下划线(_)分割的,例如Const RESPONSE_YES = "YES" Const RESPONSE_NO = "NO"
具名常量的使用原则:
1:如果某个文字常量只需使用一次,就无需为其创建具名变量。
2:如果使用具名常量代替文字常量可以使代码更清晰,那就使用具名变量。
在使用数字和日期文字常量时尤其要遵守具名常量原则2。
在使用数组时,用具名常量代替数组下标也是个不错的做法。
Select Case …End Select
For lngIndex = -10 To -20 Step -2
Exit For '终止循环
Next
查找字符串中包含字符串
strFullPath = "C:\MyStuff\Documents\Personal\resume.doc"
strFileName = Right(strFullPath,Len(strFullPath) - InStrRev(strFullPath,"\"))
MsgBox "The filename is: " & strFileName
strFileName = Right(strFullPath,Len(strFullPath) - InStrRev(strFullPath,"\"))
MsgBox "The filename is: " & strFileName
For Each…Next最常见于遍历集合,但它还可以用于遍历数组中的元素。
无论数组中有多少元素,也无论它有多少个维度,For Each…Next循环都能遍历其中的每个元素。这个例子就是用For Each…Next循环遍历一个一维数组:
astrColors=array("Red", "Green", "Blue", "Yellow")
For Each strElement In astrColors
MsgBox strElement
Next
For Each strElement In astrColors
MsgBox strElement
Next
Exit Do与Exit For
在执行Exit Do语句时,代码会跳出循环,跳到循环代码块的下一行。
On Error Resume Next
如果要将错误控制开关调到OFF状态,可以在脚本开头使用On Error Resume Next语句
On Error GoTo 0再将错误报告开启
With...End With
With关键字是一个可以减少打字次数的快捷方式。当您在一块代码中多次使用同一个对象时,可以将这段代码放到With...End With结构中。
Scripting.Dictionary
这很像数组呐,一个字符串,对应一个什么东西
Add方法
strItemAdd(LAST, 0) = "Shorter"
strItemAdd(FIRST, 0) = "Wayne"
strItemAdd(PHONE, 0) = "853-238-0060"
strKey = strItemAdd(PHONE, 0)
dicPhoneList.Add strKey, strItemAdd
CompareMode 属性
1(vbTextCompare)是进行文本比较,0(vbDatabaseCompare)是进行二进制比较。
比方说区分大小写,使用vbTextCompare时,已有abc时添加ABC即会生成错误。
Item属性
dicAnimals.Item("1234") = "Cat"
strAnimalName = dicAnimals.Item("1234")
Exists方法
Exists()方法可以用于检查字典中是否已经存在某个关键字。实例:
If dicAnimals.Exists("1234") Then
strAnimalName = dicAnimals.Item("1234")
End If
Remove方法
与Add对应
RemoveAll方法
清空数据
Class
Property Let
Property Get
Property Set
正则表达式
Set re = New RegExp
Global属性负责指明模式是匹配整个字符串中所有与之相符的地方还是只匹配第一次出现的地方。如果Global属性的值是True,那就会对整个字符串进行查找;否则就不会。默认值是False。
re.Global = True
如果IgnoreCase属性的值为False,搜索为大小写敏感;如果是True,则不是。默认是False
re.IgnoreCase = True
Pattern属性设置或返回用于搜索的正则表达式
re.Pattern = "\bin"
Execute方法将正则表达式应用到字符串上并返回Matches集合。
也就是说,Execute会返回匹配到的字符串,的集合。
要记得将Global属性设为True,否则您的Matches集合中最多也只会有一个成员。这种方法很简单,但是很难调试!
Set colMatches = re.Execute(s)
For Each match In colMatches
MsgBox "Found valid URL: " & match.Value
Next
Replace方法用于替换在正则表达式搜索中找到的文本,object.Replace(string1, string2)
Replace方法返回一份RegExp.Pattern被string2替换后的string1的副本。
Backreferencing
存放匹配结果的缓存从1开始编号,最大可以到99,可以一次用$1、$2之类的变量访问它们。
本实例,前5个单词(由一个或多个非空白字符组成)会被记住,然后只有其中的4个会出现在替换文本中:
Dim re, s
Set re = New RegExp
re.Pattern = "(\S+)\s+(\S+)\s+(\S+)\s+(\S+)\s+(\S+)"
s = "VBScript is not very cool."
MsgBox re.Replace(s, "$1 $2 $4 $5")
Set re = New RegExp
re.Pattern = "(\S+)\s+(\S+)\s+(\S+)\s+(\S+)\s+(\S+)"
s = "VBScript is not very cool."
MsgBox re.Replace(s, "$1 $2 $4 $5")
本代码会输出“VBScript is very cool.”。
注:在正则表达式字符中用括号,然后即可用$匹配相应的位置
Test方法对字符串执行正则表达式搜索,并返回一个布尔值说明匹配是否成功
object.Test(string)
如果匹配成功,Test方法返回True;否则返回False。这适用于判断字符串是否含有某个模式。注意,常常需要先将模式设为大小写敏感。
用这个方法可以验证输入
Matches的属性
1.Count返回集合中的元素数量。
Set colMatches = re.Execute(s)
MsgBox colMatches.count
2.Item根据指定的键返回元素。
Msgbox colMatches.item(0)
Msgbox colMatches.item(1)
Msgbox colMatches.item(2)
Match对象是Matches集合中的成员
1.FirstIndex属性从0开始对被搜索的字符串编号。换句话说就是字符串中的第一个字符就是字符0。
For Each objMatch in colMatches
sMsg = sMsg & ", found at position " & objMatch.FirstIndex & "of the string."
Next
2.Length属性返回在字符串中找到的匹配的长度
sMsg = sMsg& "The length matched is " & objMatch.Length & "." & vbCrLf
3.Value属性返回在字符串中找到的匹配结果的值或文本。
sMsg = sMg &"Match of " & objMatch.Value
正则表达式字符
请查看 VBScript正则表达式字符 笔记
+ 匹配前面的字符一次或多次
* 匹配前面的字符零次或多次
? 匹配前面的字符零次或一次
cscript
之所以有两个宿主程序,是因为cscript.exe被设计为从控制台窗口启动(一般来说是Windows中的MS-DOS窗口),而wscript.exe则用于直接与Windows GUI进行交互。这两者就功能来讲几乎没有区别。
cscript c:\folderName\YourScriptName.vbs