I ran this example:
#include <cstdlib>
#include <iostream>
#include <istream>
#include <ostream>
using namespace std;
class Weight {
int k;
public:
Weight(int kilos = 0)
:k(kilos) {}
Weight(const Weight& w)
: k(w.k) {cout << "WCC\n";}
friend Weight operator+(const Weight& a, const Weight& b);
Weight& operator=(const Weight & w) {
this->k = w.k;
return *this;
}
friend ostream& operator<<(ostream&, const Weight&);
};
Weight operator+(const Weight& a, const Weight& b) {
cout << "FP\n";
int newkg = a.k + b.k;
return Weight(newkg);
}
ostream& operator<<(ostream& out, const Weight& w) {
out << w.k << " KGs";
return out;
}
class Container{
Weight w;
static Weight totalW;
static int count;
public:
Container(){++count;}
~Container(){cout << "CD\n";}
Container& add(Weight weight) {
this->w = this->w + weight;
totalW = totalW + weight;
cout << "Just added a new item that weighs " << weight << endl;
return *this;
}
static void print() {
cout << "We have " << count << " Containers with a total weight "
<< totalW << endl;
}
friend ostream& operator<<(ostream&, const Container&);
};
Weight Container::totalW;
int Container::count = 0;
ostream& operator<<(ostream& out, const Container& c){
out << "This container's " << c.w;
return out;
}
int main(int argc, char** argv) {
Container c1;
Weight *w1 = new Weight(1);
Weight *w2 = new Weight(2);
Weight *w3 = new Weight(3);
cout << "Adding items to container...\n";
c1.add(*w1).add(*w2).add(*w3);
cout << c1 << endl;
Container::print();
return 0;
}
And I got this output:
Adding items to container...
WCC
WCC
WCC
FP
FP
Just added a new item that weighs 1 KGs
FP
FP
Just added a new item that weighs 2 KGs
FP
FP
Just added a new item that weighs 3 KGs
This container's 6 KGs
We have 1 Containers with a total weight 6 KGs
CD
You can see that the copy constructor for the Weight class was called three times (Output lines 2-4) before any of the cascaded functions was called. I always thought that the left most function call will be performed before any copy constructor is called up to setup the second function call.
To be more specific, I thought this what should have happened: WCC -> c1.add(*w1) -> WCC -> .add(*w2) -> WCC -> .add(*w3).
I thought this was necessary because the function argument will be stored in the function's stack frame. So, a stack frame needs to be setup before the copy constructor for the argument is called. Apparently, I am mistaken.
This makes me think that function arguments are store somewhere else other than the stack frame. So, where?
Do not mind the horrific coding style. This, obviously, is not meant to be in production code.
Aucun commentaire:
Enregistrer un commentaire