By using this site, you agree to our updated Privacy Policy and our Terms of Use. Manage your Cookies Settings.
446,301 Members | 1,456 Online
Bytes IT Community
+ Ask a Question
Need help? Post your question and get tips & solutions from a community of 446,301 IT Pros & Developers. It's quick & easy.

Order of Static Members

P: n/a
Hi,

Is the order of initialization guaranteed for static members as it is
for instance members?

Namely, the order they appear the in the declaration?

ie:

foo.h:

class Foo
{

....

private:

static std::string header_label;

static size_t header_len;

};

....

foo.cpp

std::string Foo::header_label ("vendor-product-0.1.1");

//
// Can I depend on header_label to be initialized at this point?
//
size_t Foo::header_len = header_label.length() +
2*(sizeof(AddressSize));
Thanks,

-Luther
Jul 22 '05 #1
Share this Question
Share on Google+
5 Replies


P: n/a
Luther Baker wrote:
Hi,
.... size_t Foo::header_len = header_label.length() +
2*(sizeof(AddressSize));


typo: AddressSize should be AddressType.

-Luther
Jul 22 '05 #2

P: n/a
On 30 May 2004 09:24:18 -0700, lu*********@yahoo.com (Luther Baker)
wrote:
Hi,

Is the order of initialization guaranteed for static members as it is
for instance members?


The C++ Standard articles which specify this are as follows:

<quote>
"9.4.2 Static data members
....
7 Static data members are initialized and destroyed exactly like
non-local objects. (3.6.2, 3.6.3)"
</quote>

Since 3.6.2 and 3.6.3 are rather lengthy, I'll leave the rest up to
you to find out by referring to the Standard.

In short, static objects initialized with a constant expression (or
zero-initialized) are done before any static objects initialized by
dynamic initialization (e.g. by a function call). Dynamically
initialized objects are initialized "in the order in which their
definition appears in the translation unit". IOW, this is different
than member data which is initialized in the order of the
*declaration* of the members.

Most compilers have proprietary means of ensuring that certain global
initializations are done before anything else, usually involving some
#pragma expression. E.g. in Borland C++ Builder, it's "#pragma
startup(<some number>)", M$VC++ has "#pragma compile" or something
similar.

Therefore, the linkage order, and perhaps the compiler options, will
also have an influence on the order in which static objects are
created and destroyed.

(If I have left anything out or misinterpreted something, I apologize
.... the C++ standard will have the last word. CAVEAT EMPTOR...).
--
Bob Hairgrove
No**********@Home.com
Jul 22 '05 #3

P: n/a
Luther Baker wrote:
Hi,

Is the order of initialization guaranteed for static members as it is
for instance members?

Namely, the order they appear the in the declaration?

ie:

foo.h:

class Foo
{

....

private:

static std::string header_label;

static size_t header_len;

};

....

foo.cpp

std::string Foo::header_label ("vendor-product-0.1.1");

//
// Can I depend on header_label to be initialized at this point?
//
size_t Foo::header_len = header_label.length() +
2*(sizeof(AddressSize));

Yes probably, but what would happen if someone assigns a different
header_label ?

i.e.

int main()
{
Foo::header_label = "gm-product-x.x.x";

};

If this is the case you want to wrap header* in a class.

i.e.

class HeaderStuff
{
std::string header_label;
size_t header_len;
public:
template <int N>
inline HeaderStuff( const char ( & str )[N] )
: header_label( str ),
header_len( N - 1 + 2*(sizeof(AddressType)) )
{
}

operator const std::string & () const
{
return header_label;
}

int length() const
{
return header_len;
}

};
struct Foo
{
static const HeaderStuff m_header_stuff;
....

or simply compute it every time:
class HeaderStuff
{
std::string header_label;

inline HeaderStuff( const char * str )
: header_label( str )
{
}

operator const std::string & () const
{
return header_label;
}

int length() const
{
return header_label.length() + 2*(sizeof(AddressType));
}

};
Jul 22 '05 #4

P: n/a
Gianni Mariani wrote:
....

Yes probably, but what would happen if someone assigns a different
header_label ?

i.e.

int main()
{
Foo::header_label = "gm-product-x.x.x";

};


The header_label will be private so the application can't change it, but
it is possible a class/instance method might accidentally change it ....
so at the very least, I should make it const.

Additionally, your point is well taken, I see no reason why I can't
encapsulate the entire header into a separate class.

Thanks,

-Luther
Jul 22 '05 #5

P: n/a
Bob Hairgrove wrote:

....
The C++ Standard articles which specify this are as follows:

<quote>
"9.4.2 Static data members
...
7 Static data members are initialized and destroyed exactly like
non-local objects. (3.6.2, 3.6.3)"
</quote>

Since 3.6.2 and 3.6.3 are rather lengthy, I'll leave the rest up to
you to find out by referring to the Standard.

In short, static objects initialized with a constant expression (or
zero-initialized) are done before any static objects initialized by
dynamic initialization (e.g. by a function call). Dynamically
initialized objects are initialized "in the order in which their
definition appears in the translation unit". IOW, this is different
than member data which is initialized in the order of the
*declaration* of the members.
Thanks for the direction Bob - let me see if I understand this:

In 3.6.2, objects with static storage duration with dynamic
initialization seem to be elaborated on, but the specifics of
initialization order regarding non-POD types (std::string), *static*
storage duration and *static* initialization seem to be avoided ... and
possibly circular (one section refers to another).

3.6.2p1 ends

"The initialization of local static objects is described in 6.7."

6.7p4 ...

"An implementation is permitted to perform early initialization of other
local objects with static storage duration under the same conditions
that an implementation is permitted to statically initialize an object
with static storage duration in namespace scope (3.6.2)."

So, it looks like ... implementation defined.
Most compilers have proprietary means of ensuring that certain global
initializations are done before anything else, usually involving some
#pragma expression. E.g. in Borland C++ Builder, it's "#pragma
startup(<some number>)", M$VC++ has "#pragma compile" or something
similar.

Therefore, the linkage order, and perhaps the compiler options, will
also have an influence on the order in which static objects are
created and destroyed.


Thanks for the insight. I believe I will follow Gianni's suggestion and
encapsulate the header into its own class.

-Luther
Jul 22 '05 #6

This discussion thread is closed

Replies have been disabled for this discussion.