Debug Assertion failed on making copy constructor - c++

I am trying to make a copy constructor because I have a pointer in my class. However, I got runtime error "Debug Assertion failed" and I do not know what to do. I have two classses, MyMatrix and MyImage. I want to write a copy constructor for MyImage, therefore I also write one for MyMatrix.
class MyMatrix{
private:
unsigned _width, _height;
unsigned char *_data;
public:
MyMatrix(MyMatrix &other);
}
MyMatrix::MyMatrix(MyMatrix &other) {
_width = other._width;
_height = other._height;
_data = new unsigned char[_width*_height];
memcpy(_data, other._data, _width*_height*sizeof(unsigned char));
}
class MyImage {
public:
int _width;
int _height;
MyMatrix _Y; //gray level
}
MyImage::MyImage(MyImage &other) {
_width = other._width;
_height = other._height;
_Y = MyMatrix(other._Y);
}
int main(){
char *filename = "hw1_images/p1/house.raw"; //some raw image
int width = 512;
int height = 512;
//read the image
MyImage inputImage(filename, width, height, fileMode::CFA);
//copy the image
MyImage test(inputImage);
return 0;
}
I got error even if I comment the memcry(). If I use std::cout to display the value of my copy, it is alway 221. Please help me with it. Thank you.

You are writing _Y = MyMatrix(other._Y);, I expect that you have defined the assignement operator for your Matrix class : MyMatrix & operator(const MyMatrix & other); otherwise the compiler will create a default one for you that just copy your attributes, meaning your pointer will be copied, not the content.
And, as I see that you can manipulate an important size of data and if you have c++11 enabled, I would definitely look at the copy swap idiom : What is the copy-and-swap idiom?

If its just matter of crash then you may do something like below.
class MyMatrix{
private:
unsigned _width, _height;
unsigned char *_data;
public:
MyMatrix(){
_width = 2;
_height = 3;
_data = new unsigned char[sizeof(unsigned char)];
}
MyMatrix(MyMatrix &other);
};
MyMatrix::MyMatrix(MyMatrix &other) {
_width = other._width;
_height = other._height;
_data = new unsigned char[(_width*_height) + 1];
memcpy(_data, other._data, _width*_height*sizeof(unsigned char));
}

Related

How to write a Copy Constructor for a Sprite?

My code crashes and I think I need to deep copy p_Texture and sprite.
I know how to make a deep copy of a pointer to an array but I'm not sure sure how to do this. Here I wrote this destructor:
class Sprite
{
private:
IDirect3DTexture9* p_Texture;
LPD3DXSPRITE sprite;
D3DXVECTOR3 imagepos;
int m_posX;
int m_posY;
int m_posZ;
int m_width, m_heigth;
public:
Sprite()
{
}
~Sprite()
{
if (sprite)
{
sprite->Release();
sprite = 0;
}
if (p_Texture)
{
p_Texture->Release();
p_Texture = 0;
}
}
Sprite(std::string path, int posX, int posY, int posZ, int width, int heigth)
{
m_posX = posX;
m_posY = posY;
m_posZ = posZ;
m_width = width;
m_heigth = heigth;
imagepos.x = posX;
imagepos.y = posY;
imagepos.z = posZ;
D3DXCreateTextureFromFileEx(p_Device, path.c_str(), m_width, m_heigth, D3DX_DEFAULT, 0, D3DFMT_UNKNOWN, D3DPOOL_DEFAULT,
D3DX_DEFAULT, D3DX_DEFAULT, 0, NULL, NULL, &p_Texture)
D3DXCreateSprite(p_Device, &sprite)
}
void draw()
{
sprite->Begin(D3DXSPRITE_ALPHABLEND);
sprite->Draw(p_Texture, NULL, NULL, &imagepos, 0xFFFFFFFF);
sprite->End();
}
void incPosX(int x) {imagepos.x += x;}
void decPosX(int x) {imagepos.x -= x;}
void incPosY(int x) {imagepos.y += x;}
void decPosY(int x) {imagepos.y -= x;}
float getPosX() { return imagepos.x; }
float getPosY() { return imagepos.y; }
};
However, it crashes because of copying it in the code.
The syntax for a copy constructor is:
Sprite::Sprite(Sprite& other)
Then you just copy what you need from other to the this pointer.
Your code as it is right now has an implicit copy and move constructor. Both copy everything by value.
The reason for your crashing is likely because somewhere a copy or move of a Sprite is made, and when it expires the destructor is called. This frees some resources which you later attempt to use.
You can find such places by deleteing your copy and move constructors, and seeing where the compiler complains. The syntax follows:
Sprite::Sprite(sprite& other) = delete; // no copy constructor
Sprite::Sprite(Sprite&& other) = delete; // no move constructor

Returning 2D array pointer from class

I've got a class called Engine which holds and returns a buffer like so:
template <int width, int height, int meshSize>
class Engine {
public:
byte buffers[2][width][height];
byte fBuffer = 0;
byte** getBuffer() {
return buffers[fBuffer];
};
}
and I want to loop through the values in my main, but I can't seem to get it working..
byte* buff;
// main
buff = engine->getBuffer();
for (int x = 0; x < 320; x++) {
for (int y = 0; y < 320; y++) {
if (buff[x][y] != NULL) {
Serial.println(buff[x][y]);
}
// lcd.drawPixel(x, y, RGB(buff[x][y], buff[x][y], buff[x][y]));
}
}
What combination of asterisk and/or parenthesis will work?
You should return a reference to your array, rather than a pointer. I also recommend providing a const overload of getBuffer for read-only operations.
template <int width, int height, int meshSize>
class Engine {
public:
using BufferType = byte[width][height];
BufferType const& getBuffer() const {
return buffers[fBuffer];
};
BufferType& getBuffer() {
return buffers[fBuffer];
};
private:
BufferType buffers[2];
byte fBuffer = 0;
};
You can use auto to deduce this type when calling getBuffer for brevity:
auto& buff = engine->getBuffer(); // reference to the buffer

Declaring object onto the stack in class definition vs in constructor

When I declare the "Level" object in the "LevelEditor" class definition like so, everything works fine:
class LevelEditor
{
public:
LevelEditor(int w, int h, Shader* shader)
{
width = w;
height = h;
for (int y = 0; y < height; y++)
{
for (int x = 0; x < width; x++)
{
tile[x][y] = new WorldSprite(tileWidth * x, tileHeight * y, tileWidth, tileHeight, shader);
}
}
}
//...
private:
//...
Level level = Level(50, 50);
WorldSprite* tile[300][300];
//tile characteristics
int tileWidth = 50;
int tileHeight = 50;
//flags
bool editing = true;
};
But when I declare the "Level" object in the "LevelEditor" constructor like so, I get a stack overflow:
class LevelEditor
{
public:
LevelEditor(int w, int h, Shader* shader)
{
width = w;
height = h;
for (int y = 0; y < height; y++)
{
for (int x = 0; x < width; x++)
{
tile[x][y] = new WorldSprite(tileWidth * x, tileHeight * y, tileWidth, tileHeight, shader);
}
}
//NOTE: width and height both equal 50
level = Level(width, height);
}
//...
private:
//...
Level level;
WorldSprite* tile[300][300];
//tile characteristics
int tileWidth = 50;
int tileHeight = 50;
//flags
bool editing = true;
};
This makes me wonder what the difference is between declaring a variable in the class definition and in the constructor is besides the fact of the time of defining the variable. Any idea of what the cause could be? and how I could declare the "Level" object in the constructor without having to put anything on the heap?
EDIT:
"Level" class definition in case it is helpful:
class Level
{
public:
Level(int w, int h)
{
Worldwidth = w;
Worldheight = h;
for (unsigned int y = 0; y < Worldheight; y++)
{
for (unsigned int x = 0; x < Worldwidth; x++)
{
grid[x][y] = -1;
}
}
}
Level(){}
~Level()
{
for (auto it = tiles.begin(); it != tiles.end(); ++it)
{
delete *it;
}
tiles.clear();
for (auto it = entities.begin(); it != entities.end(); ++it)
{
delete *it;
}
entities.clear();
}
void draw()
{
}
private:
int Worldwidth;
int Worldheight;
int grid[300][300];
std::vector<Tile*> tiles;
std::vector<Entity*> entities;
};
There are several issues with your code. I will try to address the stack overflow error. The other issue is that your Level class is not safely copyable -- that can be taken care of by utilizing smart pointers such as std::unique_ptr and std::shared_ptr.
First, your classes use 300 x 300 arrays of T, in one case, T is a WorldSprite* the other is int. Arrays this size declared as members will balloon the size of each of your objects that contain them to hundreds of kilobytes in size. This will at some point take a toll on the stack.
So you should remove these definitions, and instead use std::vector.
#include <vector>
class LevelEditor
{
public:
LevelEditor(int w, int h, Shader* shader) :
tile(w,std::vector<WorldSprite*>(h))
editing(true), width(w), height(h)
{
for (int y = 0; y < height; y++)
{
for (int x = 0; x < width; x++)
tile[x][y] = new WorldSprite(tileWidth * x, tileHeight * y,
tileWidth, tileHeight, shader);
}
level = Level(width, height);
}
private:
Level level;
int width, height;
std::vector<std::vector<WorldSprite*>> tile;
bool editing;
};
Here is the Level class with the same type of changes:
#include <vector>
//...
class Level
{
public:
Level(int w, int h) : Worldwidth(w), Worldheight(h),
grid(300, std::vector<int>(300, -1))
{}
Level(){}
~Level()
{
for (auto it = tiles.begin(); it != tiles.end(); ++it)
{
delete *it;
}
tiles.clear();
for (auto it = entities.begin(); it != entities.end(); ++it)
{
delete *it;
}
entities.clear();
}
void draw()
{
}
private:
int Worldwidth;
int Worldheight;
std::vector<std::vector<int> >grid;
std::vector<Tile*> tiles;
std::vector<Entity*> entities;
};
Note that the vector replaces the array, and it will use heap memory to initialize. In the Level class, we initialize the vector and set all the entries to -1 in one single call of the vector's constructor.
The reason why this will not hike the size of your objects to very high amounts is that vector will create its data on the heap (unless you have some sort of custom allocator that gets the memory from another source). Thus the size of your classes will be reasonable (probably less than 100 bytes).
The other issue is that your Level class is not safely copyable (neither is the LevelEditor, but I will leave it alone, as the same set of changes can be done).
The problem will be this line:
level = Level(width, height);
The problem with this line is that the assignment operator will be called and the copy constructor may be called. If you look at your Level class, it has a destructor that removes all the pointers from the vectors that contain pointers. This will be disastrous if you copy Level objects, since you will be destroying all of your data due to temporaries being destroyed.
If there is no sense of which Level actually owns the pointers, and it comes down to "whoever is the last man standing is the owner", and you will actually be sharing pointers between Level instances (that's why it's called shared_ptr) then you can use this solution:
#include <vector>
#include <memory>
//...
class Level
{
public:
Level(int w, int h) : Worldwidth(w), Worldheight(h),
grid(300, std::vector<int>(300, -1))
{}
Level(){}
void draw()
{
}
private:
int Worldwidth;
int Worldheight;
std::vector<std::vector<int>> grid;
std::vector<std::shared_ptr<Tile>> tiles;
std::vector<std::shared_ptr<Entity>> entities;
};
Note how there is no destructor code -- there need not be any. The deletion is all done by the shared_ptr, so there is no work for you to do -- everything is managed. What will happen is that the last Level that gets destroyed that you shared the pointers with will do the actual deletion. So when this line is done
level = Level(width, height);
the copying of the Level objects bumps up and down the internal shared_ptr's reference count, leaving you with a reference count of 1 (that is the final level on the left-hand side of the = sign).
See here for usage of std::shared_ptr: http://en.cppreference.com/w/cpp/memory/shared_ptr
Please note that you may want to use std::unique_ptr if ownership is an issue. I suggest you search SO for usages of std::unique_ptr. I showed you std::shared_ptr since it is the most straightforward at this point (but again, may not suit all your needs - YMMV).

Destructor and overloaded= operator for Image class

I am new in C++. I have a problem with Image Processing. What I am trying to do is to write my class Image, which has as private variables horizontal and vertical sizes of an image and data for each pixel (grayscale, just 2D array of floats). I also wrote basic functions within the class: getPixel,SetPixel, GetSize, GetData (returns 2D array of data).
My question is: I read, that for best performance I have to write a destructor function and overloaded "=" operator at least.
1) Can someone explain why I really need it (as long as this version working more or less).
2) Can you write destructor and "=" operator for me? I guess, it is not difficult for experts, I tried once but with my destructor I got memory errors: Error _BLOCK_TYPE_IS_VALID(pHead->nBlockUse);
Update: Even now, without defining "=" operator, I can use it in my main function. If, say, I had Image img1 of size (1x1) and img2 of size (2x2), I can write img1=img2, and it works!
Update2: After I tried to implement simple destructor (delete [] pix) the error "_BLOCK_TYPE_IS_VALID" appeared
struct Pixel
{
float p;
};
struct size
{
int x;
int y;
};
class Image {
private:
int _x, _y;
Pixel *pix;
public:
Image(int x, int y){
pix = new Pixel[x * y];
_x = x;
_y = y;
}
float getPixel(int i, int j) {
return pix[i * _y + j].p;
}
void setPixel(int i, int j, Pixel val)
{
pix[i * _y + j].p = val.p;
}
size GetSize(){
size a;
a.x = _x;
a.y = _y;
return a;
}
Pixel **GetData(){
Pixel **a=0;
a = new Pixel*[_x];
for (int i = 0; i < _x; i++){
a[i] = new Pixel[_y];
for (int j = 0; j < _y; j++){
a[i][j] = pix[i*_y + j];
}
}
return a;
}
};
UPDDATE 3: I tried to implement everything from rule of three. I added:
~Image()
{
delete[] pix;
}
Image(const Image& that)
{
pix = new Pixel[that._x*that._y];
pix = that.pix;
_x = that._x;
_y = that._y;
}
Image& operator=(const Image& that)
{
if (this != &that)
{
delete[] pix;
pix = new Pixel[that._x*that._y];
pix = that.pix;
_x = that._x;
_y = that._y;
}
return *this;
}
Still got memory error: "_BLOCK_TYPE_IS_VALID..."
You asked:
1) Can someone explain why I really need it (as long as this version working more or less).
You are allocating memory for pix in the constructor. You need to implement a destructor that deallocates the memory. I don't see one implemented in your class.
~Image()
{
delete [] pix;
}
As soon as you add code in the destructor for releasing resources that were acquired by the class at some point in its life time, The Rule of Three comes into play and you'll have to implement the copy constructor and assignment operator for a bug free code.
The assignment operator will look something like:
Image& operator=(Image const& rhs) {
// Don't do anything for self assignment, such as a = a;
if ( this != &rhs )
{
delete [] pix;
_x = rhs._x;
_y = rhs._y;
pix = new Pixel[_x * _y];
for ( int i = 0; i < _x*_y; ++i )
{
pix[i] = rhs.pix[i]
}
}
return *this;
}
1) Can someone explain why I really need it (as long as this version working more or less).
Is already answered here: https://stackoverflow.com/a/4172724/2642059
The segment that pertains to you is:
Most of the time, you do not need to manage a resource yourself, because an existing class such as std::string already does it for you. Just compare the simple code using a std::string member to the convoluted and error-prone alternative using a char* and you should be convinced. As long as you stay away from raw pointer members, the rule of three is unlikely to concern your own code.
As a new C++ coder the best thing I can do for you is steer you away from raw pointers.
2) Can you write destructor and "=" operator for me? I guess, it is not difficult for experts, I tried once but with my destructor I got memory errors: Error _BLOCK_TYPE_IS_VALID(pHead->nBlockUse);
R Sahu's answer does a good job of this. But I'd advise you to get rid of your raw pointer instead, so I'll show you how to do that:
struct Pixel
{
Pixel() : p(0.0f) {} // Create a default constructor for Pixel so it can be used in a vector
float p;
};
class Image {
private:
int _x, _y;
std::vector<Pixel> pix; // This is your new array
public:
Image(int x, int y) :
pix(x * y) // This is called the constructor initializer list and that's where you construct member objects.
{
_x = x;
_y = y;
}
float getPixel(int i, int j) {
return pix[i * _y + j].p;
}
void setPixel(int i, int j, Pixel val)
{
pix[i * _y + j].p = val.p;
}
size GetSize(){
size a;
a.x = _x;
a.y = _y;
return a;
}
const Pixel* GetData(){ // We're going to pass back the vector's internal array here, but you should probably just return a const vector
return pix.data(); // We're returning this as read only data for convenience any modification to the data should be done through the Image class
}
};

Class of dynamic array

I've been working on a C++ exercise and I was unable to figure out how to do it correctly, let me explain it:
I made this class based on the 1st question of the exercise
class cylinder
{
private:
float height;
float radius;
char * label;
public:
cylinder(float, float, char *);
cylinder();
cylinder(const cylinder &);
~cylinder();
};
The 2nd question was:
Create a new class "form3D" contain cylinders (dynamic array of cylinder)
How to make a default constructor & constructor with parameters?
This is what I did:
class forme3d
{
cylinder * tab;
int tabsize;
public:
forme3d();
forme3d(cylinder * , int);
~forme3d();
};
forme3d::forme3d(cylindre * c, int t)
{
cylindre * tab = new cylindre[t];
for (int i = 0; i < t; ++i)
{
tab[i] = c[i];
}
}
This cause an error about "operator=" not defined for this line "tab[i] = c[i];"