Rıfat Tolga Kiran
Rıfat Tolga Kiran

Reputation: 245

copy constructor is triggered but how?

Here is my code:

#include <iostream>
#include <cstring>
using namespace std;

class someClass{
    char * data;
public:
    someClass(const char * s){
        data = new char[strlen(s)+1];
        strcpy(data,s);
        cout << "constructing.."<<endl;
    }

    someClass(const someClass &o){
        data = new char[strlen(o.data)];
        strcpy(data,o.data);
        cout << "copy construction" << endl;
    }

    ~someClass(){delete [] data; cout << "destructing..." << endl;}
    char * getValue(){return data;}
};

void showValue(someClass o){
    char * s;
    s = o.getValue();
    cout << s << endl;
}

int main(int argc, char ** argv){
    someClass str("Hello"), ptr("world");
    showValue(str);
    showValue(ptr);
}

and the output is:

constructing..
constructing..
copy construction
Hello
destructing...
copy construction
world
destructing...
destructing...
destructing...
  1. Now first two 'constructing..' are triggered as soon as we create the object in main() on line 1.

  2. showValue(str) runs and it triggers copy constructor for the word 'hello'. How? After creating and temporary object, it destructs itself when it's out of function.

  3. showValue(ptr) runs and it triggers copy constructor for the word 'world'. How? After creating and temporary object, it destructs itself when it's out of function.

  4. Lastly, in reverse order our str and ptr objects are being destroyed.

Why has copy ctor run? I didn't send a someClass object to a someClass object. Can you explain me the situation?

Upvotes: 2

Views: 269

Answers (2)

Jean-Emmanuel
Jean-Emmanuel

Reputation: 688

void showValue(someClass o){
    char * s;
    s = o.getValue();
    cout << s << endl;
}

this part of your cade invokes the copy constructor of someClass. If you want to get rid of it, you can change your class to:

 void showValue(const someClass & o){
        char * s;
        s = o.getValue();
        cout << s << endl;
    }

and change GetValue to:

 char * getValue() const {return data;} 

This is called passing by const-reference, as opposed to passing by value (what you were doing). When you pass by value, the function invokes the copy constructor of the class called.

The change on getValue() suggested is because the compiler wants to be sure that the call to getValue inside of showValue will not modify the member objects of the const element const someClass & o.

Upvotes: 2

Cory Kramer
Cory Kramer

Reputation: 117876

You are making copies when you call

void showValue(someClass o)

If you want to avoid copies, pass by reference

void showValue(someClass const& o)

In the first case o is a function-local copy of your someClass argument, that is destroyed at the end of the function.

Upvotes: 4

Related Questions