2012-06-03 14 views
8

Betrachten Sie die folgenden zwei conditionals denen bitweise Vergleiche in VBScript:Boolean Nicht Operator in VBScript

If  1 And 3 Then WScript.Echo "yes" Else WScript.Echo "no" 
If Not(1 And 3) Then WScript.Echo "yes" Else WScript.Echo "no" 

ich denke, die ausgegeben werden soll:

yes 
no 

Aber die tatsächliche Ausgabe lautet:

yes 
yes 

Warten Sie eine Sekunde, the Not operator is supposed to perform logical negation on an expression. Die logische Negation von true ist false, soweit ich weiß. Muss ich daraus schließen, dass es dieses Versprechen nicht erfüllt? Wie und warum und was geht hier vor? Was ist die Begründung, wenn überhaupt?

+2

Sehen Sie sich den Abschnitt Anmerkungen des von Ihnen erwähnten Links an, lesen Sie dort, wo _ Der Operator Not die Bitwerte einer beliebigen Variablen invertiert und das entsprechende Bit im Ergebnis gemäß der folgenden Tabelle setzt ... Für boolesche Operanden erhalten Sie ein Boolesches Ergebnis, für einen numerischen Ausdruck erhalten Sie ein numerisches Ergebnis. –

+0

@SalmanA, setzen Sie es als Antwort, damit ich es akzeptieren kann. Mein Fehler begann nicht mit "Not", sondern mit "And", was zu einem numerischen Ergebnis führt, während ich dachte, dass es wegen des umgebenden "Not" boolesch wäre. – Lumi

Antwort

11

Die VBScript AND operator führt eine logische UND-Verknüpfung, wenn beide Operanden boolean sind (True, False) - - etwas wie die C (Stil) Sprache && Betreiber.

Wenn beide Operanden numerisch sind, wird es stattdessen eine bitweise UND-Operation durchführen - ein wenig wie der C-Sprache & Operator.

Wenn die Operanden gemischte Typen sind, wird der boolesche Wert in eine Zahl umgewandelt - Falsch = 0, Wahr = -1 (Überraschung!), Gefolgt von einer bitweisen UND-Operation.

So Ihr Beispiel bewertet wie folgt:

' 1 And 3 
' = &h0001 And &h0003 <- bitwise AND 
' = 1 
If 1 Then WScript.Echo "yes" Else WScript.Echo "no" ' Yes 

' Not(1 And 3) 
' = Not(1) <- see above 
' = Not(&h0001) <- bitwise NOT 
' = &hFFFE 
If -2 Then WScript.Echo "yes" Else WScript.Echo "no" ' Yes 

Falls Sie sich fragen, wie die VBScript NOT operator funktioniert, es auf einem boolean-Operanden wie die C-Sprache ! Operator und bitweise Komplement auf einem numerischen Operanden logische Negation führt wie die C-Sprache ~ Betreiber.

Falls Sie logische Operationen an Operanden erzwingen möchten, verwenden Sie die VBScript CBool function die Operanden zu werfen:

If Not(CBool(1) And CBool(3)) Then WScript.Echo "yes" Else WScript.Echo "no" ' no 

Hinweis: Wie bei den meisten VBScript-Betreiber, ein Null Operand den Operator Null zurückzukehren verursacht. Null verhält sich in einer ungewöhnlichen Weise, wenn es in einem If Konstrukt verwendet wird.

6

Ich habe die Antwort auf meine Frage auf Eric Lippert's blog: Not Logical Is VBScript gefunden. Stellt sich heraus, Not Betreiber, wie seine Brüder, ist nicht wirklich ein booleschen Operator.

And, Or, Not and Xor are filed under Logical Operators auf MSDN.

Aber Eric Lippert kennzeichnet sie als bitweise, und das ist eine bessere Beschreibung als nur logische wie auf MSDN, weil logische nicht sagt, wie sie tatsächlich arbeiten, so Leute wie mich in getäuscht werden zu glauben, sie sind boolean Betreiber, die sie nicht sind. Und das ist eine große Falle.

müsste ich meine Aussagen zu umschreiben, wie um sie, was zu tun zu haben, folgt Ich möchte:

If  (1 And 3) > 0 Then WScript.Echo "yes" Else WScript.Echo "no" 
If Not((1 And 3) > 0) Then WScript.Echo "yes" Else WScript.Echo "no" 

Dieser druckt yes und dann no wie es sollte.

Update: Während das oben für diesen Fall scheint, ist es definitiv nicht der Weg zu gehen. Das Problem besteht darin zu verstehen, wonach ich suchen möchte. Der obige Code macht es nicht klar. Ein bitweiser Vergleich und ein numerischer Vergleich für mehr als 0 im Ergebnis sind nicht äquivalent zu einer booleschen Prüfung.

Betrachten Sie den folgenden Code, der für dieses Problem CBool Vorschlag als die endgültige Lösung Salman A des annimmt:

Option Explicit 
Dim a, b 
a = -3 : b = -2 

If a And b  Then WScript.Echo "ja" Else WScript.Echo "nein" ' bad 
If (a And b) > 0 Then WScript.Echo "ja" Else WScript.Echo "nein" ' bad 
If CBool(a And b) Then WScript.Echo "ja" Else WScript.Echo "nein" ' good