optimization - Why is the static object's Constructor not called in this Factory code (C++)? -


taking various sources, managed write simple templates based factory pattern class factory doesn't depend on of derived classes. uploaded code here: https://github.com/piyushsoni/factorypattern . might not perfect works - though surprise in example. when use identically in our large actual codebase, calls constructor of 'derivedfactory' only few of classes, , totally ignores other ones. when define static function can access derivedfactory object, , actually call function somewhere assign derived factory object lvalue (without there being need) calls constructor (whereas way create them in main.cpp should sufficient). looks compiler doing unneeded optimization here.

one difference can sample project tested in vc 15, while actual codebase uses intel compiler c++ 11 features enabled (which in turn uses msvc11 on windows , gcc on linux). how can fix , make sure these simple static objects created every time both msvc11 , gcc 4.8 onwards?

edit: wanted avoid writing code here keep question clean , putting source code @ 1 public location, doing here on feedback (and avoid getting closed). again want write simple code working, identical code not working when put in our commercial code compiled using intel compiler internally using msvc11 on windows. if have other questions, please ask them in comments , i'll try answer, please don't try close question before letting me answer them. have written exact problem i'm facing above.

here files:

shapefactory.h

#pragma once  #include <map> using namespace std;  #include "shape.h"  #define register_class(objectclass) static derivedfactory<objectclass> shape##objectclass(type_ ## objectclass);  class shape; class shapefactory; typedef map<shapetype, shapefactory*> maptypeshapefactorybytype;  class shapefactory { private:     maptypeshapefactorybytype mapshapetypebyfactory; protected:     shapefactory() {}     virtual shape* create() { return null; } private:     shapefactory(const shapefactory&); public:     virtual ~shapefactory() {}     static shapefactory& getshapefactory();      shape* createshape(shapetype type);      virtual void destroyshape(shape* object) { delete object; object = nullptr; }     void registerfactory(shapetype type, shapefactory* factory); };  template<typename shapeclass> class derivedfactory : public shapefactory { public:     derivedfactory(shapetype type)     {         shapefactory::getshapefactory().registerfactory(type, this);     }     ~derivedfactory() {}     shape* create() { return new shapeclass(); } }; 

shapefactory.cpp

#include "shapefactory.h"  //maptypeshapefactorybytype shapefactory::mapshapetypebyfactory; //shapefactory* shapefactory::minstance = null;  shapefactory& shapefactory::getshapefactory() {     static shapefactory instance;     return instance; }  shape * shapefactory::createshape(shapetype type) {     if (mapshapetypebyfactory.find(type) != mapshapetypebyfactory.end())         return mapshapetypebyfactory[type]->create();     else         return nullptr; }  void shapefactory::registerfactory(shapetype type, shapefactory * factory) {     mapshapetypebyfactory[type] = factory; } 

shape.h

#pragma once  #include <string> using namespace std;  enum shapetype {     type_unknown,     type_circle,     type_rectangle,     type_polygon };  class shape {     std::string name; public:     virtual ~shape() {}     virtual shapetype gettype() { return type_unknown; } }; 

rectangle.h

#pragma once #include "shape.h" #include <iostream>  using namespace std;  class rectangle : public shape { public:     rectangle();     virtual ~rectangle();     virtual shapetype gettype() { return type_rectangle; } private:     float points[4][3]; }; 

rectangle.cpp

#include "rectangle.h" #include "shapefactory.h"  static derivedfactory<rectangle> rectanglefactory(type_rectangle);  rectangle::rectangle() {     cout << "the factory created new rectangle! \n"; }  rectangle::~rectangle() {     cout << "the rectangle object destroyed \n"; } 

circle.h

#pragma once #include "shape.h" #include <iostream>  using namespace std;  class circle : public shape { public:     circle();     virtual ~circle();     virtual shapetype gettype() { return type_circle; }  private:     float center[3];     float radius; }; 

circle.cpp

#include "circle.h" #include "shapefactory.h"  static derivedfactory<circle> circlefactory(type_circle);  circle::circle() {     cout << "the factory created new circle! \n"; }  circle::~circle() {     cout << "the circle object destroyed \n"; } 

main.cpp

#include <iostream> #include <string> #include <map> #include "shapefactory.h" #include "shape.h" #include "circle.h" #include "rectangle.h"  using namespace std;  int main() {     shapefactory& factory = shapefactory::getshapefactory();      circle* vec = (circle*)factory.createshape(type_circle);     cout << "object type : " << vec->gettype() <<"\n";     factory.destroyshape(vec);      rectangle* con = (rectangle*)factory.createshape(type_rectangle);     cout << "object type : " << con->gettype() << "\n";     factory.destroyshape(con);        getchar();     return 0; } 

thanks!!

after compilation, linker resolves symbols in object files. function declaration, static or otherwise, alone not sufficient the compiler generate symbols linked or resolved definition - unless there need when invoked in compiled code.

this related question static variables initialisation order provides more insight.

you might want review code ensure there 'need' resolve derived classes.

as @alf recommends, including minimal code snippet in question focus answers here.


Comments