2

I have a below code. Every time Constructor is called, I increase a counter and the counter is decreased every time Destructor is called. After instantiating three class objects, I tried printing out the counter value. Then I tried printing out the counter value again after deleting one of the objects. The expected values were 4 and 3, but instead I get 2 and 1.

I actually tried printing out something within the Constructor and Destructor to observe how many times they were actually called, but surprisingly Destructor was called several times in addition to the time when I called "delete object". Is it because the Destructor is called automatically? If so, is there any way to turn the feature off to test my code?

** The code originally has Add and Mult functions in the class, but I omitted here because the details of the functions seem irrelevant here.

#include <iostream> 
using namespace std; 

class Complex{ 
  private: 
  double x, y; 
  static int count; 

Complex Add(Complex como) 
{ 
   Complex t; 
   t.x=x+como.x; 
   t.y=y+como.y; 
   return t; 
} 
Complex Mul(Complex como) 
{ 
   Complex t; 
   t.x=(x*como.x)-(y*como.y); 
   t.y=(y*como.x)+(x*como.y); 
   return t; 
 } 
public: 
   Complex(double a=0, double b=0) : x(a), y(b) {count++;} 
  ~Complex() {count--;} 
  void Print() {cout << "(" << x << ", " << y << ")" << endl;} 
  static int GetCount() {return count;}
}; 

int Complex::count=0; 



int main() 
{ 
   Complex com1(1.0, 2.0), com2(3.0, 4.0); 
  Complex com3; 

  com1.Print(); cout << endl; 
  com2.Print(); cout << endl; 

  com3 = com1.Add(com2); com3.Print(); cout << endl;

  Complex *pcom4 = new Complex; 
  *pcom4 = com1.Mul(com2); pcom4->Print(); cout << endl;

  cout << "#complex numbers = " << com1.GetCount() << endl; 
  delete pcom4; 
  cout << "#complex numbers = " << com1.GetCount() << endl; 
  return 0;
} 
pandagrammer
  • 841
  • 2
  • 12
  • 24

2 Answers2

4

In C++ you can construct objects in three ways:

  1. using the "constructor"
  2. using the "copy constructor"
  3. using the "move constructor"

If don't define them the compiler will automatically write the code for you (unless you stop it from doing that explicitly).

Your method Mul and Add are accepting the other complex number by value and this means that a copy constructor call will be used to copy the argument of the call. The automatic synthesized copy constructor doesn't increment the counter.

6502
  • 112,025
  • 15
  • 165
  • 265
2

Your methods are taking Complex objects as parameters (not references to existing objects), so new objects are being created for each call and are destroyed at the end of the call.

John3136
  • 28,809
  • 4
  • 51
  • 69
  • Wrong. A default ("no args") constructor is only generated if there is no user-declared constructor at all. See http://stackoverflow.com/a/4944131/2192139 What's being compiler-generated here is the copy constructor, which takes an argument. – Geier Apr 14 '14 at 05:55
  • 1
    @Geier Fair enough. I don't have the language spec on me. So what is happening on line `Complex com3;`? – John3136 Apr 14 '14 at 05:57
  • 1
    There *is* a no-args constructor. It just happens to be the one with args that fully-populate with default parameters. What is *not* incrementing `count` is the implicit *copy-constructor*, which is fired by the param-inputs, but the same *destructor* (duh) is fired in *all* cases (copy-constructed or otherwise). – WhozCraig Apr 14 '14 at 05:58
  • @WhozCraig Got it - I didn't even notice the default parameters ;-) – John3136 Apr 14 '14 at 05:59