Static Members in C++ Template Class

We generally use static members in C++ class to maintain something that is not object specific, rather class specific. For example, if we want to maintain a counter about how many objects are created from a class, we keep a static counter in the class. In the class constructor, we increment the counter and we decrement that in desctructor. But handling static members in template class is little bit tricky.

We have simple template class like this.

template <typename T>
class MyClass {
public:
    MyClass(T val) {
        val_ = val;
    }
    
    void print() {
        std::cout << "Value: " << val_ << std::endl;
    }
private:
    T val_;
};

Now if we want to maintain how many objects are created out of this class, we can have a static counter in the class.

#include <iostream>
#include <cstdlib>

template <typename T>
class MyClass {
public:
    MyClass(T val) {
        val_ = val;
        object_count++;
    }
    
    ~MyClass() {
        object_count--;
    }
    
    void print() {
        std::cout << "Value: " << val_ << std::endl;
    }
    
static unsigned int object_count;
static void printObjectCount() {
    std::cout << "Object count: " << object_count << std::endl;
}
    
private:
    T val_;
};

template <typename T>
unsigned int MyClass<T>::object_count = 0;

Here the static counter, object_count, maintains the number of objects. We have another static function, printObjectCount(), to print the counter.

Now consider this code.

int main()
{
    MyClass<int> i1(4);
    MyClass<int> i2(5);
    MyClass<int> i3(7);
    
    MyClass<int>::printObjectCount();
}

Here the printObjectCount() function will print object count 3 as the value of object_count is 3. So far so good. Now consider another code snippet.

int main()
{
    MyClass<int> i1(4);
    MyClass<int> i2(5);
    MyClass<float> f1(0.5);
    MyClass<std::string> s1("string1");
    MyClass<std::string> s2("string2");
    MyClass<std::string> s3("string3");
    
    MyClass<int>::printObjectCount();
    MyClass<float>::printObjectCount();
    MyClass<std::string>::printObjectCount();
}

Here we created 6 objects. We can think that the value of object_count would be 6. The output of the program is like this.

Object count: 2
Object count: 1
Object count: 3

So here the program maintains three different object_count variables, one for each data type used. This might appear strange. Why to maintain multiple static variables when the class is one and static variables are class specific.

Because the assumption that we have only class is not true. Template class is basically an instruction to the compile to create one class for each data type used. In our example, we used 3 data types (int, float and string). So the compiler created 3 classes. As a result it maintains three different static variables.

Is there any way to maintain object count irrespective of the data type?

Yes, we can do that also. For that we need to have another non-template class where we’ll have the static variables and functions. The template class will derive that class. Here is the example.

#include <iostream>
#include <cstdlib>
#include <string>

class MyClassBase {
    public:
    MyClassBase() {
        object_count++;
    }
    
    ~MyClassBase() {
        object_count--;
    }
    
    static unsigned int object_count;
    static void printObjectCount() {
        std::cout << "Object count: " << object_count << std::endl;
    }
};

unsigned int MyClassBase::object_count = 0;

template <typename T>
class MyClass : public MyClassBase {
public:
    MyClass(T val) {
        val_ = val;
    }
    
    ~MyClass() {
    }
    
    void print() {
        std::cout << "Value: " << val_ << std::endl;
    }
        
private:
    T val_;
};

int main()
{
    MyClass<int> i1(4);
    MyClass<int> i2(5);
    MyClass<float> f1(0.5);
    MyClass<std::string> s1("string1");
    MyClass<std::string> s2("string2");
    MyClass<std::string> s3("string3");
    
    MyClassBase::printObjectCount();
}

Here the output is:

Object count: 6

Author: Srikanta

I write here to help the readers learn and understand computer programing, algorithms, networking, OS concepts etc. in a simple way. I have 20 years of working experience in computer networking and industrial automation.


If you also want to contribute, click here.

Leave a Reply

Your email address will not be published. Required fields are marked *

3
0
0
0
2
0