CSCI 1730                    Programming Project 6A                  Summer 2009

                    Class of sets of natural numbers, Part A


This program is due by midnight on *** Monday, July 20. ***

In this assignment you will implement your own public set class, to be called
Nset, for finite sets of natural numbers. 

Nset should be able to store arbitrarily large sets of natural numbers.
Your code may make use of arrays and other basic C++ language features,
but must never reference C++ Standard Library components involving 
container classes (declared in <vector>, <list>, <deque>, <queue>, <stack>,
<map>, <set>, <valarray>, or <bitset>).

Your project submission should include a header file nnset.h, an
implementation file nnset.cc, a driver file proj6Atest.cc, a Makefile
and a READ_ME file.  Your Makefile should allow for separate compilation of
object files nnset.o and proj6Atest.o, along with linking the two object
files to produce an executable file proj6Atest.  This executable file should
include at least one test of each public member function of your Nset 
class.  There is a sample Makefile of this sort linked from the "projects"
sub-page of the course web site.  As illustrated in the sample, your Makefile
should compile and link everything when "make" is executed in your project
directory.

You may implement more functions than required.  Remember to include a test
for each public function you implement, whether or not the function is required.

The required public functions, with their behaviors, are as follows.
All are to be member functions of Nset.

Constructors: supply constructors in such a way that the default is to create
  an empty set, and for any n >= 0 Nset( n ) creates the set of natural numbers
  which are  < n, i.e., the set {0, 1, ..., n-1}.  Also define a copy
  constructor.
  
Destructor: define a destructor which deallocates any memory which was
  allocated dynamically.

Accessors: supply functions which perform as follows for an arbitrary object
  myset of type Nset and arbitrary m, n >= 0.
    myset.minelt( n ) returns the smallest element of myset which is >= n,
      or -1 if there is no such element.  The default for n should be 0,
      so that myset.minelt( ) returns the same value as myset.minelt( 0 ).
    myset.maxelt( n ) returns the largest element of myset which is <= n, or
      -1 if there is no such element.  With no argument myset.maxelt( ) should
      return the largest element of myset, or -1 if there is no such element.
    myset.has( n ) returns true if n is an element of myset and false if not.
    myset.card( ) returns the cardinality of myset.
    myset.display( m, n ) displays to standard output the smallest m members of
      myset which are >= n, or all of them which are >= n if there are <=  m
      of them.  If n is omitted it should default to 0, but m should never be
      omitted.
  
Comparators: supply boolean functions subset( ), superset( ), and equals( ) so
  that if lset and rset are objects of type Nset then lset.subset( rset ) is
  true iff lset is contained in rset, lset.superset( rset ) is true iff lset
  contains rset, and  lset.equals( rset ) is true iff lset is equal to rset.

Mutators: supply functions which perform as follows for arbitrary objects
  lset and rset of type Nset and arbitrary n >= 0.
    lset.addelt( n ) adds n to lset (so no change to lset if it already
      contains n).
    lset.delelt( n ) removes n from lset (so no change to lset if it doesn't
      contain n to begin with).
    lset.Union ( rset ) adds the members of rset to lset.
    lset.intersect ( rset ) replaces lset by its intersection with rset.
    lset.minus ( rset ) removes all members of rset from lset.
    lset.delta ( rset ) replaces lset by its symmetric difference with rset.
    lset.add ( n ) adds (numerically) n to each element of lset.
    lset.add ( rset ) replaces lset by the numbers which can be obtained as
      as the numerical sum of an element of lset and an element of rset.
    lset.mul ( n ) multiplies (numerically) each element of lset by n.
    lset.mul ( rset ) replaces lset by the numbers which can be obtained as
      as the numerical product of an element of lset and an element of rset.

Some things to note:

  *The behaviors of the public member functions should be as described,
   so that the teaching assistant and the instructor can test your Nset
   class and its functions without editing your code.  The same goes 
   for the name of the class, the names of the files submitted, and the
   names of the executable files generated by the Makefile.
   
  *Develop this program following proper methodology, starting with a 
   written plan.  Develop the code one function at a time, with readable 
   formatting, meaningful identifier names and illuminating comments.
   For each function, write the test code for it before writing the code for
   the function itself.

  *Note that an overloaded assignment operator for Nset has not been asked for,
   so your code should pass and return Nset objects only by reference.  
   Operator overloading will be required in Project 6B. 

  *Design your Nset class to be efficient in its use of time and memory, and
   not to leak memory.  Design Nset for "dense" sets, so that if your
   platform can support an Nset containing the element n then it can support
   the Nset created by a call to the constructor Nset( n ).  This means you 
   shouldn't use linked lists or other data structures aimed at sparse sets.

  *The submission procedure and requirements common to all projects are
   described on a separate page which is linked from the course "projects"
   sub-page.  Follow the submission procedure carefully.

  *Your programs must be written in C++.
  
  *Your programs should be robust and include appropriate error checks.

  *Your project should compile on "odin", or on "albany" or one of the
   other Linux workstations in the 307 lab, using g++ for GCC 4.1.2.
   Projects which compile properly will be scored out of 100
   (if on time) based on (1) correctness of operation, (2) quality of design,
   (3) coding style and documentation of the source code, and (4) correctness
   and usefulness of the READ_ME file and the Makefile.