4
votes

I'm trying to understand when the static initialization order fiasco is a real problem. If I use a string constant like kName below would it suffer any of the problems of the static initialization order fiasco? Is this a problem in this case because an instance of Derived can be created before kName is initialized as in main.cpp?

// Base.cpp
namespace test {
class Base {
public:
  virtual ~Base() = default;

protected:
  explicit Base(const std::string &name);
};
} // namespace test

// Derived.cpp
namespace test {
static const std::string kName = "my name";

class Derived : public Base {
public:
  Derived() : Base(kName) {}
  ~Derived() override = default;
};
} // namespace test

// main.cpp
int main() {
  test::Derived instance{};
  return 0;
}
2
static initialization order fiasco happens with depending static variable between several files. - Jarod42
So when would it be an actual problem using a string constant? I'm having a hard time wrapping my head around when this can be a problem. If the instance of test::Derived were defined outside of main() would it be a problem? - Mike Sweeney
Here you have only one (and so no dependencies). So you are fine. Having a static Derived in Base.cpp/main.cpp would be problematic. - Jarod42
Maybe this helps a bit to understand. - user1810087

2 Answers

2
votes

The main function will not be called until all "global" variables are initialized. That includes static member variables as well as variables in namespace scope (static or not).

So in this case it's no problem since you define the instance inside the main function.

It would be different if the definition of instance was done statically outside the main function.

2
votes

Within a specific translation unit, the order of initialization of static objects is guaranteed to be the order in which the object definitions appear in that translation unit. The order of destruction is guaranteed to be the reverse of the order of initialization. However, there is no guarantee concerning the order of initialization of static objects across translation units. This is what is termed as static initialization order fiasco.

So here you will not have static initialization order fiasco.