/******************************************************************************
Container Interface
----------------------------------------------------
Copyright (c) Gunnar Gotshalks. All Rights Reserved.

Permission to use, copy, modify, and distribute this software
and its documentation for NON-COMMERCIAL purposes and
without fee is hereby granted. 
*******************************************************************************/

package FlexOr.container;
import java.util.Enumeration;

/** A container can hold any collection of Objects. 
<P>
@author Gunnar Gotshalks
@version 1.0 1999 Jan 15
*/

public interface Container extends Cloneable {

/*******************************************************************************
   Access Methods
*******************************************************************************/

/** Determines whether an element is in the container.

<P><PRE><B>Requires:</B> True
<B>Ensures:</B> contains(obj) => result = true
            not contains(obj) => result = false
</PRE>
*/

  boolean contains(Object obj);

/** Returns an enumerator over the whole container. */
  
  Enumeration<Object> elements();

/** Check if the container is empty.
<P><PRE><B>Requires:</B> True
<B>Ensures:</B> result = (size = 0)
</PRE>
 */

  boolean isEmpty();

/** Check if the container is full.
<P><PRE><B>Requires:</B> True
<B>Ensures:</B> result = (size = capacity)
</PRE>
 */

  boolean isFull();

/** Returns the number of elements in the container.
<P><PRE><B>Requires:</B> True
<B>Ensures:</B> result = size
</PRE>
*/
  
  int size();

/*******************************************************************************
   Update Methods

Remove has two versions.  One without argument removes a default element
which makes sense for sequence type containers.  The other with an argument
obj specifying which object to remove which does not make sense for sequences
such as stacks and queues, and does not make sense for non-linear containers
such as trees and graphs.  This implies that one specifies a basic container
to which one can only add and then create two subclasses; one for each type of
remove.

Specifying add without a corresponding remove seems odd as that
implies one cannot remove from a "basic" container.  The solution adopted is to
specify remove(), with no arguments, based on the observation that
removal with no arguments means the removal of the first element in a standard
enumeration of the container contents.  While not always useful, at least it
makes sense for all containers.
*******************************************************************************/

/** Adds <CODE>obj</CODE> at the default location.
<P><PRE><B>Requires:</B> size < capacity
<B>Ensures:</B> contains(obj) = true
                size = old size + 1
</PRE>
@exception ContainerFullException if container already contains capacity
elements for finite size containers.
*/

  void add(Object obj);
  
/** Empty the container.
<P><PRE><B>Requires:</B> True
<B>Ensures:</B> size = 0
</PRE>
*/

  void removeAll();

/**
Remove the first element based on a standard enumeration of the container
contents.

<P><PRE><B>Requires:</B> size > 0
<B>Ensures:</B> size = old size -1
</PRE>
@exception ContainerEmptyException if removing from an empty container.
*/

  Object remove();

/*******************************************************************************
   Object Methods
*******************************************************************************/

/** Return a copy of the container that points to the same objects
as in the original container.  Part way between a shallow and deep copy.  This is
equivalent to how a Vector is cloned.
<P><PRE><B>Requires:</B> True
<B>Ensures:</B> result = copy of container
</PRE>
*/

  Object clone();

/** Return a string representation of the contents of the container.
<P><PRE><B>Requires:</B> True
<B>Ensures:</B> result = string representation of contents
</PRE>
*/
  
  String toString();

/** Check for equality of contents of two containers.  By equality we mean an
equal sequence of elements as returned by the Enumerator for each sequence.
<P><PRE><B>Requires:</B> True
<B>Ensures:</B> result = true => container contents are equal
                result = false => container contents are not equal
</PRE>
 */

  boolean equals(Object container);

}