Jump to content
  • Advertisement
Sign in to follow this  
ukdeveloper

Copy constructor never getting called

This topic is 3907 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

Hi, I'm having problems with both a copy constructor and an overloaded assignment operator, in that they're never getting called. Essentially, I've got a class called Potion. It does not contain any dynamically assigned memory, but is dynamically assigned itself inside main(). Here's Potion.h:
#pragma once
#include "item.h"
#include <string>

class Potion :
	public Item
{
public:
	Potion(void);
	virtual ~Potion(void);
	Potion(std::string description);
	Potion::Potion(const Potion& potion);
	// Overridden ToString() function for the potion
	void ToString(void);
	// Returns the amount of health this potion can provide
	int getHealth(void);

	// Overloaded assignment operator
	Potion operator=(const Potion& newPotion);
private:
	// The health that this potion provides
	int health;
public:
	// Sets the health this potion will provide
	void setHealth(int hVal);
};



Potion.cpp:
#include "Potion.h"

Potion::Potion(void)
: health(0)
{
}

Potion::~Potion(void)
{
}

Potion::Potion(std::string description)
{
	this->setDescription(description);
}

// Copy constructor
Potion::Potion(const Potion& potion)
{
	std::cout<<"DEBUG: Potion Copy constructor running!"<<std::endl;
	health = potion.health;
	description = potion.description;
}


Potion Potion::operator=(const Potion& newPotion)
{
	std::cout<<"DEBUG: Potion overloaded assignment running"<<std::endl;
	if (this == &newPotion){
		std::cout<<"DEBUG: Potion - this==&newPotion"<<std::endl;
		return(*this); }
	
	std::cout<<"DEBUG: Potion - doing assignments and returning"<<std::endl;
	health = newPotion.health;
	description = newPotion.description;

	return(*this);
}


// Overridden ToString() function for the potion
void Potion::ToString(void)
{
	std::cout<<"Health memory address: "<<&health<<std::endl;
	std::cout<<"Description memory address: "<<&description<<std::endl;
	std::cout<<"Potion: "<<getDescription()<<"("<<getHealth()<<")"<<std::endl;
}

// Returns the amount of health this potion can provide
int Potion::getHealth(void)
{
	return health;
}

// Sets the health this potion will provide
void Potion::setHealth(int hVal)
{
	health = hVal;
}



And main.cpp:
#include <iostream>
#include <cassert>
#include "Item.h"
#include "Potion.h"
#include "Armour.h"

int main(int argc, char *argv[])
{
	Potion* testPotion = new Potion();
	testPotion->setHealth(40);

	std::cout<<"Testing copy constructors..."<<std::endl<<std::endl;

	std::cout<<"-------------- POTION ----------------"<<std::endl;

	Potion* newPotion = new Potion();

	newPotion = testPotion; // Should call copy constructor/overloaded assignment operator??

	std::cout<<"Memory address of newPotion: "<<&newPotion<<std::endl;

	std::cout<<"Memory address of testPotion: "<<&testPotion<<std::endl<<std::endl;

	std::cout<<"testPotion: "<<std::endl;

	testPotion->ToString();

	std::cout<<std::endl;

	std::cout<<"newPotion: "<<std::endl;

	newPotion->ToString();

	std::cout<<std::endl;

	std::cout<<"-------------- END POTION --------------"<<std::endl;

	std::cout<<"\n\n\n\n\n"<<std::endl;

	return (0);
}



As you can see, I've got debug statements in the overloaded assignment operator and copy constructor code. I never see these messages so it's obvious to me neither are ever getting called, and the debugger isn't really helping me here. When I run this code, what I see is the two objects having different memory addresses ("Memory address of newPotion: " etc.), but the ToString() function shows that both objects, created separately, have the same memory addresses for the internal data fields? It's obviously doing some kind of shallow copy and ignoring the code I've got but I can't see why; this all looks fine based on what I have been taught in lectures. Either that or I've misunderstood what a copy constructor is supposed to do; my understanding is that it is supposed to create a direct copy of an object including the internal data, and store it in a different area of memory instead of a shallow copy which links back to the original area of memory. I'm stumped, what's going on? Thanks in advance, ukd. EDIT: I should add that, if I call delete on either of the Potion objects and then try to delete the other, I get a crash because the internals of both are pointing at the same section of memory and that's been deleted.

Share this post


Link to post
Share on other sites
Advertisement
newPotion and testPotion are POINTERS to potions. That is, they are the memory address of object instances. When you do &newPotion you are retrieving the memory address which is storing the object's memory address. Similarly, when you do newPotion = testPotion, you are merely making the newPotion point to the same object instance as testPotion.

In order to call the overloaded assignment operator, you need to do objectInstance = anotherObjectInstance. To get an object instance directly from a pointer, use the dereference operator *pointer. That is, *newPotion = *testPotion. This should call your overloaded assignment operator.

Share this post


Link to post
Share on other sites
I only glanced over the code, but here:
newPotion = testPotion;
You are assigning the value of one pointer to another pointer. What you want is:
*newPotion = *testPotion;


[Edit: What Guntharpo said.]

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

We are the game development community.

Whether you are an indie, hobbyist, AAA developer, or just trying to learn, GameDev.net is the place for you to learn, share, and connect with the games industry. Learn more About Us or sign up!

Sign me up!