
/*****************************************
* A basic grid class using std::vector
* Accessors: height(), width(), retrieve(n,m), print()
* Mutalators: insert(n,m,x), resize(n,m)
*
* Author: Phil Gunnewiek
 *****************************************/

#ifndef GRID_H
#define GRID_H

// Includes
#include <vector>
#include <stdexcept>

using std::vector;

class grid {
	private:
        int HEIGHT;
        int WIDTH;
        vector<vector<double> > array2D;

	public:
        // Constructors
        grid(int n, int m);
        ~grid();

        // Accessors
        int height();
        int width();
        double retrieve(int n, int m);
        void print();

        // Mutalators
        void insert(int n, int m, double x);
        void resize(int n, int m);
};

grid::grid(int n, int m){
    // Constructor
    HEIGHT = n;
    WIDTH = m;

    array2D.resize(HEIGHT);
    for (int i = 0; i < HEIGHT; ++i)
    {
        array2D[i].resize(WIDTH);
    }
}

grid::~grid() {
    // Destructor
}

int grid::height(){
    // Returns the height
    return HEIGHT;
}

int grid::width(){
    // Returns the width
    return WIDTH;
}

double grid::retrieve(int n, int m){
    // Returns the value at a particualr location
    if(n < HEIGHT && m < WIDTH)
    {
        return array2D[n][m];
    }
    else
    {
        throw std::out_of_range ("Invlaid retrieve coords");
    }
}

void grid::insert(int n, int m, double x){
    // Sets the value at a particualr location
    if(n < HEIGHT && m < WIDTH)
    {
        array2D[n][m] = x;
    }
    else
    {
        throw std::out_of_range ("Invlaid insert coords");
    }
}

void grid::resize(int n, int m){
    // Resizes the grid
    HEIGHT = n;
    WIDTH = m;

    array2D.resize(HEIGHT);
    for (int i = 0; i < HEIGHT; ++i)
    {
        array2D[i].resize(WIDTH);
    }
}


void grid::print(){
    // Prints out the grid on the console
    for(int i = 0; i < HEIGHT; i++)
    {
        for(int j = 0; j < WIDTH; j++)
        {
            std::cout << array2D[i][j] << " ";
        }
        std::cout << std::endl;
    }
}

#endif

