// Copyright(c) 1996,1997 ObjectSpace, Inc.
// Portions Copyright(c) 1995, 1996 Hewlett-Packard Company.

package COM.objectspace.jgl;

/**
 * The Copying class contains generic copying algorithms.
 * <p>
 * @see COM.objectspace.jgl.examples.CopyingExamples
 * @version 2.0.2
 * @author ObjectSpace, Inc.
 */

public final class Copying
  {
  private Copying()
    {
    }

  /**
   * Copy the elements from one range to another range of the same size.
   * Time complexity is linear and space complexity is constant.
   * @param first An iterator positioned at the first element of the input range.
   * @param last An iterator positioned immediately after the last element of the input range.
   * @param result An iterator positioned at the first element of the output range.
   * @return An iterator positioned immediately after the last element of the output range.
   */
  public static OutputIterator copy( InputIterator first, InputIterator last, OutputIterator result )
    {
    InputIterator firstx = (InputIterator) first.clone();
    OutputIterator resultx = (OutputIterator) result.clone();

    while ( !firstx.equals( last ) )
      {
      resultx.put( firstx.nextElement() );
      resultx.advance();
      }

    return resultx;
    }

  /**
   * Copy the elements from a container to a sequence.
   * Time complexity is linear and space complexity is constant.
   * @param input The input container.
   * @param result An iterator positioned at the first element of the output sequence.
   * @return An iterator positioned immediately after the last element of the output sequence.
   */
  public static OutputIterator copy( Container input, OutputIterator result )
    {
    return copy( input.start(), input.finish(), result );
    }

  /**
   * Insert the elements from one container into another container.
   * Time complexity is linear and space complexity is constant.
   * @param source The source container.
   * @param destination The destination container.
   */
  public static void copy( Container source, Container destination )
    {
    copy( source.start(), source.finish(), new InsertIterator( destination ) );
    }

  /**
   * Copy the elements backwards from one range to another range of the same size.
   * Time complexity is linear and space complexity is constant.
   * @param first An iterator positioned at the first element of the input range.
   * @param last An iterator positioned immediately after the last element of the input range.
   * @param result An iterator positioned immediately after the last element of the output range.
   * @return An iterator positioned at the first element of the output range.
   */
  public static OutputIterator copyBackward( BidirectionalIterator first, BidirectionalIterator last, BidirectionalIterator result )
    {
    BidirectionalIterator lastx = (BidirectionalIterator) last.clone();
    BidirectionalIterator resultx = (BidirectionalIterator) result.clone();

    while ( !first.equals( lastx ) )
      {
      resultx.retreat();
      lastx.retreat();
      resultx.put( lastx.get() );
      }

    return resultx;
    }
  }
