473,325 Members | 2,872 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 473,325 software developers and data experts.

Lifetime of static objects revisited

I have a C++ file which needs to work along these lines:

class foo
{
private:
int i1_;
public:
foo():i1_(12){}
~foo()
{
ExecuteSomething(); // Must be executed before program exits
}
int GetI1(void)const{return(i1_);}
void SetI1(int i1){i1_ = i1;}
};

static foo MyStaticFoo;

extern void f1()
{
MyStaticFoo.SetI1(13);
}

extern int f2()
{
return(MyStaticFoo.GetI1());
}

In other words, it needs to retain some state in a static object. On
program exit, the static object's destructor must be called.

Unfortunately, it seems that foo's destructor is (sometimes) being
called before some of the functions which need to access it.

How can I change this design so that foo is not destroyed until I'm
finished with it?

I can't change
static foo MyStaticFoo;
to
static foo* MyStaticFoo = 0;

and use dynamic allocation, because then someone will have to remember
to call delete on the object, and if they forget, the destructor won't
be called.

I don't think I can use a singleton pattern either, because I still
can't guarantee that the object won't be destroyed while I still need
it.

Any thoughts?
--
Simon Elliott http://www.ctsn.co.uk
Jul 22 '05 #1
5 1485
Simon Elliott wrote:
I have a C++ file which needs to work along these lines:

class foo
{
private:
int i1_;
public:
foo():i1_(12){}
~foo()
{
ExecuteSomething(); // Must be executed before program exits
}
int GetI1(void)const{return(i1_);}
void SetI1(int i1){i1_ = i1;}
};

static foo MyStaticFoo;

extern void f1()
{
MyStaticFoo.SetI1(13);
}

extern int f2()
{
return(MyStaticFoo.GetI1());
}

In other words, it needs to retain some state in a static object. On
program exit, the static object's destructor must be called.

Unfortunately, it seems that foo's destructor is (sometimes) being
called before some of the functions which need to access it.

How can I change this design so that foo is not destroyed until I'm
finished with it?

I can't change
static foo MyStaticFoo;
to
static foo* MyStaticFoo = 0;

and use dynamic allocation, because then someone will have to remember
to call delete on the object, and if they forget, the destructor won't
be called.

I don't think I can use a singleton pattern either, because I still
can't guarantee that the object won't be destroyed while I still need
it.

Any thoughts?


Creating it dynamically and relying upon _not_ destroying it is basically
all you can do with current design.

If you can change the design, you can make the 'MyStaticFoo' a static
object of some base class of those classes that use it. Thus you can
ensure that it exists until the last object that needs it is destroyed.
IOW, rethink your design so you don't use global functions f1 and f2.

V
Jul 22 '05 #2
On 02/12/2004, Victor Bazarov wrote:
Creating it dynamically and relying upon not destroying it is
basically all you can do with current design.

If you can change the design, you can make the 'MyStaticFoo' a static
object of some base class of those classes that use it. Thus you can
ensure that it exists until the last object that needs it is
destroyed. IOW, rethink your design so you don't use global
functions f1 and f2.


Unfortunately I can't do this because it must fit into a legacy design.
However the foo object lifetime is bounded by a particular function so
I might be able to create an object which manages it...

--
Simon Elliott http://www.ctsn.co.uk
Jul 22 '05 #3
Simon Elliott wrote:
On 02/12/2004, Victor Bazarov wrote:

Creating it dynamically and relying upon not destroying it is
basically all you can do with current design.

If you can change the design, you can make the 'MyStaticFoo' a static
object of some base class of those classes that use it. Thus you can
ensure that it exists until the last object that needs it is
destroyed. IOW, rethink your design so you don't use global
functions f1 and f2.

Unfortunately I can't do this because it must fit into a legacy design.
However the foo object lifetime is bounded by a particular function so
I might be able to create an object which manages it...


It could be the limitation of your "legacy design", of course, but if you
can, put the definition for your 'MyStaticFoo' in the same module as the
object that attempts to access it in the destructor (that's what causes
the problem, as I understand it) and place 'MyStaticFoo' _above_.

If you cannot due to aforementioned limitations, use the dynamic memory
approach, and rewrite the legacy stuff ASAP. Static initialisation fiasco
is a bitch and there is no way to fix it, only to avoid it.

V
Jul 22 '05 #4
Simon Elliott wrote:
I have a C++ file which needs to work along these lines:

class foo
{
private:
int i1_;
public:
foo():i1_(12){}
~foo()
{
ExecuteSomething(); // Must be executed before program exits
}
int GetI1(void)const{return(i1_);}
void SetI1(int i1){i1_ = i1;}
};

static foo MyStaticFoo;

extern void f1()
{
MyStaticFoo.SetI1(13);
}

extern int f2()
{
return(MyStaticFoo.GetI1());
}

In other words, it needs to retain some state in a static object. On
program exit, the static object's destructor must be called.

Unfortunately, it seems that foo's destructor is (sometimes) being
called before some of the functions which need to access it.

How can I change this design so that foo is not destroyed until I'm
finished with it?

I can't change
static foo MyStaticFoo;
to
static foo* MyStaticFoo = 0;

and use dynamic allocation, because then someone will have to remember
to call delete on the object, and if they forget, the destructor won't
be called.

I don't think I can use a singleton pattern either, because I still
can't guarantee that the object won't be destroyed while I still need
it.

Any thoughts?

It is the dead reference problem of the singleton pattern. As described
in the book Modern C++ Design by Andrei Alexandrescu, you can deal
with it in 3 ways:
1. Ignore it (which is not applicable in your case)
2. Recreate it (Phoenix Singleton)
3. Singletons with Longevity

Since MyStaticFoo keeps states, the 2nd choice is not applicable as well.
You can make use of the Loki library provided by the author for free.
You can download it by following the author's home page:
http://www.moderncppdesign.com/

Ricky
Jul 22 '05 #5
On 04/12/2004, Ricky Liu wrote:
Any thoughts?

It is the dead reference problem of the singleton pattern. As
described in the book Modern C++ Design by Andrei Alexandrescu, you
can deal with it in 3 ways:
1. Ignore it (which is not applicable in your case)
2. Recreate it (Phoenix Singleton)
3. Singletons with Longevity

Since MyStaticFoo keeps states, the 2nd choice is not applicable as
well. You can make use of the Loki library provided by the author
for free. You can download it by following the author's home page:
http://www.moderncppdesign.com/


Thanks for this. I'm not familiar with the concept of "Singletons with
Longevity". Andrei Alexandrescu's book is refrred to so frequently that
I think it's time for me to buy a copy...

--
Simon Elliott http://www.ctsn.co.uk
Jul 22 '05 #6

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

7
by: Simon Elliott | last post by:
Consider the following, incorrect, code: #pragma hdrstop #include <condefs.h> #include <iostream> #include <conio.h> class bar {
5
by: Stuart MacMartin | last post by:
I have a problem with static lifetime (order of destruction of statics within different cpp files). I have a workaround that happens to work in my case. I'd like to know if this is luck or...
4
by: Terry | last post by:
There are a number of things about using unmanaged resources in Windows Forms programming that is unclear to me. In C++, if you loaded an icon resource using "ExtractIcon()", the resource was...
6
by: Richard Steele | last post by:
I have a static object that gets referenced at application startup. This object stores a dataset and various strings to be used whenever required. This object may be called at anytime to provide...
1
by: Eduardo Azevedo | last post by:
If I have a class with method Shared, when this objects are destroies what's happend with the objects Shared? How long is the lifetime of a function shared in the Class ? there are no...
16
by: anonymous.user0 | last post by:
The way I understand it, if I have an object Listener that has registered as a listener for some event Event that's produced by an object Emitter, as long as Emitter is still allocated Listener...
9
by: Chuck Cobb | last post by:
I am creating some static classes with static methods and static variables, but I have a question: What is the lifetime of static classes and static variables? Is there any risk that these...
14
by: John Goche | last post by:
Hello, The extern keyword can be used in C and C++ to share global variables between files by declaring the variable in header file and defining it in only one of the two files. For example,...
9
by: David | last post by:
With a non-server app there is one instance of the program running and one user 'using' it at a time. With this scenario I'm pretty comfortable with variable scope and lifetime. With a server app...
0
by: DolphinDB | last post by:
Tired of spending countless mintues downsampling your data? Look no further! In this article, you’ll learn how to efficiently downsample 6.48 billion high-frequency records to 61 million...
0
by: ryjfgjl | last post by:
ExcelToDatabase: batch import excel into database automatically...
0
isladogs
by: isladogs | last post by:
The next Access Europe meeting will be on Wednesday 6 Mar 2024 starting at 18:00 UK time (6PM UTC) and finishing at about 19:15 (7.15PM). In this month's session, we are pleased to welcome back...
0
by: Vimpel783 | last post by:
Hello! Guys, I found this code on the Internet, but I need to modify it a little. It works well, the problem is this: Data is sent from only one cell, in this case B5, but it is necessary that data...
1
by: PapaRatzi | last post by:
Hello, I am teaching myself MS Access forms design and Visual Basic. I've created a table to capture a list of Top 30 singles and forms to capture new entries. The final step is a form (unbound)...
1
by: CloudSolutions | last post by:
Introduction: For many beginners and individual users, requiring a credit card and email registration may pose a barrier when starting to use cloud servers. However, some cloud server providers now...
1
by: Defcon1945 | last post by:
I'm trying to learn Python using Pycharm but import shutil doesn't work
0
by: af34tf | last post by:
Hi Guys, I have a domain whose name is BytesLimited.com, and I want to sell it. Does anyone know about platforms that allow me to list my domain in auction for free. Thank you
0
isladogs
by: isladogs | last post by:
The next Access Europe User Group meeting will be on Wednesday 3 Apr 2024 starting at 18:00 UK time (6PM UTC+1) and finishing by 19:30 (7.30PM). In this session, we are pleased to welcome former...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.