#include "vector.h"


//Helper/Admin functions
void vector::destroy(){	
	if(capacity( )){
		if(capacity( )==1) delete InnerArray;
		else delete[] InnerArray;
	}
	this->m_size = 0;
	this->m_filled_in = 0;
	InnerArray = NULL;
}
void vector::allocate( size_type initialSize ){
	if(initialSize > max_size()) throw "Some Exception";
	if(initialSize){
		if(initialSize == 1) InnerArray = new char;
		else InnerArray = new char[initialSize];
	}
	this->m_size = initialSize;
	this->m_filled_in = 0;
}

//Construction/Destruction
vector::vector(size_type initialSize):m_size(initialSize),m_filled_in(0){
	allocate(this->m_size);		
}

vector::vector(const vector& refVec){
	allocate(refVec.size( ));
	for(int i=0; i<refVec.size( ); i++)
		push_back(refVec.InnerArray[i]);
}
vector::~vector(void){	
	destroy();
}

void vector::resize(int n, char Default){
	//First do some verifications
    if((n > max_size()) || (n < 0))
		throw "some exception that says that the argument is bad";
	
	int old_m_filled_in = m_filled_in;
	char* NewArray = new char[n];
    int i=0;
    for(i; (i < m_filled_in && i < n); i++)
		NewArray[i] =  InnerArray[i]; 
	while(i < n) {
		NewArray[i] = Default;
		i++;
   }
   destroy();
   InnerArray = NewArray;
   m_size = n;
   m_filled_in = old_m_filled_in;
   if(size( ) > capacity( )) m_filled_in = capacity( );
}


/*Operator overload, class 4*/
bool vector::operator==(const vector& vec) const{
	if(size( ) != vec.size( )) return false;
		for(int i=0; i<size( ); i++)
			if (vec.InnerArray[i]!=InnerArray[i]) return false;
	return true;
}
void vector::push_back(const char& Elt){ 
             //Back Insertion Sequence
             //Inserts a new element at the end.
                    if(max_size() == m_filled_in){
                       throw "some exception that says the vector is at its max";
                    }
                    if(m_filled_in < capacity( )){ 
                          InnerArray[m_filled_in] = Elt;
                          m_filled_in++;
                          return;
                    }
                    size_type NewSize =
                              (capacity( )+ m_inc_size < max_size())?capacity( )+ m_inc_size:max_size();
                    resize(NewSize);
                    return push_back(Elt);
                    };

vector::reference vector::operator [](size_type n){
	if((n >= size( )) || (n < 0)) throw "outta bound";
	return InnerArray[n];
}
//Assignment operator
const vector& vector::operator=(const vector& vec){
	destroy ( );
	allocate(vec.size( ));
	for(int i=0; i<vec.size( ); i++)
		this->push_back(vec.InnerArray[i]);
	return *this;	
}