/*
 * Example 3: class RWGDlist; generic doubly-linked lists, using ints
 *
 * $Id: gdlist.cpp,v 7.3 1995/09/06 23:45:19 jims Exp $
 *
 * (c) Copyright 1989 - 1996 Rogue Wave Software, Inc.
 * ALL RIGHTS RESERVED
 *
 * The software and information contained herein are proprietary to, and
 * comprise valuable trade secrets of, Rogue Wave Software, Inc., which
 * intends to preserve as trade secrets such software and information.
 * This software is furnished pursuant to a written license agreement and
 * may be used, copied, transmitted, and stored only in accordance with
 * the terms of such license and with the inclusion of the above copyright
 * notice.  This software and information or any other copies thereof may
 * not be provided or otherwise made available to any other person.
 *
 * Notwithstanding any other lease or license that may pertain to, or
 * accompany the delivery of, this computer software and information, the
 * rights of the Government regarding its use, reproduction and disclosure
 * are as set forth in Section 52.227-19 of the FARS Computer
 * Software-Restricted Rights clause.
 * 
 * Use, duplication, or disclosure by the Government is subject to
 * restrictions as set forth in subparagraph (c)(1)(ii) of the Rights in
 * Technical Data and Computer Software clause at DFARS 252.227-7013.
 * Contractor/Manufacturer is Rogue Wave Software, Inc.,
 * P.O. Box 2328, Corvallis, Oregon 97339.
 *
 * This computer software and information is distributed with "restricted
 * rights."  Use, duplication or disclosure is subject to restrictions as
 * set forth in NASA FAR SUP 18-52.227-79 (April 1985) "Commercial
 * Computer Software-Restricted Rights (April 1985)."  If the Clause at
 * 18-52.227-74 "Rights in Data General" is specified in the contract,
 * then the "Alternate III" clause applies.
 *
 ***************************************************************************
 *
 * $Log: gdlist.cpp,v $
 * Revision 7.3  1995/09/06 23:45:19  jims
 * Use new copyright macro
 *
 * Revision 7.2  1995/06/28  13:57:24  pearson
 * *** empty log message ***
 *
 * Revision 7.1  94/10/16  04:14:27  04:14:27  josh
 * Merged 6.1 and 7.0 development trees
 * 
 * Revision 6.3  1994/07/12  20:40:30  vriezen
 * Updated Copyright
 *
 * Revision 6.2  1994/06/02  19:22:32  foote
 * Port to Symantec 7.0 on Macintosh
 *
 * Revision 6.1  1994/04/15  19:08:25  vriezen
 * Move all files to 6.1
 *
 * Revision 2.3  1993/04/12  11:17:32  jims
 * Replaced "GDlist" with "RWGDlist"
 *
 * Revision 2.2  1993/02/13  21:46:42  keffer
 * Zortech does not have a definition for ostream::flush().
 *
 * Revision 2.1  1993/02/09  18:37:29  keffer
 * Updated with new iterator semantics.
 *
 * Revision 2.0  1992/10/23  03:34:26  keffer
 * RCS Baseline version
 *
 * 
 *    Rev 1.1   07 Jun 1992 17:11:08   KEFFER
 * Tools.h++ V5.1
 * 
 */


// Include the header file for the class RWGDlist:
#include "rw/gdlist.h"
#include "rw/rstream.h"

/* The class RWGDlist makes use of the macro declare defined in the header file
 * <generic.h> to implement the current C++ approximation to parameterized types.
 * The first argument is the class name (RWGDlist).
 * The second argument is the type of object being stored (int).
 */

declare(RWGDlist,int)

// Some data to be stored:
int idata[] = { 0, 1, 2, 3, 4, 5, 6, 7, 8 };

main()
{
  // Construct a linked-list of pointers to ints with no links:
  // The form: RWGDlist(int) is converted via a macro to intRWGDlist.
  RWGDlist(int) L;

  cout << "Prepend ints: 4 3 2 1 0\n";
  L.prepend(&idata[4]);
  L.prepend(&idata[3]);
  L.prepend(&idata[2]);
  L.prepend(&idata[1]);
  L.prepend(&idata[0]);

  cout << "Insert (append) ints: 5 6 7 8\n";
  L.insert(&idata[5]);
  L.insert(&idata[6]);
  L.insert(&idata[7]);
  L.insert(&idata[8]);

  cout << "Value at head is:   " << *L.first()   << endl;
  cout << "Value at tail is:   " << *L.last()    << endl;
  cout << "Number of links is: " <<  L.entries() << endl;

  cout << "Now remove and print each link from head:\n";
  while ( !L.isEmpty() )
    cout << *L.get() << endl;

  cout << "Remake list L, insert: 0 1 2 3 4 5\n\n";
  L.insert(&idata[0]);
  L.insert(&idata[1]);
  L.insert(&idata[2]);
  L.insert(&idata[3]);
  L.insert(&idata[4]);
  L.insert(&idata[5]);

  cout << "Construct an iterator for the linked-list.\n";
  RWGDlistIterator(int) c(L);

  // Exercise the iterator:

  cout << "Advance iterator 1 link.  Should point to: 0\n";
  ++c;
  cout << " *c.key() = " << *c.key() << endl;

  cout << "Advance iterator again.  Should point to: 1\n";
  ++c;
  cout << " *c.key() = " << *c.key() << endl;

  cout << "Move iterator to head of list.  Should point to: 0\n";
  c.toFirst();
  cout << " *c.key() = " << *c.key() << endl;

  cout << "Move iterator to find '4' and print it out:\n";
  c.findNextReference(&idata[4]);
  cout << " *c.key() = " << *c.key() << endl;

  cout << "Delete current item (which is 4).  Should point to 3.\n";
  c.remove();
  cout << " *c.key() = " << *c.key() << endl;

  // Use the operator () to move through the list:
  // first, reset the iterator:
  c.reset();

  cout << "Now reset the iterator and use operator() to move through the list.\n";
  cout << "Should read 0 1 2 3 5:\n";
  const int* v;
  while( (v = c()) != 0 )
    cout << *v << " ";

  cout << endl;

  return 0;
}
