Copy constructor + assignment constructor of C + +

Keywords: Programming

Copy constructor + assignment constructor of C + +

As mentioned in the high quality C programming guide, there are four default constructors in an empty C + + class.

For example, as string

	AString();                              //Default constructor 
	~AString();                             //default destructor 
	AString(const AString &as);	            //Default Copy Constructor 
	AString& operator =(const AString &as); //Default assignment constructor

Why do programmers write functions when they can generate them automatically?

There are two reasons:

1. If the default parameterless constructor and default destructor are used, the chance of autonomous initialization and cleanup is abandoned.

2. "Default copy constructor" and "default assignment function" are implemented by "bit copy" instead of "value copy". If the class contains pointer variables, these two functions are bound to make mistakes. (the so-called deep copy and shallow copy problems).

for instance:

#include <iostream>
using namespace std;

class AString
{
public:
	AString();					 //Default constructor 
	~AString();					 //default destructor 	
public:
	AString (char* pstr);		//Parametrical constructor
	void print();
private :
	char * m_data;
};
AString::AString()
{
	cout<<"Execute parameterless constructor..."<<endl;
	m_data = NULL;
}
AString::~AString()
{
	if(NULL != m_data)
	{
		delete m_data;
		m_data = NULL;
		
	}
	cout<<"End of releasing resources"<<endl;
}

AString::AString(char *pstr)
{
	cout<<"Execute constructor with parameters..."<<endl;
	int nLen = strlen(pstr);
	m_data = new char[nLen + 1];
	memcpy(m_data,pstr,nLen);
	m_data[nLen]='\0';
}
void AString::print()
{
	if (NULL != m_data)
	{
		cout<<"Output data:"<<m_data<<endl;
	}
}

/*
	Problems in implementing copy constructor
*/
void ExampleFunc()
{
	AString str1("Hello world");
	AString str2 = str1; // Note that the copy constructor is called here	
	str2.print();
	str2 = str1;		//The assignment constructor is called here
	str2.print();
}
int main(int argc,char argv[])
{
	ExampleFunc();

	getchar();
	return 0;
}

An error occurred while running this program.

Output results:

Execute constructor with parameters...
Output data: Hello world
 Output data: Hello world
 End of releasing resources
 Pop up the error prompt box of Debug Assertion Failed!

Why is there a mistake?

Because at the end of the life cycle of ExampleFunc(), the destructors of str1 and str2 will be called to release resources, and str2 will release the resources occupied by m_data.

At this time, m_data in str1 has changed to "wild pointer", so when releasing the resources occupied by m_data in str1, an error will be reported.

Therefore, the copy constructor and the assignment constructor should be overridden at this time

Override copy constructor:

AString::AString(const AString &as)
{
	cout<<"Execute overloaded copy constructor"<<endl;
	if (this == &as)
	{
		return ;
	}
	//Allow the private member of the operation as
	int length = strlen(as.m_data);
	m_data = new char[length + 1];
	strcpy(m_data,as.m_data);
}

Override assignment constructor:

AString& AString::operator =(const AString &as)
{
	cout<<"Execute overloaded assignment function"<<endl;

	if (this == &as)
	{
		return *this;
	}
	delete m_data;

	int nLen = strlen(as.m_data);
	m_data = new char[nLen + 1];
	memcpy(m_data,as.m_data,nLen);
	m_data[nLen]='\0';
	return *this;
}

 

Posted by Clarkey Boy on Sat, 19 Oct 2019 13:40:52 -0700