Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • World
  • Users
  • Groups
Skins
  • Light
  • Cerulean
  • Cosmo
  • Flatly
  • Journal
  • Litera
  • Lumen
  • Lux
  • Materia
  • Minty
  • Morph
  • Pulse
  • Sandstone
  • Simplex
  • Sketchy
  • Spacelab
  • United
  • Yeti
  • Zephyr
  • Dark
  • Cyborg
  • Darkly
  • Quartz
  • Slate
  • Solar
  • Superhero
  • Vapor

  • Default (No Skin)
  • No Skin
Collapse
Code Project
  1. Home
  2. General Programming
  3. Visual Basic
  4. Bitwise AND in an If/Else block

Bitwise AND in an If/Else block

Scheduled Pinned Locked Moved Visual Basic
questioncsharptutorial
16 Posts 5 Posters 0 Views 1 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • T treddie

    If (ValueA And MaskA) = 0 Then ' or If Not (ValueA And MaskA) Then After testing, the first example works, the second does not. For the first one, I see now the importance of hierarchy and the parens. For the second, I don't think it works because it is performing a binary NOT on the result, thus turning it into a negative number (or just a huge unsigned integer). At any rate, since it is now a non-zero number, the final condition is "True", and the intended action fails.

    D Offline
    D Offline
    Dave Kreskowiak
    wrote on last edited by
    #7

    treddie wrote:

    After testing, the first example works, the second does not

    Oh, it works, just not the way to think it does. The result of (ValueA And MaskA) results in an integer value, not True/False. That integer is compared to zero. If the result of the expression is non-zero, True is returned. The Not operator will invert that to False. If the result of the expression is zero, False is returned, then inverted to True by the Not operator. Withouting seeing the values of ValueA and Mask, it's pretty much all we can tell you.

    A guide to posting questions on CodeProject[^]
    Dave Kreskowiak

    T 1 Reply Last reply
    0
    • T treddie

      If (ValueA And MaskA) = 0 Then ' or If Not (ValueA And MaskA) Then After testing, the first example works, the second does not. For the first one, I see now the importance of hierarchy and the parens. For the second, I don't think it works because it is performing a binary NOT on the result, thus turning it into a negative number (or just a huge unsigned integer). At any rate, since it is now a non-zero number, the final condition is "True", and the intended action fails.

      L Offline
      L Offline
      Lost User
      wrote on last edited by
      #8

      treddie wrote:

      After testing, the first example works, the second does not.

      You need to show us the values of ValueA and MaskA, so we can try to figure out why.

      Use the best guess

      1 Reply Last reply
      0
      • T treddie

        I have to admit, this is probably about as basic as it gets, but I must confess ignorance on this, and I cannot seem to find an answer anywhere. It goes like this: I have an If/EndIf block: If ValueA And MaskA Then ' Do stuff. End if Now, I look at that and my first reaction is to knee-jerk and expect that the above If-line is written incorrectly since a bitwise operation has been evaluated but no condition on it has been defined. In other words, I would expect it to be written more like: If ValueA And MaskA = 1 Then ' Do stuff. End if I ran the first example and, indeed, it seemed to work OK. So then it seemed that vb.Net can treat such an expression in a special way, assuming that such a line before being evaluated is "0" (False) and then POSSIBLY, not zero AFTER evaluation, making the result "True". Then, based on that assumption, I needed a reverse logic, so that if the condition was False, it would execute rather than when it is True: If Not (ValueA And MaskA) Then ' Do stuff. End if However, that does not work since all that does is essentially take the binary digits and flip them, turning the result into a negative value (a signed integer). So now it seems that the only solution is to set the block up as an If/Else block: If ValueA And MaskA Then ' Do stuff. Else ' Do alternate stuff. End if That should ALWAYS work, I would tend to think. But if my above logic has been perfectly consistent, then the 2nd example in this post, should also work, but with a test for the value "0": If ValueA And MaskA = 0 Then ' Do stuff. End if Alas, it failed, since vb.Net seems fixated on interpreting the result as having to be a Boolean, so my above logic is flawed somewhere. Even though evaluating the result in the Immediate window returns "0", the code does not execute. What IS the vb.Net convention for using bitwise operators in an If-conditional statement? Hopefully the answer to this question can solve the riddle of Global Warming and lead to cures for all diseases! :))

        T Offline
        T Offline
        TnTinMn
        wrote on last edited by
        #9

        Elimate the confusion and set "Option Strict On"; it is off in the default configuration. This will disallow the implied conversion from integer to boolean. see: Visual Studio compiler options, Part 2: Option Strict Also, review Operator Precedence in Visual Basic

        T 1 Reply Last reply
        0
        • D Dave Kreskowiak

          treddie wrote:

          After testing, the first example works, the second does not

          Oh, it works, just not the way to think it does. The result of (ValueA And MaskA) results in an integer value, not True/False. That integer is compared to zero. If the result of the expression is non-zero, True is returned. The Not operator will invert that to False. If the result of the expression is zero, False is returned, then inverted to True by the Not operator. Withouting seeing the values of ValueA and Mask, it's pretty much all we can tell you.

          A guide to posting questions on CodeProject[^]
          Dave Kreskowiak

          T Offline
          T Offline
          treddie
          wrote on last edited by
          #10

          The Not operator will invert that to False. But that is not what happens. Here are some actual tests I performed:

          The value and the mask in these examples are:
          FileAttributes Value that contains a bit field that indicates whether a resource is a folder or a file.
          Folder = 8208D, File = 8224D

          Mask		Bit mask that tests for the presence of a folder (16D).
          

          Option Strict is NOT set.
          _____________________________________________________________________________________________________

          GOAL: Run code on "True" condition (Resource is a folder):
          If (FileAttributes And FILE_ATTRIBUTE_DIRECTORY) Then
          'Execute code.
          End If

          When FileAttributes = 8208D (Folder):
          	8208D (Folder)    =    		2	0	1	0	H
          					0010	0000	0001	0000	B
          	16D (Mask)        =	AND	0000	0000	0001	0000	B
                                                      \_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_
          	Result			        0000	0000	0001	0000	B    <>	0, ("True"), Code executes as it should.
          
          
          When FileAttributes = 8224D (File):
          	8224D (File)    =    		2	0	2	0	H
          					0010	0000	0010	0000	B
          	16D (Mask)      =	AND	0000	0000	0001	0000	B
                                                      \_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_
          	Result			        0000	0000	0000	0000	B     =	0, ("False"), Code does not execute.
          											      This is correct.
          

          _____________________________________________________________________________________________________
          GOAL: Run code on "False" condition (Resource is a file):
          If Not (FileAttributes And FILE_ATTRIBUTE_DIRECTORY) Then
          'Execute code.
          End If

          When FileAttributes = 8208D (Folder):
          	8208D (Folder)    =    		2	0	1	0	H
          					0010	0000	0001	0000	B
          	16D (Mask)        =	AND	0000	0000	0001	0000	B
                                                      \_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_
          	Result			        0000	0000	0001	0000	B    <> 0, ("True"), Code WOULD  execute, if left as is.
                                                      \_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_
          				NOT	1111	1111	1110	1111	B    <>	0, ("True"), Code executes when it SHOULD NOT.
          
          
          When FileAttributes = 8224D (File):
          	8224D (File)    =    		2	0	2	0	H
          					0010	0000	0010	0000	B
          	16D (Mask)      =	AND	0000	0000	0001	0000	B
                                                      \_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_
          	Result			        0000	0000	0000	0000	B    =  0, ("False"), Code does not execute, if left as is.
                                                      \_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_
          
          D L 2 Replies Last reply
          0
          • T treddie

            The Not operator will invert that to False. But that is not what happens. Here are some actual tests I performed:

            The value and the mask in these examples are:
            FileAttributes Value that contains a bit field that indicates whether a resource is a folder or a file.
            Folder = 8208D, File = 8224D

            Mask		Bit mask that tests for the presence of a folder (16D).
            

            Option Strict is NOT set.
            _____________________________________________________________________________________________________

            GOAL: Run code on "True" condition (Resource is a folder):
            If (FileAttributes And FILE_ATTRIBUTE_DIRECTORY) Then
            'Execute code.
            End If

            When FileAttributes = 8208D (Folder):
            	8208D (Folder)    =    		2	0	1	0	H
            					0010	0000	0001	0000	B
            	16D (Mask)        =	AND	0000	0000	0001	0000	B
                                                        \_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_
            	Result			        0000	0000	0001	0000	B    <>	0, ("True"), Code executes as it should.
            
            
            When FileAttributes = 8224D (File):
            	8224D (File)    =    		2	0	2	0	H
            					0010	0000	0010	0000	B
            	16D (Mask)      =	AND	0000	0000	0001	0000	B
                                                        \_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_
            	Result			        0000	0000	0000	0000	B     =	0, ("False"), Code does not execute.
            											      This is correct.
            

            _____________________________________________________________________________________________________
            GOAL: Run code on "False" condition (Resource is a file):
            If Not (FileAttributes And FILE_ATTRIBUTE_DIRECTORY) Then
            'Execute code.
            End If

            When FileAttributes = 8208D (Folder):
            	8208D (Folder)    =    		2	0	1	0	H
            					0010	0000	0001	0000	B
            	16D (Mask)        =	AND	0000	0000	0001	0000	B
                                                        \_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_
            	Result			        0000	0000	0001	0000	B    <> 0, ("True"), Code WOULD  execute, if left as is.
                                                        \_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_
            				NOT	1111	1111	1110	1111	B    <>	0, ("True"), Code executes when it SHOULD NOT.
            
            
            When FileAttributes = 8224D (File):
            	8224D (File)    =    		2	0	2	0	H
            					0010	0000	0010	0000	B
            	16D (Mask)      =	AND	0000	0000	0001	0000	B
                                                        \_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_
            	Result			        0000	0000	0000	0000	B    =  0, ("False"), Code does not execute, if left as is.
                                                        \_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_
            
            D Offline
            D Offline
            Dave Kreskowiak
            wrote on last edited by
            #11

            OK. You should be testing the value of the bitwise operation against the value of the mask, NOT depending on an implied true or false.

            A guide to posting questions on CodeProject[^]
            Dave Kreskowiak

            1 Reply Last reply
            0
            • T treddie

              The Not operator will invert that to False. But that is not what happens. Here are some actual tests I performed:

              The value and the mask in these examples are:
              FileAttributes Value that contains a bit field that indicates whether a resource is a folder or a file.
              Folder = 8208D, File = 8224D

              Mask		Bit mask that tests for the presence of a folder (16D).
              

              Option Strict is NOT set.
              _____________________________________________________________________________________________________

              GOAL: Run code on "True" condition (Resource is a folder):
              If (FileAttributes And FILE_ATTRIBUTE_DIRECTORY) Then
              'Execute code.
              End If

              When FileAttributes = 8208D (Folder):
              	8208D (Folder)    =    		2	0	1	0	H
              					0010	0000	0001	0000	B
              	16D (Mask)        =	AND	0000	0000	0001	0000	B
                                                          \_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_
              	Result			        0000	0000	0001	0000	B    <>	0, ("True"), Code executes as it should.
              
              
              When FileAttributes = 8224D (File):
              	8224D (File)    =    		2	0	2	0	H
              					0010	0000	0010	0000	B
              	16D (Mask)      =	AND	0000	0000	0001	0000	B
                                                          \_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_
              	Result			        0000	0000	0000	0000	B     =	0, ("False"), Code does not execute.
              											      This is correct.
              

              _____________________________________________________________________________________________________
              GOAL: Run code on "False" condition (Resource is a file):
              If Not (FileAttributes And FILE_ATTRIBUTE_DIRECTORY) Then
              'Execute code.
              End If

              When FileAttributes = 8208D (Folder):
              	8208D (Folder)    =    		2	0	1	0	H
              					0010	0000	0001	0000	B
              	16D (Mask)        =	AND	0000	0000	0001	0000	B
                                                          \_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_
              	Result			        0000	0000	0001	0000	B    <> 0, ("True"), Code WOULD  execute, if left as is.
                                                          \_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_
              				NOT	1111	1111	1110	1111	B    <>	0, ("True"), Code executes when it SHOULD NOT.
              
              
              When FileAttributes = 8224D (File):
              	8224D (File)    =    		2	0	2	0	H
              					0010	0000	0010	0000	B
              	16D (Mask)      =	AND	0000	0000	0001	0000	B
                                                          \_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_
              	Result			        0000	0000	0000	0000	B    =  0, ("False"), Code does not execute, if left as is.
                                                          \_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_
              
              L Offline
              L Offline
              Lost User
              wrote on last edited by
              #12

              That is the difference between a logical and a bitwise expression. In your expressions you cannot use NOT to invert from non-zero (implied TRUE) to FALSE. I think as Dave suggests you need something like:

              If (FileAttributes And FILE_ATTRIBUTE_DIRECTORY) Then
              ' it is a directory.
              Else
              ' it is NOT a directory.
              End If

              or even

              If (FileAttributes And FILE_ATTRIBUTE_DIRECTORY) = FILE_ATTRIBUTE_DIRECTORY Then
              ' it is a directory.
              Else
              ' it is NOT a directory.
              End If

              Use the best guess

              T 1 Reply Last reply
              0
              • L Lost User

                That is the difference between a logical and a bitwise expression. In your expressions you cannot use NOT to invert from non-zero (implied TRUE) to FALSE. I think as Dave suggests you need something like:

                If (FileAttributes And FILE_ATTRIBUTE_DIRECTORY) Then
                ' it is a directory.
                Else
                ' it is NOT a directory.
                End If

                or even

                If (FileAttributes And FILE_ATTRIBUTE_DIRECTORY) = FILE_ATTRIBUTE_DIRECTORY Then
                ' it is a directory.
                Else
                ' it is NOT a directory.
                End If

                Use the best guess

                T Offline
                T Offline
                treddie
                wrote on last edited by
                #13

                That is the conclusion I came to in an earlier post. But I needed to understand why, and now I think I get the behavior. It's kind of like that old saying, "You can prove a positive, but you can't prove a negative." At least not without that extra Else clause thrown in.

                L 1 Reply Last reply
                0
                • T TnTinMn

                  Elimate the confusion and set "Option Strict On"; it is off in the default configuration. This will disallow the implied conversion from integer to boolean. see: Visual Studio compiler options, Part 2: Option Strict Also, review Operator Precedence in Visual Basic

                  T Offline
                  T Offline
                  treddie
                  wrote on last edited by
                  #14

                  Good advice.

                  1 Reply Last reply
                  0
                  • T treddie

                    That is the conclusion I came to in an earlier post. But I needed to understand why, and now I think I get the behavior. It's kind of like that old saying, "You can prove a positive, but you can't prove a negative." At least not without that extra Else clause thrown in.

                    L Offline
                    L Offline
                    Lost User
                    wrote on last edited by
                    #15

                    treddie wrote:

                    It's kind of like that old saying, "You can prove a positive, but you can't prove a negative." At least not without that extra Else clause thrown in.

                    Well that's not quite the issue. The issue is that you are using a bitwise operation whose result will be some number of 1 bits, including zero. If you than apply the NOT operator (which is also a bitwise operator) to that result you will get the bitwise complement. Neither of these is a boolean expression so their results are neither TRUE nor FALSE, they are just some number of bits from 0 to hex FF etc. If the result has any bits set then it is generally assumed to be TRUE in an IF clause; if it has no bits set then it is assumed to be FALSE. But applying the NOT operator to a non-zero result, can still give a non-zero answer. If you want strict boolean tests then you must include a comparison operator in the expression, as I did in the second example of my previous answer.

                    Use the best guess

                    T 1 Reply Last reply
                    0
                    • L Lost User

                      treddie wrote:

                      It's kind of like that old saying, "You can prove a positive, but you can't prove a negative." At least not without that extra Else clause thrown in.

                      Well that's not quite the issue. The issue is that you are using a bitwise operation whose result will be some number of 1 bits, including zero. If you than apply the NOT operator (which is also a bitwise operator) to that result you will get the bitwise complement. Neither of these is a boolean expression so their results are neither TRUE nor FALSE, they are just some number of bits from 0 to hex FF etc. If the result has any bits set then it is generally assumed to be TRUE in an IF clause; if it has no bits set then it is assumed to be FALSE. But applying the NOT operator to a non-zero result, can still give a non-zero answer. If you want strict boolean tests then you must include a comparison operator in the expression, as I did in the second example of my previous answer.

                      Use the best guess

                      T Offline
                      T Offline
                      treddie
                      wrote on last edited by
                      #16

                      Makes total sense.

                      1 Reply Last reply
                      0
                      Reply
                      • Reply as topic
                      Log in to reply
                      • Oldest to Newest
                      • Newest to Oldest
                      • Most Votes


                      • Login

                      • Don't have an account? Register

                      • Login or register to search.
                      • First post
                        Last post
                      0
                      • Categories
                      • Recent
                      • Tags
                      • Popular
                      • World
                      • Users
                      • Groups