#include "list.h"

//Abstract data type for telephone directory object implemented
//as an array of entry objects.

//Imports: Abstract data type Entry

void List::Init()
//Creates an initially empty list.
//Pre : None.
//Post: List with zero elements is defined.
{
  Count = 0;
}

void List::ReadList()
//Reads data from a file into a list.
//Pre : Data file exists on disk.
//Post: Entries from data file are copied to list.
{
  int Next = 0;              //next subscript for new entry
  Entry InEntry;             //new entry
  char FileName[15];         //directory name of input file
  char InName[MaxSize];      //Name for new entry
  char InNumber[StrLength];  //Number for new entry
  ifstream Infile;           //internal file variable

  cout << "Enter the name of the telephone directory file:\n";
  cin >> FileName;
  Infile.open(FileName) ;    //open the data file
  if ((Infile) == NULL)      //check file existence
    {
     cout << "input file does not exist";
     exit(1);
    }

  while (!Infile.eof())
    {
     Infile >> InName;                  //read next entry
     Infile >> InNumber;
     InEntry.Init(InName, InNumber);
     Entries[Next] = InEntry;          //store entry in list
     Next++;                           //increment Next
    }

  Count=Next;                //save number of list entries
  Infile.close();            //close files
}

void List::Insert (Entry AnEntry, int &Success)
//Inserts entry into list.
//Pre : AnEntry is defined.
//Post: If the list was not full and AnEntry is not in list,
//      then AnEntry is the last entry in the list and Success
//      is 1; otherwise Success is 0.
{
  int PosEntry;

  PosEntry = Search(AnEntry);         //new entry?
  if ((PosEntry == -1) && (Count < (MaxEntry - 1)))
    {
      Success = True;
      Entries[Count] = AnEntry;    //insert new entry
      Count++;                     //update Count
    }
  else
    Success = False;
}

void List::Replace(Entry AnEntry, int &Success)
//Replaces the entry with the same key as AnEntry with AnEntry.
//Pre : AnEntry is defined.
//Post: Either list entry with same key as AnEntry has same
//      number and Success is 1 or Success is 0.
{
  int PosEntry;

  PosEntry = Search(AnEntry);
  if (PosEntry != -1)
    {
      Entries[PosEntry] = AnEntry;     //replace entry if found
      Success = True;
    }
  else
    Success = False;
}

void List::Remove(Entry AnEntry, int &Success)
//Removes entry with same key as AnEntyr from the list.
//Pre : AnEntry is defined.
//Post: If found the last list entry takes the place of AnEntry
//      in the list, Success is 1, and list Count is decremented;
//      otherwise Success is 0.
{
  int PosEntry;         //position of entry to remove

  PosEntry = Search(AnEntry);
  if (PosEntry != -1)
    {
      Count--;                             // decrement count
      Entries[PosEntry] = Entries[Count];  // copy last entry
      Success = True;
    }
  else
    Success = False;
}

int List::Search(Entry AnEntry)
//Searches list for position of AnEntry.
//Pre : AnEntry is defined.
//Post: Position of AnEntry returned as function value, if found;
//      otherwise -1 is returned.
{
  int Success;        //loop control flag
  int PosEntry;       //list position checked

  Success = False;    //AnEntry is not found
  PosEntry = 0;       //start with first position.

  while ((!Success) && (PosEntry < Count))
    {
      if (AnEntry.EqualTo(Entries[PosEntry]))
	Success = True;    //AnEntry is found
      else
	PosEntry++;        //advance to next entry
    }

  if (!Success)            //check for failed search
    PosEntry = -1;
  return(PosEntry);
}

int List::GetCount()
//Returns count of entries in list
//Pre : List is defined.
//Post: Returns count of entries.
{
  return(Count);
}

void List::GetEntry(Entry &AnEntry, int &Success)
//Retrieves the entry with the same key as AnEntry.
//Pre : AnEntry is defined.
//Post: AnEntry contains data of same element if Entries with
//      same key and Success is 1; otherwise Success is 0.
{
  int PosEntry;   //position of entry in list

  PosEntry = Search (AnEntry);            //find AnEntry
  if (PosEntry != -1)
    {
      AnEntry = Entries[PosEntry];        //return data
      Success = True;
    }
  else
    Success = False;
}

void List::Sort()
//Stub procedure for sorting list.
//Pre : List is defined.
//Post: List is sorted.
{
  cout << "Sort not implemented yet.\n";
}

void List::DisplayList()
//Displays the list.
//Pre : List is initialized.
//Post: Each list entry is displayed.
{
  Entry AnEntry;      //next entry
  int Next;           //next subcript

  for (Next = 0; Next < Count; ++Next)
    Entries[Next].DisplayEntry();
}
