Static field initialization in template class in C++

瘦欲@ 提交于 2019-12-06 03:28:48

问题


I'm trying to create some self-registering classes in C++. So I tried the solution similar to the one provided here. While doing this I stumble over something strange.

Here's the code:

#include <iostream>

class StaticClassType {
public:
  StaticClassType() {
    // Notify when the static member is created
    std::cout << "We're in." << std::endl;
  }
};


template<typename T>
class TestClass1 {
public:
  TestClass1() { &m; }
private:
  // Static member in a template class
  static StaticClassType m;
};

template<typename T>
StaticClassType TestClass1<T>::m;


class TestClass2 : public TestClass1<TestClass2> {
public:
  TestClass2() { } // required; why?
};


int main() {
  return 0;
}

This code create the static member variable TestClass1::m on startup (thereby printing "We're in." to the console) - i.e. before main() is started. However, the code only works if I write a (empty) constructor for TestClass2 (as shown in the example).

Why do I need to write this constructor? Why doesn't the default constructor generated by the compiler does the same thing?

This problem only occurs for template classes. If TestClass1 wasn't a template class, the code would work without writing the empty constructor for TestClass2.


回答1:


I created even smaller example (without constructors, which are not needed) :

#include <iostream>

class StaticClassType {
public:
  StaticClassType(int v) {
    // Notify when the static member is created
    std::cout << "We're in."<<v << std::endl;
  }
};


template<typename T>
class TestClass1 {
protected:
  // Static member in a template class
  static StaticClassType m;
};

template<typename T>
StaticClassType TestClass1<T>::m = StaticClassType(3);


class TestClass2 : public TestClass1<TestClass2> {
public:
    void foo()
    {
        (void)m;
    }
};

int main() {
  std::cout << "main" << std::endl;
}

take a note that foo() method is needed, otherwise the compiler removes the static variable, since it's not used anywhere.




回答2:


From my point of view the "issue" is that in "Template world" the compiler will generate only what is really used by the client code. Here You never instanciate the TestClass2 class. Therefore a lot of code won't be generated. Try :

int main() {

  TestClass2 instance;
  return 0;
} 

And it works then.



来源:https://stackoverflow.com/questions/9209052/static-field-initialization-in-template-class-in-c

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!