4
\$\begingroup\$

I'm trying to write a function that returns the number of bits set in a 32-bit integer in VBScript, it's just for practising the language. The function I've written so far looks okay, but I'm wondering if there was a simpler solution.

Function countBits(value)
  Dim n : n = 0
  Dim mask : mask = 1
  Dim i
  For i = 0 to 30
    If (value And mask) > 0 Then
      n = n +1
    End If
  Next
  If (value And &h8000) then
    n = n+1
  End If
  countBits = n
End Function

I found that there are no shift operators in VBScript and an overflow (Err.Number = 6) if I iterate for 0 to 31, that's why I add the explicitly check of the MSB after the look.

Any solutions to improve (maybe generalize) this?


edit: removed the useless error handling part, as it's a remains of starting with 31 as an upper bound in the first (and at that time only) loop

\$\endgroup\$

1 Answer 1

2
\$\begingroup\$

According to information in VBScript Data Types MSDN article, a 32-bit integer is long variant subtype.

However, the value &h8000 (decimal -32768) seems to be a 16-bit integer minimal value; it's hexadecimal &hFFFF8000 if converted to long subtype (check Wscript.Echo Hex(&h8000).

This means that your function miscounts 1 additional bit for all long values above 32767 i.e. above 16-bit integer maximal value &h7FFF.

To check the sign bit of a long value correctly, use &h80000000 as follows:

Function countBits(value)
  Dim mask : mask = 1
  Dim i
  countBits = 0                    ' no need to use any auxiliary variable
  For i = 0 to 30
    If ( value And mask ) > 0 Then
      countBits = countBits + 1
    End If
    mask = mask * 2                ' got lost due to your own edit Dec 11 '16 at 14:22
  Next
  If ( value And &h80000000 ) Then ' check the sign bit
    countBits = countBits + 1
  End If
End Function

Sample tests:

Wscript.Echo countBits(2^16)         '  1
Wscript.Echo countBits(2^30)         '  1
Wscript.Echo countBits(1)            '  1
Wscript.Echo countBits(-1)           ' 32
Wscript.Echo countBits(-2)           ' 31
Wscript.Echo countBits(-2147483648)  '  1
\$\endgroup\$
1
  • \$\begingroup\$ thanks so much sometimes I seem to be so blind for some important details, the off-by-one syndrome has so many faces this time I was off by one chunk of hexadecimal places. \$\endgroup\$
    – Wolf
    Jul 31, 2017 at 14:46

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Not the answer you're looking for? Browse other questions tagged or ask your own question.