// The interface for the C++ input and output routines.
#include <iostream.h>

// Class description for the int_table.
#include "int_table.h"

// We simply want to initialize the table to be using no ints, and have one 
// int as the current table.
int_table::int_table() : size(0), max_size(1) {
  table = new int;
}

// Here we check to see if someone is using an index within or without of the
// array.  If they are within, they get a good value, what they think they 
// should get, however, if they are accessing beyond the end of the array, or 
// before the beginning of the array, then they get the bogus value of 0. This
// is in-band signalling, generally considered bad, but we don't have any other
// method to deal with this error, except maybe throwing an exception.
int& int_table::operator[](int a) {
  if (a > -1 && a < size)
    return table[a];
  // Just in case someone changed it with a t[pow(32,5)] = 92 call :) 
  phantom = 0;
  return phantom;
}

//  Append an element onto the table.  If the table is too small to contain
// the new element, then the table is resized.  The table size is doubled in
// resize(), so the average case running time becomes O(1).
void int_table::add_elem(int a) {
  if (size+1 > max_size) {
    resize();
  }
  table[size++] = a;
}


//  This is solving a problem that really should be taken care of, every time
// this is called, it takes 2N time, though considering that it is not called
// often, the average case running time of an insert (which is the only thing 
// that resizes the table implicitly) becomes O(1).  A better way to do this 
// would be memcpy(table, old_table, size), but I have been counselled to avoid
// that due to the fact that it is not supported on all platforms.
// The algorithm used here is simply to keep the old table around, increase the
// max size by doubling it (thereby amortizing away the O(n) time), make a new 
// table with the size of max_size, and then copy the old table into the new 
// table one element at a time.  As I said, memcpy is reported to be faster 
// than a single element transfer method, though unfortunately, it is platform
// dependent in implementation, and further, it is not available on all systems.
void int_table::resize() {
  int * old_table = table;
  max_size *= 2;
  table = new int[max_size];
  for (int i = 0; i < size; i++) table[i] = old_table[i];
}

// Puke the table out, one element at a time.  This is the only reason that 
// we have the include of iostream.h
void int_table::print_out() {
  cout << endl;
  for (int i = 0; i < size; i++) cout << table[i] << endl;
  cout << endl;
}

