Personal tools
You are here: Home Using an Integer to Store Bits
FrontPage >> MapInfoRoadmap >> MapBasicDevelopment >>

Using an Integer to Store Bits

Document Actions
last edited 1 year ago by BillThoen
This page discusses how you can use an Integer Column or Integer Variable to store and process bits.
Background

Normally MapInfo uses 1 byte per logical field, this is normal for a database. I have a situation where I want to be able to maintain a number of logical fields, but using a Logical column would create a large number of columns. The following functions allow you to use a 4-byte integer to store up to 32 bit-sized logical fields.


NOTES:

All bits are numbered from right to left starting at 1.
Current only handles 31 Bits (not sure how I can easily and safely check the 32nd bit). See Testing Bits in Signed Integers for the answer.


GetBit

This is a function that retrieves the status of the required bit. Simply by looping through the value you can establish what bits are set.

'  MapBasic Bitwise Operators
Declare Function GetBit(ByVal iVal As Integer, ByVal iBit as Integer) As Logical

' GetBit - Returns True or False Depending on the Status of the Bit
' iVal is the integer containing the bit pattern for checking
' iBit is the integer number of the bit to check
' Bits are Numbered From Right to Left Starting at 1

'REGION ' GetBit Function
FUNCTION GetBit(ByVal iVal As Integer, ByVal iBit as Integer) As Logical
DIM lBits(33) As Logical ' Bits Status
DIM iCnt As Integer ' Loop Counter


	' Make Sure Positive Integer
	iVal = Abs(iVal)
	
	'REGION ' Loop through testing Bits
	iCnt = 33
	Do
		lBits(iCnt) = False
		If iVal >= 2^(iCnt - 1) Then
			lBits(iCnt) = True
			iVal = iVal - 2^(iCnt - 1)
			'Print ":DEBUG :- Bit(" & iCnt & ") = True"
		Else
			'Print ":DEBUG :- Bit(" & iCnt & ") = False"
		End If
		
		iCnt = iCnt - 1
	Loop Until iCnt = 0
	'ENDREGION
	
	'REGION ' Make Sure iBit is outside the Array
	If iBit = 0 Then
		iBit = iBit + 1
	End If
	
	If iBit > 33 Then
		iBit = 33
	End If
	'ENDREGION
	
	'Return Value
	GetBit = lBits(iBit)


END FUNCTION
'ENDREGION

ModifyBit

This function allows you to set the status of any bit. It doesn't check the existing status to see if it need changing, it will just set the bit.

Declare Function ModifyBit(ByVal iVal As Integer, ByVal iBit As Integer, ByVal lState As Logical) As Integer

' ModifyBit - Returns an Integer With the requested bit set.
' iVal is the Input integer to modify
' iBit is the Integer number of the Bit to be changed
' lState is the new Logical state of the bit
'REGION
Function ModifyBit(ByVal iVal As Integer, ByVal iBit As Integer, ByVal lState As Logical) As Integer
DIM lBits(33) As Logical ' Bits Status
DIM iCnt As Integer ' Loop Counter

	' Set Default Value
	ModifyBit = 0

	' Make Sure Positive Integer
	iVal = Abs(iVal)
	
	'REGION ' Loop through testing Bits
	iCnt = 33
	Do
		lBits(iCnt) = False
		If iVal >= 2^(iCnt - 1) Then
			lBits(iCnt) = True
			iVal = iVal - 2^(iCnt - 1)
			'Print ":DEBUG :- Bit(" & iCnt & ") = True"
		Else
			'Print ":DEBUG :- Bit(" & iCnt & ") = False"
		End If
		
		iCnt = iCnt - 1
	Loop Until iCnt = 0
	'ENDREGION
	
	'REGION ' Make Sure iBit is inside the Array
	If iBit = 0 Then
		iBit = iBit + 1
	End If
	
	If iBit > 33 Then
		iBit = 33
	End If
	'ENDREGION
	
	'REGION ' Change iBit Status
	lBits(iBit) = lState
	'ENDREGION
	
	'REGION 'Calculate New Integer Value (the safe way)
	iVal = 0
	iCnt = 33
	Do
		If lBits(iCnt) = True Then
			iVal = iVal + (2^(iCnt - 1))
		 'Print ":DEBUG :- iVal = " & iVal
		End If
		iCnt = iCnt - 1
	Loop Until iCnt = 0
	'ENDREGION
	
	' Set Return Value
	'Print ":DEBUG :- ModifyBit = " & iVal
	ModifyBit = iVal
	
END FUNCTION
'ENDREGION

subtopics:
« December 2008 »
Su Mo Tu We Th Fr Sa
1 2 3 4 5 6
7 8 9 10 11 12 13
14 15 16 17 18 19 20
21 22 23 24 25 26 27
28 29 30 31
 

Powered by Plone, the Open Source Content Management System

This site conforms to the following standards: