Any way to work with bits?

Just starting out? Need help? Post your questions and find answers here.
infratec
Always Here
Always Here
Posts: 7582
Joined: Sun Sep 07, 2008 12:45 pm
Location: Germany

Re: Any way to work with bits?

Post by infratec »

You were right.

When I use

Code: Select all

MessageRequester("Time", Str(ElapsedMilliseconds() - StartTime))
and disable the debugger,
I got:

Long: 1531
Byte: 1750

But...
I had to increase the loop counter to 100000000.

Ok, it is faster. (2us)
But it needs 3 bytes more memory in the worst case :mrgreen: :mrgreen: :mrgreen:

Bernd
User avatar
Kaeru Gaman
Addict
Addict
Posts: 4826
Joined: Sun Mar 19, 2006 1:57 pm
Location: Germany

Re: Any way to work with bits?

Post by Kaeru Gaman »

well... s**t on three bytes.
in the end the allocation the OS makes for the process will happen in 512byte chunks or something like that, so it's less than unimportant.
oh... and have a nice day.
infratec
Always Here
Always Here
Posts: 7582
Joined: Sun Sep 07, 2008 12:45 pm
Location: Germany

Re: Any way to work with bits?

Post by infratec »

Hi,

here is my final version:

Code: Select all

#MaxBits = 1024


Macro BitArraySize(Bits)
 ((Bits - 1) / 32 + 1)
EndMacro


Structure Test
 arry.l [BitArraySize(#MaxBits)]
EndStructure

Define myTest.Test

Dim NormalArray.l(BitArraySize(#MaxBits))


Debug "Arraysize: " + Str(ArraySize(NormalArray()))


Procedure InitBits(*A.l, Bits.i, Value.l) 
 If Value <> 0 : Value = $FFFFFFFF : EndIf
 FillMemory(*A, BitArraySize(Bits) * 4, Value, #PB_Long)         ; * 4 because we need the bytesize
EndProcedure


Procedure SetBit(*A.l, Index.i)
 *A + (Index >> 5)
  PokeL(*A, PeekL(*A) | (1 << (Index & $1F)))
EndProcedure


Procedure ClrBit(*A.l, Index.i)
 *A + (Index >> 5)
 PokeL(*A, PeekL(*A) &~ (1 << (Index & $1F)))
EndProcedure


Procedure TglBit(*A.l, Index.i)
 *A + (Index >> 5)
 PokeL(*A, PeekL(*A) ! (1 << (Index & $1F)))
EndProcedure


Procedure.i GetBit(*A.l, Index.l)
 *A + (Index >> 5)
 ProcedureReturn (PeekL(*A) & (1 << (Index & $1F))) >> (Index & $1F)
EndProcedure




InitBits(@myTest\arry, #MaxBits, #True)

SetBit(@myTest\arry, 4)
Debug GetBit(@myTest\arry, 4)

ClrBit(@myTest\arry, 4)
Debug GetBit(@myTest\arry, 4)

TglBit(@myTest\arry, 4)
Debug GetBit(@myTest\arry, 4)



InitBits(@NormalArray(), #MaxBits, #False)

SetBit(@NormalArray(), 144)
Debug GetBit(@NormalArray(), 144)

ClrBit(@NormalArray(), 144)
Debug GetBit(@NormalArray(), 144)

TglBit(@NormalArray(), 144)
Debug GetBit(@NormalArray(), 144)
Now it uses long for the speed.
And I had a fault with the parameter of the NormalArray:

The address of the first element is @NormalArray() and not @NormalArray :!:

Bernd
Seymour Clufley
Addict
Addict
Posts: 1264
Joined: Wed Feb 28, 2007 9:13 am
Location: London

Re: Any way to work with bits?

Post by Seymour Clufley »

Thanks for this. :)
JACK WEBB: "Coding in C is like sculpting a statue using only sandpaper. You can do it, but the result wouldn't be any better. So why bother? Just use the right tools and get the job done."
User avatar
idle
Always Here
Always Here
Posts: 5836
Joined: Fri Sep 21, 2007 5:52 am
Location: New Zealand

Re: Any way to work with bits?

Post by idle »

If you want it quicker better to use macros, I just ripped this from my bloomfilter

Code: Select all

*mem = AllocateMemory(32767/8)

Macro setBit(mem,bit)
*tb.byte
*tb = mem+(bit>>3)
*tb\b | (1 << (bit % 8))  
EndMacro

Macro GetBit(mem,bit,x)
*tb.byte
mf = (bit % 8)
*tb = mem+(bit>>3)
x  = (*tb\b & (1 << mf)) >> mf
EndMacro

getbit(*mem,1000,x)
Debug x  ;"0" 

setbit(*mem,1000)

getbit(*mem,1000,x)
Debug x  ;"1"

Post Reply