home *** CD-ROM | disk | FTP | other *** search
/ ftp.ee.pdx.edu / 2014.02.ftp.ee.pdx.edu.tar / ftp.ee.pdx.edu / pub / users / Harry / Blitz / OSProject / p7 / BitMap.c next >
Text File  |  2007-09-19  |  6KB  |  185 lines

  1. code BitMap
  2.  
  3.   -- Harry Porter  --  September 18, 2004
  4.  
  5.   behavior BitMap
  6.  
  7.     method Init (numberOfBits: int)
  8.       -- Initialize the BitMap instance, including the allocation of
  9.       -- an array of words to hold the data.  The computation of
  10.       -- numberOfWords is such that there will always be enough room
  11.       -- for one extra bit.  This is so that there will always be at
  12.       -- least one clear ("0") bit just beyond the bits holding the
  13.       -- data.  This is so the "FindAndSet" method can use a faster
  14.       -- algorithm.
  15.       --
  16.       -- NOTE: This routine calls "alloc".
  17.       --
  18.         var numWords: int = (numberOfBits / 32) + 1
  19.         if numberOfBits <= 0
  20.           FatalError ("In BitMap.Init, the numberOfBits is zero or less")
  21.         endIf
  22.         numBits = numberOfBits
  23.         arrayOfWords = alloc array of int { numWords of 0 }
  24.       endMethod
  25.  
  26.     method Print ()
  27.       -- Print the bit vector showing (by number) which bits have
  28.       -- been set.  For example:
  29.       --     BitMap with the following bits set: 0 1 2 7 9 13 99
  30.       --
  31.         var i: int
  32.         print ("BitMap with the following bits set:")
  33.         for i = 0 to numBits-1
  34.           if self.IsBitSet (i)
  35.             print (" ")
  36.             printInt (i)
  37.           endIf
  38.         endFor
  39.         nl ()
  40.       endMethod
  41.  
  42.     method Print2 ()
  43.       -- Print the bit vector showing each bit as "0" or "1".  Spaces are
  44.       -- inserted after every 8 bits for readability.  For example:
  45.       --     BitMap: 11100101 00110110 11011
  46.       --
  47.         var i: int
  48.         print ("BitMap:")
  49.         for i = 0 to numBits-1
  50.           if i%8 == 0
  51.             print (" ")
  52.           endIf
  53.           if self.IsBitSet (i)
  54.             print ("1")
  55.           else
  56.             print ("0")
  57.           endIf
  58.         endFor
  59.         nl()
  60.       endMethod
  61.  
  62.     method NumberOfClearBits () returns int
  63.       -- This method returns the number of bits that are clear (i.e., "0").
  64.         var i, count: int
  65.         count = 0
  66.         for i = 0 to numBits-1
  67.           if !self.IsBitSet (i)
  68.             count = count + 1
  69.           endIf
  70.         endFor
  71.         return count
  72.       endMethod
  73.  
  74.     method SetBit (bitNum: int)
  75.       -- This method is passed the number of a bit; it sets the bit to "1".
  76.       -- Bits are indexed with numbers from 0 through numberOfBits-1.
  77.         var word: int
  78.         if (bitNum < 0) || (bitNum >= numBits)
  79.           FatalError ("Within BitMap.SetBit: invalid bitNum")
  80.         endIf
  81.         word = bitNum / 32
  82.         arrayOfWords [word] = (arrayOfWords [word]) | (0x00000001 << bitNum % 32)
  83.       endMethod
  84.  
  85.     method ClearBit (bitNum: int)
  86.       -- This method is passed the number of a bit; it clears the bit to "0".
  87.       -- Bits are indexed with numbers from 0 through numberOfBits-1.
  88.         var word: int
  89.         if (bitNum < 0) || (bitNum >= numBits)
  90.           FatalError ("Within BitMap.ClearBit: invalid bitNum")
  91.         endIf
  92.         word = bitNum / 32
  93.         arrayOfWords [word] = (arrayOfWords [word]) & ! (0x00000001 << bitNum % 32)
  94.       endMethod
  95.  
  96.     method IsBitSet (bitNum: int) returns bool
  97.       -- This method is passed the number of a bit; it returns TRUE iff that bit is
  98.       -- set to "1".  Bits are indexed with numbers from 0 through numberOfBits-1.
  99.         var word: int
  100.         if (bitNum < 0) || (bitNum >= numBits)
  101.           FatalError ("Within BitMap.IsBitSet: invalid bitNum")
  102.         endIf
  103.         word = bitNum / 32
  104.         return (((arrayOfWords [word]) >> (bitNum % 32)) & 0x00000001) != 0
  105.       endMethod
  106.  
  107.     method FindZeroAndSet () returns int
  108.       -- This method finds the first bit that is clear (i.e., "0").  The sets
  109.       -- it to "1" and returns index of the bit.  If all bits are already set,
  110.       -- this method returns -1.
  111.       --
  112.       -- Note:  The arrayOfWords was initialized so that there is always at least
  113.       -- one extra bit beyond the end, which will be zero.  This allows the
  114.       -- search for a clear bit to use a faster algorithm, which finds the
  115.       -- first clear bit, then tests to see if it is a legal bit.
  116.       --
  117.         var i, word: int
  118.         -- Find the first word containing at least one clear bit.
  119.         while arrayOfWords [i] == 0xffffffff
  120.           i = i + 1
  121.         endWhile
  122.         -- Find the clear bit within that word.
  123.         word = arrayOfWords [i]
  124.         i = i * 32
  125.         while (word & 0x00000001) != 0
  126.           i = i + 1
  127.           word = word >> 1
  128.         endWhile
  129.         -- See if this is a legal bit; if so set the bit and return its index.
  130.         if i >= numBits
  131.           return -1
  132.         else
  133.           self.SetBit (i)
  134.           return i
  135.         endIf
  136.       endMethod
  137.  
  138.   endBehavior
  139.  
  140.  
  141.  
  142.   -- This function is used to test/debug the BitMap code.
  143.   function TestBitMap ()
  144.       var bm: BitMap = new BitMap
  145.           i, j: int
  146.       print ("Running test of 'BitMap' class....\n")
  147.       bm.Init (40)
  148.  
  149.       bm.Print2 ()
  150.       for i = 0 to 40
  151.         print ("Calling FindZeroAndSet(")  printInt (i)   print (")...")
  152.         j = bm.FindZeroAndSet ()
  153.         print ("    returns... ")
  154.         printInt (j)
  155.         nl ()
  156.         bm.Print2 ()
  157.       endFor
  158.  
  159.       print ("Clear each of the bits...\n")
  160.       for i = 0 to 39
  161.         bm.ClearBit (i)
  162.         bm.Print2 ()
  163.       endFor
  164.  
  165.       print ("number clear = ")  printInt (bm.NumberOfClearBits ())  nl ()
  166.  
  167.       print ("Set each of the bits...\n")
  168.       for i = 0 to 39
  169.         bm.SetBit (i)
  170.         bm.Print2 ()
  171.         print ("number clear = ")  printInt (bm.NumberOfClearBits ())  nl ()
  172.       endFor
  173.  
  174.       bm.ClearBit (3)
  175.       bm.ClearBit (4)
  176.       bm.ClearBit (5)
  177.       bm.ClearBit (6)
  178.       bm.ClearBit (32)
  179.       bm.Print2 ()
  180.       bm.Print ()
  181.  
  182.     endFunction
  183.  
  184. endCode
  185.