I'd like to use the concept of summing the powers of number 2 to combine settings in my app.
Kind of the same as VB uses vbNo, vbYes, vbIgnore etc
After I sum these numbers the challenge is to determine which numbers have been used in the sum.
Eg.
Setting #1 --> 2^1=2
Setting #2 --> 2^2=4
Setting #3 --> 2^3=8
If user selects #1 & #3 that sums up to 10 (2+8) --> this 10 can only be constructed from 2 and 8, no other combination of 2,4 and 8 is possible.
But how to deterrmine that with a function?
In the past I have been using a built-in function that gave me TRUE/FALSE if asked whether a certain number is a part of the this kind of sum or not, but cannot find it.
So:
is 2 a part of 10 (where 10 is a sum of 2^n) = TRUE
is 4 a part of 10 (where 10 is a sum of 2^n) = FALSE
is 8 a part of 10 (where 10 is a sum of 2^n) = TRUE
Using standard bit-wise operations...
If (10 And 2) Then Msgbox "2 is part of 10" Else MsgBox "2 is not part of 10"
If wanting to know each bit set in the number, high bit (&H80000000) needs to be tested separately
Code:
Dim lMask As Long
Dim lTarget As Long
lTarget = 2018 ' <<< number to test; negative numbers contain high bit
lMask = &H40000000
Do Until lMask = 0
If (lTarget And lMask) Then Debug.Print "number includes: " lMask
lMask = lMask \ 2
Loop
Last edited by LaVolpe; Jan 18th, 2018 at 10:37 AM.
Reason: oops, left of a zero on the starting mask
Insomnia is just a byproduct of, "It can't be done"
And here is another solution that can produce less loops, but rewrites the target number in the process. Same restriction, high bit needs to be tested separately.
Code:
Dim lMask As Long
Dim lTarget As Long
lTarget = 2018 ' <<< number to test; negative numbers contain high bit
Do Until lTarget = 0
lMask = lTarget And -lTarget: Debug.Print "number includes: "; lMask
lTarget = lTarget Xor lMask
Loop
Insomnia is just a byproduct of, "It can't be done"
Also, for Integers, you could only go to a power of 14 and Longs could only go to a power of 30, or you start tangling with the sign-bit, which is another discussion.
Maybe That'll Help,
Elroy
Last edited by Elroy; Jan 18th, 2018 at 12:11 PM.
Any software I post in these forums written by me is provided "AS IS" without warranty of any kind, expressed or implied, and permission is hereby granted, free of charge and without restriction, to any person obtaining a copy. To all, peace and happiness.
Normally you'd be better off using integer multiply/divide and masking as described.
But there are also the "Driver Support Routines" in the NT Kernel that could be used. While meant for longer Byte arrays they work with non-Variant value types in VB6. Here is an example using a single Long as the buffer: