259 lines
9.2 KiB
C
259 lines
9.2 KiB
C
|
#pragma once
|
||
|
|
||
|
namespace BWTA
|
||
|
{
|
||
|
/**
|
||
|
* Template used for work with dynamically initialized array with dimension 2.
|
||
|
*/
|
||
|
template <class Type>
|
||
|
class RectangleArray
|
||
|
{
|
||
|
public :
|
||
|
/**
|
||
|
* Creates the array with the specified proportions.
|
||
|
* @param width Width of the new array.
|
||
|
* @param height Height of the new array.
|
||
|
*/
|
||
|
RectangleArray(unsigned int width = 1, unsigned int height = 1, Type* data = NULL);
|
||
|
/** Copy constructor */
|
||
|
RectangleArray(const RectangleArray<Type>& rectangleArray);
|
||
|
/** Destorys the array and deletes all content of array. */
|
||
|
~RectangleArray(void);
|
||
|
/**
|
||
|
* Gets the width of the array.
|
||
|
* @return width of the array.
|
||
|
*/
|
||
|
unsigned int getWidth(void) const;
|
||
|
/**
|
||
|
* Gets the height of the array.
|
||
|
* @return height of the array.
|
||
|
*/
|
||
|
unsigned int getHeight(void) const;
|
||
|
/**
|
||
|
* Gets item of the array on the specified position.
|
||
|
* @param x horizontal index of the array position.
|
||
|
* @param y vertical index of the array position.
|
||
|
* @return item on the specified position.
|
||
|
*/
|
||
|
Type getItem(unsigned int x, unsigned int y);
|
||
|
Type getItemSafe(unsigned int x, unsigned int y);
|
||
|
inline Type* operator[](int i) { return this->getColumn(i); }
|
||
|
inline Type const * const operator[](int i) const {return this->getColumn(i); }
|
||
|
/**
|
||
|
* Sets item of the array on the specified position.
|
||
|
* @param x horizontal index of the array position.
|
||
|
* @param y vertical index of the array position.
|
||
|
* @param item new value of the field.
|
||
|
*/
|
||
|
void setItem(unsigned int x, unsigned int y, Type *item);
|
||
|
void resize(unsigned int width, unsigned int height);
|
||
|
void printToFile(FILE* f);
|
||
|
void saveToFile(const std::string& fileName);
|
||
|
/** Sets all fields of the array to the specified value */
|
||
|
void setTo(const Type& value);
|
||
|
void setBorderTo(const Type& value);
|
||
|
private :
|
||
|
bool owner;
|
||
|
/** width of array */
|
||
|
unsigned int width;
|
||
|
/** height of array */
|
||
|
unsigned int height;
|
||
|
/** Array data, stored as linear array of size width*height */
|
||
|
Type *data;
|
||
|
/** Pointers to begins of lines*/
|
||
|
Type **columns;
|
||
|
/**
|
||
|
* Gets data item on the specified index
|
||
|
* @param index index of the data to be returned.
|
||
|
*/
|
||
|
Type getData(unsigned int index);
|
||
|
/**
|
||
|
* Gets the pointer in data to the beginning of line with the specified
|
||
|
* index.
|
||
|
* @param index index of the line.
|
||
|
*/
|
||
|
Type *getColumn(unsigned int index);
|
||
|
/**
|
||
|
* Gets the pointer in data to the beginning of line with the specified
|
||
|
* index.
|
||
|
* @param index index of the line.
|
||
|
*/
|
||
|
const Type *getColumn(unsigned int index) const;
|
||
|
/**
|
||
|
* Sets the width of the array.
|
||
|
* @param width New width of the array.
|
||
|
*/
|
||
|
void setWidth(unsigned int width);
|
||
|
/**
|
||
|
* Sets the height of the array.
|
||
|
* @param height New height of the array.
|
||
|
*/
|
||
|
void setHeight(unsigned int height);
|
||
|
};
|
||
|
//---------------------------------------------- CONSTRUCTOR -----------------------------------------------
|
||
|
template <class Type>
|
||
|
RectangleArray<Type>::RectangleArray(unsigned int width, unsigned int height, Type* data)
|
||
|
{
|
||
|
this->setWidth(width);
|
||
|
this->setHeight(height);
|
||
|
this->owner = (data == NULL);
|
||
|
if (this->owner)
|
||
|
this->data = new Type[this->getWidth()*this->getHeight()];
|
||
|
else
|
||
|
this->data = data;
|
||
|
|
||
|
columns = new Type*[this->getWidth()];
|
||
|
unsigned int i = 0;
|
||
|
for (unsigned int position = 0;i < width; i ++,position += height)
|
||
|
columns[i] = &this->data[position];
|
||
|
}
|
||
|
//---------------------------------------------- CONSTRUCTOR -----------------------------------------------
|
||
|
template <class Type>
|
||
|
RectangleArray<Type>::RectangleArray(const RectangleArray<Type>& rectangleArray)
|
||
|
:owner(true)
|
||
|
{
|
||
|
this->setWidth(rectangleArray.getWidth());
|
||
|
this->setHeight(rectangleArray.getHeight());
|
||
|
this->data = new Type[this->getWidth()*this->getHeight()];
|
||
|
columns = new Type*[this->getWidth()];
|
||
|
|
||
|
unsigned int i = 0;
|
||
|
for (unsigned int position = 0;i < width; i ++,position += height)
|
||
|
columns[i] = &data[position];
|
||
|
memcpy(this->data, rectangleArray.data, sizeof(Type)*this->getWidth()*this->getHeight());
|
||
|
}
|
||
|
//----------------------------------------------- DESTRUCTOR -----------------------------------------------
|
||
|
template <class Type>
|
||
|
RectangleArray<Type>::~RectangleArray(void)
|
||
|
{
|
||
|
delete [] columns;
|
||
|
if (this->owner)
|
||
|
delete [] data;
|
||
|
}
|
||
|
//----------------------------------------------- GET WIDTH ------------------------------------------------
|
||
|
template <class Type>
|
||
|
unsigned int RectangleArray<Type>::getWidth(void) const
|
||
|
{
|
||
|
return this->width;
|
||
|
}
|
||
|
//----------------------------------------------- SET WIDTH ------------------------------------------------
|
||
|
template <class Type>
|
||
|
void RectangleArray<Type>::setWidth(unsigned int width)
|
||
|
{
|
||
|
this->width = width;
|
||
|
}
|
||
|
//----------------------------------------------- GET HEIGHT -----------------------------------------------
|
||
|
template <class Type>
|
||
|
unsigned int RectangleArray<Type>::getHeight(void) const
|
||
|
{
|
||
|
return this->height;
|
||
|
}
|
||
|
//----------------------------------------------- SET HEIGHT -----------------------------------------------
|
||
|
template <class Type>
|
||
|
void RectangleArray<Type>::setHeight(unsigned int height)
|
||
|
{
|
||
|
this->height = height;
|
||
|
}
|
||
|
//------------------------------------------------ GET ITEM ------------------------------------------------
|
||
|
template <class Type>
|
||
|
Type RectangleArray<Type>::getItem(unsigned int x, unsigned int y)
|
||
|
{
|
||
|
return this->getColumn(x)[y];
|
||
|
}
|
||
|
//------------------------------------------------ GET ITEM ------------------------------------------------
|
||
|
template <class Type>
|
||
|
Type RectangleArray<Type>::getItemSafe(unsigned int x, unsigned int y)
|
||
|
{
|
||
|
if (x<0 || y<0 || x>=this->width || y>=this->height)
|
||
|
{
|
||
|
return (Type)NULL;
|
||
|
}
|
||
|
return this->getColumn(x)[y];
|
||
|
}
|
||
|
//------------------------------------------------ SET ITEM ------------------------------------------------
|
||
|
template <class Type>
|
||
|
void RectangleArray<Type>::setItem(unsigned int x, unsigned int y, Type* item)
|
||
|
{
|
||
|
this->getColumn(x)[y] = item;
|
||
|
}
|
||
|
//------------------------------------------------ GET LINE ------------------------------------------------
|
||
|
template <class Type>
|
||
|
Type* RectangleArray<Type>::getColumn(unsigned int index)
|
||
|
{
|
||
|
return columns[index];
|
||
|
}
|
||
|
//------------------------------------------------ GET LINE ------------------------------------------------
|
||
|
template <class Type>
|
||
|
const Type* RectangleArray<Type>::getColumn(unsigned int index) const
|
||
|
{
|
||
|
return columns[index];
|
||
|
}
|
||
|
//------------------------------------------------- RESIZE -------------------------------------------------
|
||
|
template <class Type>
|
||
|
void RectangleArray<Type>::resize(unsigned int width, unsigned int height)
|
||
|
{
|
||
|
if (this->getWidth() == width &&
|
||
|
this->getHeight() == height)
|
||
|
return;
|
||
|
|
||
|
delete [] this->columns;
|
||
|
delete [] this->data;
|
||
|
|
||
|
this->setWidth(width);
|
||
|
this->setHeight(height);
|
||
|
|
||
|
this->data = new Type[this->width * this->height];
|
||
|
|
||
|
this->columns = new Type*[this->width];
|
||
|
unsigned int i = 0;
|
||
|
for (unsigned int position = 0;i < this->width; i ++,position += this->height)
|
||
|
columns[i] = &data[position];
|
||
|
}
|
||
|
//--------------------------------------------- PRINT TO FILE ----------------------------------------------
|
||
|
template <class Type>
|
||
|
void RectangleArray<Type>::printToFile(FILE* f)
|
||
|
{
|
||
|
for (unsigned int y = 0; y < this->getHeight(); y++)
|
||
|
{
|
||
|
for (unsigned int x = 0; x < this->getWidth(); x++)
|
||
|
{
|
||
|
char ch = this->getColumn(x)[y];
|
||
|
fprintf_s(f, "%c", ch);
|
||
|
}
|
||
|
fprintf_s(f, "\n");
|
||
|
}
|
||
|
}
|
||
|
//---------------------------------------------- SAVE TO FILE ----------------------------------------------
|
||
|
template <class Type>
|
||
|
void RectangleArray<Type>::saveToFile(const std::string& fileName)
|
||
|
{
|
||
|
FILE* f = fopen(fileName.c_str(), "wt");
|
||
|
if (!f)
|
||
|
exit(1);
|
||
|
this->printToFile(f);
|
||
|
fclose(f);
|
||
|
}
|
||
|
//------------------------------------------------- SET TO -------------------------------------------------
|
||
|
template <class Type>
|
||
|
void RectangleArray<Type>::setTo(const Type& value)
|
||
|
{
|
||
|
for (unsigned int i = 0; i < this->getWidth()*this->getHeight(); i++)
|
||
|
this->data[i] = value;
|
||
|
}
|
||
|
//--------------------------------------------- SET BORDER TO ----------------------------------------------
|
||
|
template <class Type>
|
||
|
void RectangleArray<Type>::setBorderTo(const Type& value)
|
||
|
{
|
||
|
for (unsigned int i = 0; i < this->width; i++)
|
||
|
{
|
||
|
this->getColumn(i)[0] = value;
|
||
|
this->getColumn(i)[this->height - 1] = value;
|
||
|
}
|
||
|
for (unsigned int i = 0; i < this->height; i++)
|
||
|
{
|
||
|
this->getColumn(0)[i] = value;
|
||
|
this->getColumn(this->width - 1)[i] = value;
|
||
|
}
|
||
|
}
|
||
|
//----------------------------------------------------------------------------------------------------------
|
||
|
}
|