home *** CD-ROM | disk | FTP | other *** search
/ The Devil's Doorknob BBS Capture (1996-2003) / devilsdoorknobbbscapture1996-2003.iso / Dloads / OTHERUTI / TCPP10-8.ZIP / CLASSSRC.ZIP / ABSTARRY.CPP next >
C/C++ Source or Header  |  1990-09-26  |  14KB  |  545 lines

  1. //
  2. // This file contains proprietary information of Borland International.
  3. // Copying or reproduction without prior written approval is prohibited.
  4. //
  5. // Copyright (c) 1990
  6. // Borland International
  7. // 1800 Scotts Valley Dr.
  8. // Scotts Valley, CA 95066
  9. // (408) 438-8400
  10. //
  11.  
  12. // Contents ----------------------------------------------------------------
  13. //
  14. //      AbstractArray::AbstractArray                        constructor
  15. //      AbstractArray::~AbstractArray                       destructor
  16. //      AbstractArray::detach                               Object
  17. //      AbstractArray::detach                               int
  18. //      AbstractArray::hashValue
  19. //      AbstractArray::reallocate
  20. //      AbstractArray::isEqual
  21. //      AbstractArray::initIterator
  22. //      AbstractArray::printContentsOn
  23. //
  24. //      ArrayIterator::operator int
  25. //      ArrayIterator::operator Object
  26. //      ArrayIterator::restart
  27. //      ArrayIterator::operator ++
  28. //
  29. // Description
  30. //
  31. //      Implementation of class AbstractArray and class ArrayIterator member
  32. //      functions.
  33. //
  34. // End ---------------------------------------------------------------------
  35.  
  36. // Interface Dependencies ---------------------------------------------------
  37.  
  38. #ifndef __IOSTREAM_H
  39. #include <iostream.h>
  40. #define __IOSTREAM_H
  41. #endif
  42.  
  43. #ifndef __STDLIB_H
  44. #include <stdlib.h>
  45. #define __STDLIB_H
  46. #endif
  47.  
  48. #ifndef __ASSERT_H
  49. #include <assert.h>
  50. #define __ASSERT_H
  51. #endif
  52.  
  53. #ifndef __CLSDEFS_H
  54. #include <clsdefs.h>
  55. #endif
  56.  
  57. #ifndef __CLSTYPES_H
  58. #include <clstypes.h>
  59. #endif
  60.  
  61. #ifndef __OBJECT_H
  62. #include <object.h>
  63. #endif
  64.  
  65. #ifndef __CONTAIN_H
  66. #include <contain.h>
  67. #endif
  68.  
  69. #ifndef __ABSTARRY_H
  70. #include <abstarry.h>
  71. #endif
  72.  
  73. // End Interface Dependencies ------------------------------------------------
  74.  
  75. // Implementation Dependencies ----------------------------------------------
  76. // End Implementation Dependencies -------------------------------------------
  77.  
  78.  
  79. // Constructor //
  80.  
  81. AbstractArray::AbstractArray( int anUpper, int aLower, sizeType aDelta )
  82.  
  83. // Summary -----------------------------------------------------------------
  84. //
  85. //      Constructor for an abstract array.  An abstract array can be made
  86. //         to be either of a fixed or expanding size.  In an expanding array,
  87. //         when a reference is made to an index greater than the current upper
  88. //         bound of the array, the array will grow to allow the given index
  89. //      to reference a valid array object.  The number of elements by
  90. //      which this growth is performed is given by the parameter aDelta.
  91. //
  92. // Parameters
  93. //
  94. //      anUpper
  95. //
  96. //      The upper bound for the array.
  97. //
  98. //      aLower
  99. //
  100. //      The lower bound for the array.  The initial size of the array is
  101. //      calculated from the upper and lower bounds.
  102. //
  103. //      aDelta
  104. //
  105. //      The growth factor for the array.
  106. //
  107. // Functional Description
  108. //
  109. //      We set up the private parts of the array, allocate space for the
  110. //      pointers, then set all the allocated pointers to point to the 
  111. //      error object.
  112. //
  113. // End ---------------------------------------------------------------------
  114. {
  115.     lowerbound = whereToAdd = aLower;
  116.     upperbound = anUpper;
  117.     delta = aDelta;
  118.     theArray = new Object *[ arraySize() ];
  119.     for( int i = 0; i < arraySize(); i++ )
  120.     {
  121.         theArray[ i ] = ZERO;
  122.     } // end for
  123. }
  124. // End Constructor AbstractArray::AbstractArray //
  125.  
  126.  
  127. // Destructor //
  128.  
  129. AbstractArray::~AbstractArray()
  130.  
  131. // Summary -----------------------------------------------------------------
  132. //
  133. //      Destructor for a AbstractArray object.
  134. //
  135. // End ---------------------------------------------------------------------
  136. {
  137.     for( int i = 0; i < arraySize(); i++ )
  138.         if( theArray[ i ] != ZERO )
  139.             delete theArray[ i ];
  140.     delete [ arraySize() ] theArray;
  141. }
  142. // End Destructor //
  143.  
  144.  
  145. // Member Function //
  146.  
  147. void    AbstractArray::detach( const Object& toDetach, int deleteObjectToo )
  148.  
  149. // Summary -----------------------------------------------------------------
  150. //
  151. //      Detaches an object from the array.
  152. //
  153. // Parameter
  154. //
  155. //      toDetach
  156. //
  157. //      The object we are to search for and detach from the AbstractArray.
  158. //
  159. //      deleteObjectToo
  160. //
  161. //      Specifies whether we are to delete the object.
  162. //
  163. // Functional Description                     
  164. //
  165. //      If the object specified is at the lower bound of the array, we remove
  166. //      the reference right away.  Otherwise, we iterate through the array until
  167. //      we find it, then remove the reference.
  168. //
  169. // Remarks
  170. //
  171. //  warnings:
  172. //      No error condition is generated if the object which was specified
  173. //      isn't in the array.
  174. //
  175. // End ---------------------------------------------------------------------
  176. {
  177.     if ( toDetach == NOOBJECT )
  178.         return;
  179.  
  180.     for ( int i = 0; i < arraySize(); i++ )
  181.     {
  182.         if ( ( theArray[ i ] != ZERO ) && ( *theArray[ i ] == toDetach ) )
  183.         {
  184.             if ( deleteObjectToo )
  185.             {
  186.                 delete theArray[ i ];
  187.             }
  188.             theArray[ i ] = ZERO;
  189.             itemsInContainer--;
  190.             break;
  191.         }
  192.     } // end for //
  193. }
  194. // End Member Function AbstractArray::detach //
  195.  
  196.  
  197. // Member Function //
  198.  
  199. void    AbstractArray::detach( int atIndex, int deleteObjectToo )
  200.  
  201. // Summary -----------------------------------------------------------------
  202. //
  203. //      Detaches an object from the array at the given index.
  204. //
  205. // Parameter
  206. //
  207. //      toIndex
  208. //
  209. //      The index from which we are to detach the object.
  210. //
  211. //      deleteObjectToo
  212. //
  213. //      Specifies whether we are to delete the object.
  214. //
  215. // Remarks
  216. //
  217. //  warnings:
  218. //      No error condition is generated if the object which was specified
  219. //      isn't in the array.
  220. //
  221. // End ---------------------------------------------------------------------
  222. {
  223.     if ( theArray[ atIndex - lowerbound ] != ZERO )
  224.     {
  225.         if ( deleteObjectToo )
  226.         {
  227.             delete ( theArray[ atIndex - lowerbound ] );
  228.         }
  229.         theArray[ atIndex - lowerbound ] = ZERO;
  230.         itemsInContainer--;
  231.     } // end if there was an element already there in the array.
  232. }
  233. // End Member Function AbstractArray::detach //
  234.  
  235.  
  236. // Member Function //
  237.  
  238. hashValueType AbstractArray::hashValue() const
  239.  
  240. // Summary -----------------------------------------------------------------
  241. //
  242. //      Returns the hash value of a array.
  243. //
  244. // End ---------------------------------------------------------------------
  245. {
  246.     return hashValueType(0);
  247. }
  248. // End Member Function AbstractArray::hashValue //
  249.  
  250.  
  251. // Member Function //
  252.  
  253. void AbstractArray::reallocate( sizeType newSize )
  254.  
  255. // Summary -----------------------------------------------------------------
  256. //
  257. //         Reallocates the array's pointer vector to a new size.
  258. //
  259. // Parameters
  260. //
  261. //         newSize
  262. //
  263. //         The number of pointers which is to be in the new vector.
  264. //
  265. // Functional Description
  266. //
  267. //         We allocate space for a new pointer vector of the given size,
  268. //         adjusted to take into account the growth factor.  We then copy
  269. //         the old vector into the new one and fix up the pointer in the
  270. //         array object.
  271. //
  272. // Remarks
  273. //
  274. //  assumptions
  275. //         Asserts that the new size of the pointer vector is greater than
  276. //         the current size.  We do "expanding-only" arrays, not accordions.
  277. //
  278. // End ---------------------------------------------------------------------
  279. {
  280.     if ( delta == 0 )
  281.     {
  282.         cerr << "Error:  Attempting to expand a fixed size array.";
  283.         exit(__EEXPAND);
  284.     }
  285.  
  286.     int i;        // Loop counter for moving the pointers from the old vector
  287.                 // to the new one.
  288.  
  289. // Body Comment
  290. //
  291. //         We assume that the new pointer vector size is greater than the
  292. //         current vector size.
  293. //
  294. // End
  295.  
  296.     assert ( newSize > arraySize() );
  297.  
  298.     sizeType adjustedSize = newSize + ( delta - ( newSize % delta ) );
  299.  
  300.     Object **newArray = new Object *[ adjustedSize ];
  301.     if ( newArray == 0 )
  302.     {
  303.         cerr << "Error:  Out of Memory";
  304.         exit(__ENOMEM);
  305.     }
  306.  
  307.     for ( i = 0; i < arraySize(); i++ )
  308.     {
  309.         newArray[i] = theArray[i];
  310.     }
  311.     for (; i < adjustedSize; i++ )
  312.     {
  313.         newArray[i] = ZERO;
  314.     }
  315.  
  316.     delete [ arraySize() ] theArray;
  317.     theArray = newArray;
  318.     upperbound = adjustedSize + lowerbound - 1;
  319.  
  320. }
  321. // End Member Function AbstractArray::reallocate //
  322.  
  323.  
  324. // Member Function //
  325.  
  326. int AbstractArray::isEqual( const Object& testObject ) const
  327.  
  328. // Summary -----------------------------------------------------------------
  329. //
  330. //         Tests for equality of two arrays.  Two arrays are equal if they
  331. //         have the same dimensions and the same objects at the same indices.
  332. //
  333. // Parameters
  334. //
  335. //         testObject
  336. //
  337. //         The array which we will be testing against this.
  338. //
  339. // End ---------------------------------------------------------------------
  340. {
  341.  
  342.     if ( lowerbound != ((AbstractArray&)testObject).lowerbound ||
  343.          upperbound != ((AbstractArray&)testObject).upperbound )
  344.     {
  345.         return 0;
  346.     }
  347.  
  348.     for ( int i = 0; i < arraySize(); i++ )
  349.     {
  350.  
  351. // Body Comment
  352. //
  353. //         The two array elements can be null, so check that first.
  354. //         If there are really objects there, compare them for equality.
  355. //
  356. // End
  357.  
  358.         if ( theArray[i] != ZERO )
  359.         {
  360.             if ( ((AbstractArray&)testObject).theArray[i] != ZERO )
  361.             {
  362.                 if ( *theArray[i] !=
  363.                      *( ((AbstractArray &)testObject).theArray[i] ) )
  364.                 {
  365.                     return 0; // objects weren't equal.
  366.                 }
  367.             }
  368.             else // the first pointer wasn't ZERO but the second was
  369.             {
  370.                 return 0;
  371.             }
  372.         }
  373.         else
  374.             if ( ((AbstractArray&)testObject).theArray[i] != ZERO )
  375.             {
  376.                 return 0;  // first pointer was ZERO but the second wasn't
  377.             }
  378.     }  // end for each element in the array.
  379.     return 1;
  380. }
  381. // End Member Function AbstractArray::isEqual //
  382.  
  383.  
  384. // Member Function //
  385.  
  386. ContainerIterator& AbstractArray::initIterator() const
  387.  
  388. // Summary -----------------------------------------------------------------
  389. //
  390. //      Initializes an iterator for a list.
  391. //
  392. // End ---------------------------------------------------------------------
  393. {
  394.     return *( (ContainerIterator *)new ArrayIterator( *this ) );
  395. }
  396. // End Member Function AbstractArray::initIterator //
  397.  
  398.  
  399. // Member Function //
  400.  
  401. void AbstractArray::printContentsOn( ostream& outputStream ) const
  402.  
  403. // Summary -----------------------------------------------------------------
  404. //
  405. //      Displays the non-ZERO contents of an array on the given stream.
  406. //
  407. // Parameters
  408. //
  409. //      outputStream
  410. //
  411. //      The stream on which we will be writing the contents.
  412. //
  413. // Functional Description
  414. //
  415. //      We initialize an iterator, then iterator through each object,
  416. //      asking the objects to print themselves if they are not the
  417. //         error object.
  418. //
  419. // Remarks
  420. //
  421. //  warnings:
  422. //      We must be sure to delete the container iterator, since it was
  423. //      allocated on the heap.
  424. //
  425. // End ---------------------------------------------------------------------
  426. {
  427.     ContainerIterator& printIterator = initIterator();
  428.  
  429.     printHeader( outputStream );
  430.  
  431.     while( int(printIterator) != 0 )
  432.     {
  433.         Object& arrayObject = printIterator++;
  434.         if ( arrayObject != NOOBJECT )
  435.         {
  436.             arrayObject.printOn( outputStream );
  437.  
  438.             if ( int(printIterator) != 0 )
  439.             {
  440.             printSeparator( outputStream );
  441.             }
  442.             else // there are no more objects in the array.
  443.             {
  444.                 break;
  445.             }
  446.         } // end if the array object is NOOBJECT.
  447.     } // end while //
  448.  
  449.     printTrailer( outputStream );
  450.     delete &printIterator;
  451. }
  452. // End Member Function AbstractArray::printContentsOn //
  453.  
  454.  
  455. // Destructor //
  456.  
  457. ArrayIterator::~ArrayIterator()
  458.  
  459. // Summary -----------------------------------------------------------------
  460. //
  461. //      Destructor for a ArrayIterator object.
  462. //
  463. // End ---------------------------------------------------------------------
  464. {
  465. }
  466. // End Destructor //
  467.  
  468.  
  469. // Member Function //
  470.  
  471. ArrayIterator::operator int()
  472.  
  473. // Summary -----------------------------------------------------------------
  474. //
  475. //      Integer conversion for an array iterator.
  476. //
  477. // End ---------------------------------------------------------------------
  478. {
  479.     return currentIndex <= beingIterated.upperbound;
  480. }
  481. // End Member Function operator int //
  482.  
  483.  
  484. // Member Function //
  485.  
  486. ArrayIterator::operator Object&()
  487.  
  488. // Summary -----------------------------------------------------------------
  489. //
  490. //      Object reference conversion for an array iterator.
  491. //
  492. // End ---------------------------------------------------------------------
  493. {
  494.     if ( currentIndex <= beingIterated.upperbound )
  495.     {
  496.         return ( (Object&)( beingIterated.objectAt( currentIndex ) ) );
  497.     }
  498.     else // no more elements in the array.
  499.     {
  500.         return NOOBJECT;
  501.     }
  502. }
  503. // End Member Function operator Object& //
  504.  
  505.  
  506. // Member Function //
  507.  
  508. void ArrayIterator::restart()
  509.  
  510. // Summary -----------------------------------------------------------------
  511. //
  512. //      ArrayIterator restart.
  513. //
  514. // End ---------------------------------------------------------------------
  515. {
  516.     currentIndex = beingIterated.lowerbound;
  517. }
  518. // End Member Function ArrayIterator::restart //
  519.  
  520.  
  521. // Member Function //
  522.  
  523. Object& ArrayIterator::operator ++()
  524.  
  525. // Summary -----------------------------------------------------------------
  526. //
  527. //         Increments the array iterator and returns the next object.
  528. //
  529. // End ---------------------------------------------------------------------
  530. {
  531.     if ( currentIndex <= beingIterated.upperbound )
  532.     {
  533.         currentIndex++;
  534.         return ( (Object&)( beingIterated.objectAt( currentIndex - 1 ) ) );
  535.  
  536.     }
  537.     else // no more elements in the array.
  538.     {
  539.         return NOOBJECT;
  540.     }
  541.  
  542. }
  543. // End Member Function ArrayIterator::operator ++//
  544.  
  545.