Dan*_*man -3 excel vba excel-vba
如果我遇到错误,我正在尝试编写VBA代码。
我希望代码检查是否其中一个值(“ S925,S936,S926,G”)不在单元格10上。
Sub checklist()
Dim x
Dim LineType
NumRows = Cells(Rows.Count, "j").End(xlUp).Row
For x = 2 To NumRows
If LineType = "G" Then
If Not InStr("S925,S936,S926,G", cellsCells(x, 10).Value) Then
cells Cells(x, 52).Interior.Color = rgbCrimson
cells Cells(x, 52).Value = "G"
End If
End If
End If
Next x
End Sub
Run Code Online (Sandbox Code Playgroud)
这不会导致错误,但是会导致程序出现问题,因此我将对其进行解释。
InStr
不返回布尔值,而是返回第一次出现的搜索字符串的索引。如果未找到该字符串,则返回0。例如InStr("12345", "23")
将返回2。
因为除0外的所有其他元素都强制转换为True
,所以类似的操作If Instr(....) Then
将按预期执行。
但是,如果您使用If Not InStr(....) Then
其他东西,可能/将会发生
If Not InStr("12345", "23") Then
Debug.Print "test evaluated as True!"
End If
Run Code Online (Sandbox Code Playgroud)
test evaluated as True!
即使“ 12345”中包含“ 23”,也会打印此内容。这不是因为InStr
返回False
了。我们可以将InStr
表达式替换为2以更好地理解:
Debug.Print 2 '2 (duh)
Debug.Print CBool(2) 'True (2 converted to Boolean)
Debug.Print Not 2 '-3
Debug.Print CBool(Not 2) 'True (-2 converted to Boolean)
Run Code Online (Sandbox Code Playgroud)
Wy为Not 2
评价为-3?这是因为2
之前未将转换为,Not
而是将Not
逐位应用于2
,这意味着每一位都被翻转了。因此2(0010
)变为1101
-3,因为计算机使用二进制补码表示负数。(实际上,使用了更多的位,Integer
但它的工作原理相同。)由于-3不为0,因此它将转换为True
。由于Not 0
还将被评估为True
(0000
将被转换1111
为-1作为二进制补码),因此表达式Not InStr(...)
将始终被评估为True。
在使用布尔值时,不会注意到这种按位行为,因为它们在内部表示为0000
和1111
。这样也很明显:
Debug.Print 1 = True 'False
Debug.Print CBool(1) = True 'True
Debug.Print -1 = True 'True
Debug.Print CBool(-1) = True'True
Debug.Print CInt(True) '-1 (True converted to Integer)
Run Code Online (Sandbox Code Playgroud)
如您在这里看到的,将True
转换为Integer而不是将Integer转换为布尔值进行=
比较。
长解释,短解决:使用If InStr(...) > 0 Then
代替If InStr(...) Then
和If InStr(...) = 0 Then
代替If Not InStr(...) Then
。
PS:如果将两个InStr
测试结合使用,也会导致混乱的行为,And
因为And
也会按位应用。
归档时间: |
|
查看次数: |
2100 次 |
最近记录: |