C++Talk.NET Forum Index C++Talk.NET
C++ language newsgroups
 
Archives   FAQFAQ   SearchSearch   MemberlistMemberlist   UsergroupsUsergroups   RegisterRegister 
 ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

static class member variables
Goto page 1, 2  Next
 
Post new topic   Reply to topic    C++Talk.NET Forum Index -> C++ Language (Moderated)
View previous topic :: View next topic  
Author Message
Eric
Guest





PostPosted: Wed Nov 17, 2004 11:12 am    Post subject: static class member variables Reply with quote



I have a static class member variable as follows:

struct A
{
static void Set (int i) { v = i; }
static int& Get () { return v; }
static int v;
};

int A::v; // define A::v in the cpp file
A::v will have external linkage and there will only be one instance of this
variable in the executable:

However, let's say I don't want to define the variable in the cpp file (eg.
it's a template class and I don't want users to have to define the
variable).
Is there anything wrong with defining it in a static member function which
returns a reference to the variable? Will there also always only be one copy
of the local static variable? Any other unforseen problems? Thanks in
advance for any comments.

struct A
{
static void Set (int i) { v() = i; }
static int& Get () { return v(); }
static int& v()
{
static v;
return v;
}
};



[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]
Back to top
Maxim Yegorushkin
Guest





PostPosted: Thu Nov 18, 2004 12:09 am    Post subject: Re: static class member variables Reply with quote



On 17 Nov 2004 06:12:08 -0500, Eric <shoongi (AT) yahoo (DOT) com> wrote:

Quote:
I have a static class member variable as follows:

struct A
{
static void Set (int i) { v = i; }
static int& Get () { return v; }
static int v;
};

int A::v; // define A::v in the cpp file
A::v will have external linkage and there will only be one instance of
this variable in the executable:

However, let's say I don't want to define the variable in the cpp file
(eg. it's a template class and I don't want users to have to define the
variable).

You can use a trick to place the static in *.h without getting multiple
simbol definitions linker error - place that static in a template base
class as follows:

template<int dummy> struct statics { static int v; };
template<int dummy> int statics<dummy>::v;

struct A : private statics<1234>
{
// Get/Set are the same as before
};

Quote:
Is there anything wrong with defining it in a static member function
which returns a reference to the variable? Will there also always only
be one copy of the local static variable? Any other unforseen problems?
Thanks in
advance for any comments.

struct A
{
static void Set (int i) { v() = i; }
static int& Get () { return v(); }
static int& v()
{
static v;
return v;
}
};

Probably, you forgot static keyword here. The code as it is written now
returns a dangling reference to the already evaporated local variable. You
can fix it as:

static int& Get () { static int v; return v; }

--
Maxim Yegorushkin

[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]

Back to top
James Hopkin
Guest





PostPosted: Fri Nov 19, 2004 12:50 pm    Post subject: Re: static class member variables Reply with quote



"Maxim Yegorushkin" <e-maxim (AT) yandex (DOT) ru> wrote

Quote:

You can use a trick to place the static in *.h without getting multiple
simbol definitions linker error - place that static in a template base
class as follows:

template<int dummy> struct statics { static int v; };
template<int dummy> int statics<dummy>::v;

struct A : private statics<1234
{
// Get/Set are the same as before
};


Just a slight tidy up:

template template<int dummy> int statics<dummy>::v;

struct A : private statics<>
{
// Get/Set are the same as before
};


Quote:
Is there anything wrong with defining it in a static member function
which returns a reference to the variable? Will there also always only
be one copy of the local static variable? Any other unforseen problems?
Thanks in
advance for any comments.

struct A
{
static void Set (int i) { v() = i; }
static int& Get () { return v(); }
static int& v()
{
static v; <------------------ missing int
return v;
}
};

Probably, you forgot static keyword here. The code as it is written now
returns a dangling reference to the already evaporated local variable. You
can fix it as:

static int& Get () { static int v; return v; }


Look again. The only mistake is a missing int on the line I marked
(which of course will compile on older compilers, since the int was
implied in pre-standard C++). (Also, Get should probably return by
value, but that's a design point rather than an error.)


James

[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]

Back to top
Daniel Krügler (ne Spange
Guest





PostPosted: Fri Nov 19, 2004 12:59 pm    Post subject: Re: static class member variables Reply with quote

Hello Maxim Yegorushkin,

Maxim Yegorushkin schrieb:

Quote:
On 17 Nov 2004 06:12:08 -0500, Eric <shoongi (AT) yahoo (DOT) com> wrote:


Is there anything wrong with defining it in a static member function
which returns a reference to the variable? Will there also always only
be one copy of the local static variable? Any other unforseen problems?
Thanks in
advance for any comments.

struct A
{
static void Set (int i) { v() = i; }
static int& Get () { return v(); }
static int& v()
{
static v;
return v;
}
};



Probably, you forgot static keyword here. The code as it is written now
returns a dangling reference to the already evaporated local variable. You
can fix it as:

static int& Get () { static int v; return v; }

Your description is somewhat misleading. I think the actual error, the

OP made was, that its declaration
of the local static in v misses a type. This looks like an MSVC
compiler: Its a real **shame** that even MSVC7.1
does allow implicit int declarations!! (In this case the compiler was
taking the right "guess", but what about
the next time??).

Furtheron it seems reasonable that the OP's Get function signature
should be changed to

struct A
{
...
static int Get () { return v(); }
...
};

because otherwise The Set function does not make very much sense...

Last but not least: Your proposal to use the template helper class is a very
cool idea, Maxim!

Greetings from Bremen,

Daniel




[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]


Back to top
Tokyo Tomy
Guest





PostPosted: Fri Nov 19, 2004 3:24 pm    Post subject: Re: static class member variables Reply with quote

"Maxim Yegorushkin" <e-maxim (AT) yandex (DOT) ru> wrote

Quote:
On 17 Nov 2004 06:12:08 -0500, Eric <shoongi (AT) yahoo (DOT) com> wrote:
...
Is there anything wrong with defining it in a static member function
which returns a reference to the variable? Will there also always only
be one copy of the local static variable? Any other unforseen problems?
Thanks in
advance for any comments.

struct A
{
static void Set (int i) { v() = i; }
static int& Get () { return v(); }
static int& v()
{
static v;
return v;
}
};

Probably, you forgot static keyword here.

Where?

Quote:
The code as it is written now returns a dangling reference to the already
evaporated local variable. You can fix it as:

static int& Get () { static int v; return v; }

static int& v () { static int v; return v; } // ?

[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]

Back to top
Renjith Mohan
Guest





PostPosted: Fri Nov 19, 2004 4:01 pm    Post subject: Re: static class member variables Reply with quote

"Maxim Yegorushkin" <e-maxim (AT) yandex (DOT) ru> wrote

Quote:
On 17 Nov 2004 06:12:08 -0500, Eric <shoongi (AT) yahoo (DOT) com> wrote:

I have a static class member variable as follows:

struct A
{
static void Set (int i) { v = i; }
static int& Get () { return v; }
static int v;
};

int A::v; // define A::v in the cpp file
A::v will have external linkage and there will only be one instance of
this variable in the executable:

However, let's say I don't want to define the variable in the cpp file
(eg. it's a template class and I don't want users to have to define the
variable).
Another solution is to use an unnamed namespace which is semantically

equivalent to internal linkage and is a mcuh more simple and elegant
solution.
Thus in a header file you can do this.
namespace
{
int v;
}
struct A
{
static void Set (int i) { v = i; }
static int& Get () { return v; }

};

[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]


Back to top
Maxim Yegorushkin
Guest





PostPosted: Fri Nov 19, 2004 4:51 pm    Post subject: Re: static class member variables Reply with quote

On 19 Nov 2004 07:59:16 -0500, Daniel Krügler (ne Spangenberg)
<dsp (AT) bdal (DOT) de> wrote:

[]

Quote:
Your description is somewhat misleading.

I agree, that was not a well thought answer.

Quote:
Last but not least: Your proposal to use the template helper class is a
very cool idea, Maxim!

I've stolen the idea from Dinkum STL implementation where it's used for
std::ios_base::flags (in, out, ate, etc.).

--
Maxim Yegorushkin

[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]

Back to top
Thomas Mang
Guest





PostPosted: Sat Nov 20, 2004 10:17 am    Post subject: Re: static class member variables Reply with quote


"Renjith Mohan" <renjithmohan (AT) hotmail (DOT) com> schrieb im Newsbeitrag
news:cd7223bc.0411180707.4fb20450 (AT) posting (DOT) google.com...
Quote:
"Maxim Yegorushkin" <e-maxim (AT) yandex (DOT) ru> wrote in message
news:<opshlwtry2ti5cme (AT) devlx007 (DOT) ipcb.net>...
On 17 Nov 2004 06:12:08 -0500, Eric <shoongi (AT) yahoo (DOT) com> wrote:

I have a static class member variable as follows:

struct A
{
static void Set (int i) { v = i; }
static int& Get () { return v; }
static int v;
};

int A::v; // define A::v in the cpp file
A::v will have external linkage and there will only be one instance of
this variable in the executable:

However, let's say I don't want to define the variable in the cpp file
(eg. it's a template class and I don't want users to have to define
the
variable).
Another solution is to use an unnamed namespace which is semantically
equivalent to internal linkage and is a mcuh more simple and elegant
solution.
Thus in a header file you can do this.
namespace
{
int v;
}
struct A
{
static void Set (int i) { v = i; }
static int& Get () { return v; }

};

Not a clever solution.

v is not tied to class A by any means and can be accessed directly without
any A object / operator ::.
Also, try to use this with multiple translation units, each changing and
reading v (via the functions provided in A). Surprise, surprise (at least
when the semantic of the OP is intended).


Thomas



[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]

Back to top
Seungbeom Kim
Guest





PostPosted: Sat Nov 20, 2004 4:23 pm    Post subject: Re: static class member variables Reply with quote

Renjith Mohan wrote:

Quote:
Another solution is to use an unnamed namespace which is semantically
equivalent to internal linkage and is a mcuh more simple and elegant
solution.
Thus in a header file you can do this.
namespace
{
int v;
}
struct A
{
static void Set (int i) { v = i; }
static int& Get () { return v; }

};

An unnamed namespace in a header file? Each of the translation units
that includes it will have its own copy of v, then. :(

--
Seungbeom Kim

[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]


Back to top
Maxim Yegorushkin
Guest





PostPosted: Sat Nov 20, 2004 6:19 pm    Post subject: Re: static class member variables Reply with quote

Renjith Mohan wrote:

Quote:
Another solution is to use an unnamed namespace which is semantically
equivalent to internal linkage and is a mcuh more simple and elegant
solution.
Thus in a header file you can do this.
namespace
{
int v;
}
struct A
{
static void Set (int i) { v = i; }
static int& Get () { return v; }

};

I strongly disagree. I am not sure, but it seems to me, that you've got
ODR violation here. The exact meaning of 'return v' is different in every
TU because of the fact that an unnamed namespace does have a name, though
hidden and distinct for every TU.

Aside from (possible) ODR violation, there are other problems. This places
a distinct instance of an object from the unnamed namespace in every TU
that includes the header with the unnamed namespace, what results in quite
different semantics because now every TU operates on an own instance of v.

--
Maxim Yegorushkin

[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]

Back to top
Thomas Mang
Guest





PostPosted: Sun Nov 21, 2004 5:00 am    Post subject: Re: static class member variables Reply with quote


"Maxim Yegorushkin" <e-maxim (AT) yandex (DOT) ru> schrieb im Newsbeitrag
news:opshq9w3y9ti5cme (AT) wkcg6rirwp (DOT) ..
Quote:
Renjith Mohan wrote:

Another solution is to use an unnamed namespace which is semantically
equivalent to internal linkage and is a mcuh more simple and elegant
solution.
Thus in a header file you can do this.
namespace
{
int v;
}
struct A
{
static void Set (int i) { v = i; }
static int& Get () { return v; }

};

I strongly disagree. I am not sure, but it seems to me, that you've got
ODR violation here.


Don't think so. Since v has internal linkage....


Quote:

Aside from (possible) ODR violation, there are other problems. This places
a distinct instance of an object from the unnamed namespace in every TU
that includes the header with the unnamed namespace, what results in quite
different semantics because now every TU operates on an own instance of v.

That IS a problem.


Thomas



[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]


Back to top
Francis Glassborow
Guest





PostPosted: Sun Nov 21, 2004 11:10 pm    Post subject: Re: static class member variables Reply with quote

In article <419fcbdb$0$24064$3b214f66 (AT) usenet (DOT) univie.ac.at>, Thomas Mang
<nospam (AT) nospam (DOT) invalid> writes
Quote:
"Maxim Yegorushkin" <e-maxim (AT) yandex (DOT) ru> schrieb im Newsbeitrag
news:opshq9w3y9ti5cme (AT) wkcg6rirwp (DOT) ..
Renjith Mohan wrote:

Another solution is to use an unnamed namespace which is semantically
equivalent to internal linkage and is a mcuh more simple and elegant
solution.
Thus in a header file you can do this.
namespace
{
int v;
}
struct A
{
static void Set (int i) { v = i; }
static int& Get () { return v; }

};

I strongly disagree. I am not sure, but it seems to me, that you've got
ODR violation here.


Don't think so. Since v has internal linkage....

It doesn't, it has external linkage but with an unutterable name.
However that is not really relevant because there is a potential ODR
violation which ever way you take it. If the above header file is
included in more than one TU the definition of struct A will be an ODR
issue.


--
Francis Glassborow ACCU
Author of 'You Can Do It!' see http://www.spellen.org/youcandoit
For project ideas and contributions: http://www.spellen.org/youcandoit/projects


[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]

Back to top
Renjith Mohan
Guest





PostPosted: Sun Nov 21, 2004 11:16 pm    Post subject: Re: static class member variables Reply with quote

"Maxim Yegorushkin" <e-maxim (AT) yandex (DOT) ru> wrote

Quote:
Renjith Mohan wrote:

Another solution is to use an unnamed namespace which is semantically
equivalent to internal linkage and is a mcuh more simple and elegant
solution.
Thus in a header file you can do this.
namespace
{
int v;
}
struct A
{
static void Set (int i) { v = i; }
static int& Get () { return v; }

};

I strongly disagree. I am not sure, but it seems to me, that you've got
ODR violation here. The exact meaning of 'return v' is different in every
TU because of the fact that an unnamed namespace does have a name, though
hidden and distinct for every TU.

Aside from (possible) ODR violation, there are other problems. This places
a distinct instance of an object from the unnamed namespace in every TU
that includes the header with the unnamed namespace, what results in quite
different semantics because now every TU operates on an own instance of v.
I understand my misconception. Thanks for pointing this out. I seem to

have been over enthusiastic about the clause 7.3.1.1 - Unnamed
namespaces para 2 which says something like this
"The use of the static keyword is deprecated when declaring objects in
a namespace scope (see annex depr); the unnamed-namespace provides a
superior alternative."

As has been pointed out this applies to "namespace scope" members only
and even with such variables this must be used with caution as the
generated namespace name(for the unnamed namespace) in each TU is
implementation dependent which may create binary differences of the
executable which is beyond programmers control.

But a doubt remains; since the standard does recommend it for
"namespace scope" variables, does it violate ODR for such variables?.

[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]

Back to top
David Olsen
Guest





PostPosted: Sun Nov 21, 2004 11:30 pm    Post subject: Re: static class member variables Reply with quote

Thomas Mang wrote:
Quote:
"Maxim Yegorushkin" <e-maxim (AT) yandex (DOT) ru> schrieb im Newsbeitrag news:opshq9w3y9ti5cme (AT) wkcg6rirwp (DOT) ..
Renjith Mohan wrote:
Another solution is to use an unnamed namespace which is semantically
equivalent to internal linkage and is a mcuh more simple and elegant
solution.
Thus in a header file you can do this.
namespace
{
int v;
}
struct A
{
static void Set (int i) { v = i; }
static int& Get () { return v; }
};

I strongly disagree. I am not sure, but it seems to me, that you've got
ODR violation here.

Don't think so. Since v has internal linkage....

No, v does not have internal linkage. Things inside the unnamed
namespace have external linkage. They just have a name that is known
only to the current translation unit, making them inaccessible from
other translation units. The ultimate effect is very similar to making
v static, but there are some subtle differences that must be understood.

The one-definition rule (ODR) violation is not with v, it is with A::Set
and A::Get. Within each translation unit, A::Set and A::Get refer to
the v that is unique to that translation unit. Therefore, A::Set and
A::Get are not the same in all translation units, which is not allowed.

--
David Olsen
[email]qg4h9ykc5m (AT) yahoo (DOT) com[/email]

[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]

Back to top
James Hopkin
Guest





PostPosted: Mon Nov 22, 2004 9:37 pm    Post subject: Re: static class member variables Reply with quote

[email]renjithmohan (AT) hotmail (DOT) com[/email] (Renjith Mohan) wrote in message
news:<cd7223bc.0411210606.50c8d68a (AT) posting (DOT) google.com>...
Quote:

But a doubt remains; since the standard does recommend it for
"namespace scope" variables, does it violate ODR for such variables?.


In this context, you get ODR violations using either (deprecated)
namespace scope statics or a nameless namespace. Using a nameless
namespace doesn't make it any more wrong :-)

Point of interest: boost::bind uses a nameless namespace in a header
to define _1, _2 etc. (the parameter placeholders). I've yet to get a
grip on the pros and cons of this - not that it's something you have
to understand to use bind itself.


James

[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]

Back to top
Display posts from previous:   
Post new topic   Reply to topic    C++Talk.NET Forum Index -> C++ Language (Moderated) All times are GMT
Goto page 1, 2  Next
Page 1 of 2

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Powered by phpBB © 2001, 2006 phpBB Group
SEO toolkit © 2004-2006 webmedic.