Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > C++ > Nonstatic member example?

Reply
Thread Tools

Nonstatic member example?

 
 
fl
Guest
Posts: n/a
 
      12-31-2007
Hi,
There is a question about nonstatic member. C++ primer says: A
nonstatic member is restricted to being declared as a pointer or
reference to an object of its class. It only gives an example of
pointer *b.

class Bar {
public:

private:
static Bar a; // OK
Bar *b; // OK
Bar c; // error

My question is how a nonstatic member is declared as a reference to an
object of its class. Because a reference is legal only after the
original variable has been declared, where is the original object? I
feel it is really bizarre. Could you give me an example? Thanks in
advance.




private variable
 
Reply With Quote
 
 
 
 
Juha Nieminen
Guest
Posts: n/a
 
      12-31-2007
fl wrote:
> Hi,
> There is a question about nonstatic member. C++ primer says: A
> nonstatic member is restricted to being declared as a pointer or
> reference to an object of its class. It only gives an example of
> pointer *b.
>
> class Bar {
> public:
>
> private:
> static Bar a; // OK
> Bar *b; // OK
> Bar c; // error
>
> My question is how a nonstatic member is declared as a reference to an
> object of its class. Because a reference is legal only after the
> original variable has been declared, where is the original object? I
> feel it is really bizarre. Could you give me an example? Thanks in
> advance.


References and pointers can be created from pre-declared (ie.
incomplete) types. It's not necessary to have the full declaration of
the type in order to create a reference or pointer of that type. That
is, for example, this is valid:

class A; // Incomplete type

void foo(const A&); // Ok

In your example "Bar" has implicitly been pre-declared, and thus it's
ok to create a reference of pointer to it, even inside Bar's declaration.
 
Reply With Quote
 
 
 
 
Jim Langston
Guest
Posts: n/a
 
      12-31-2007
fl wrote:
> Hi,
> There is a question about nonstatic member. C++ primer says: A
> nonstatic member is restricted to being declared as a pointer or
> reference to an object of its class. It only gives an example of
> pointer *b.
>
> class Bar {
> public:
>
> private:
> static Bar a; // OK
> Bar *b; // OK
> Bar c; // error
>
> My question is how a nonstatic member is declared as a reference to an
> object of its class. Because a reference is legal only after the
> original variable has been declared, where is the original object? I
> feel it is really bizarre. Could you give me an example? Thanks in
> advance.


Passing it as a parameter to the constructor is one way. this (the instance
pointer) is another. In fact, class member references have to be
initialized in the constructor initialization list (I know of no other way)
and passing as a paramter would be the usuall way. Something like (untested
code)

class Bar {
public:
Bar( Bar& foo ): d( foo ) {}
private:
Bar& d;
};


--
Jim Langston
http://www.velocityreviews.com/forums/(E-Mail Removed)


 
Reply With Quote
 
Rahul
Guest
Posts: n/a
 
      12-31-2007
On Dec 31, 9:36 am, Juha Nieminen <(E-Mail Removed)> wrote:
> fl wrote:
> > Hi,
> > There is a question about nonstatic member. C++ primer says: A
> > nonstatic member is restricted to being declared as a pointer or
> > reference to an object of its class. It only gives an example of
> > pointer *b.

>
> > class Bar {
> > public:

>
> > private:
> > static Bar a; // OK
> > Bar *b; // OK
> > Bar c; // error

>
> > My question is how a nonstatic member is declared as a reference to an
> > object of its class. Because a reference is legal only after the
> > original variable has been declared, where is the original object? I
> > feel it is really bizarre. Could you give me an example? Thanks in
> > advance.

>
> References and pointers can be created from pre-declared (ie.
> incomplete) types. It's not necessary to have the full declaration of
> the type in order to create a reference or pointer of that type. That
> is, for example, this is valid:
>
> class A; // Incomplete type
>
> void foo(const A&); // Ok
>
> In your example "Bar" has implicitly been pre-declared, and thus it's
> ok to create a reference of pointer to it, even inside Bar's declaration.


Then how does a static member object work? The type is incomplete even
for that isn't it?
 
Reply With Quote
 
Salt_Peter
Guest
Posts: n/a
 
      12-31-2007
On Dec 30, 11:24 pm, fl <(E-Mail Removed)> wrote:
> Hi,
> There is a question about nonstatic member. C++ primer says: A
> nonstatic member is restricted to being declared as a pointer or
> reference to an object of its class. It only gives an example of
> pointer *b.
>
> class Bar {
> public:
>
> private:
> static Bar a; // OK
> Bar *b; // OK
> Bar c; // error
>
> My question is how a nonstatic member is declared as a reference to an
> object of its class. Because a reference is legal only after the
> original variable has been declared, where is the original object? I
> feel it is really bizarre. Could you give me an example? Thanks in
> advance.
>
> private variable


the original object, in a special case like this one, would have to
refer to itself, which would then basicly mean that such a class could
not have a static member since the static member has no 'this'.
Its a special case, don't dissmiss references. They solve many, many
problems.

[10.7] Should you use the this pointer in the constructor?
http://www.parashift.com/c++-faq-lit....html#faq-10.7

#include <iostream>

class A
{
const A& r_a;
public:
A() : r_a(*this) { }
A(const A& copy) : r_a(copy) { }
A& operator=(const A& rhv); // disabled
A const& get_r() const { return r_a; }
};

void foo(const A& r)
{
std::cout << "&r = " << &r;
std::cout << "\tr.r_a = " << &r.get_r();
std::cout << std::endl;
}

int main()
{
A a;
foo(a);
A another = a; // is NOT an assignment
foo(another);
}

/*
&r = 0x7fff0f2e1930 r.r_a = 0x7fff0f2e1930
&r = 0x7fff0f2e1920 r.r_a = 0x7fff0f2e1930
*/

 
Reply With Quote
 
James Kanze
Guest
Posts: n/a
 
      12-31-2007
On Dec 31, 8:25 am, Rahul <(E-Mail Removed)> wrote:
> On Dec 31, 9:36 am, Juha Nieminen <(E-Mail Removed)> wrote:
> > fl wrote:


> > > There is a question about nonstatic member. C++ primer says: A
> > > nonstatic member is restricted to being declared as a pointer or
> > > reference to an object of its class. It only gives an example of
> > > pointer *b.


> > > class Bar {
> > > public:


> > > private:
> > > static Bar a; // OK
> > > Bar *b; // OK
> > > Bar c; // error


> > > My question is how a nonstatic member is declared as a
> > > reference to an object of its class. Because a reference
> > > is legal only after the original variable has been
> > > declared, where is the original object? I feel it is
> > > really bizarre. Could you give me an example? Thanks in
> > > advance.


> > References and pointers can be created from pre-declared (ie.
> > incomplete) types.


The correct terminology is "incomplete type". A class type is
known as soon as it is declared, i.e. immediately after the name
of the class in either a declaration or a definition. The class
type is only complete after the final closing } of the
definition.

> . It's not necessary to have the full declaration of
> > the type in order to create a reference or pointer of that
> > type.


Yes and no. I think that Rahul's problem was more along the
lines of:

class Foo
{
Foo& myFoo ;
} ;

According to the standard, myFoo, here, is a definition (not a
declaration), so one would expect it to be initialized with an
object. Which isn't possible at this point in the program,
because the type Foo is still incomplete, and you cannot have
objects with incomplete types.

The reason, of course, is that the definition of myFoo is
actually a definition of an unspecified number of instances of
the reference; each instance only comes into being when the
constructor of Foo is called. At that point, Foo must be
complete (and the reference must have an initializer, in the
initialization list), or the code is ill formed. (Note that if
the definition of the constructor is given within the class
body, it is processed as if it were immediately following the
complete definition of the class, so even something like the
following is legal:

class Foo
{
public:
Foo() : myFoo( *this ) { }
Foo( Foo& parent ) : myFoo( parent ) {}

Foo& myFoo ;
}

(Note that if the class contains a reference to itself, the only
possible initialization for the first instance is to itself.
Class instances are created one after the other, there are no
null references, and the reference must refer to an "existing"
object.)

> > That is, for example, this is valid:


> > class A; // Incomplete type


> > void foo(const A&); // Ok


> > In your example "Bar" has implicitly been pre-declared,
> > and thus it's ok to create a reference of pointer to it,
> > even inside Bar's declaration.


> Then how does a static member object work? The type is
> incomplete even for that isn't it?


A declaration of a non-static data member in a class is a
definition, and requires a complete type. A declaration of a
static data member is not a definition, and so does not require
a complete type (although if the static data member is used, you
must provide a definition somewhere, and the type must be
complete when you provide that definition).

Note the different lifetimes (and storage durations) associated
with static and non-static members. A non-static member has the
same lifetime and storage duration as the containing instance,
and is only initialized (and only requires a complete type) when
the containing instance is initialized. A static member has
static lifetime and storage duration, and is initialized during
static initialization, very much as if it were a variable
declared at namespace scope.

--
James Kanze (GABI Software) email:(E-Mail Removed)
Conseils en informatique orientée objet/
Beratung in objektorientierter Datenverarbeitung
9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34

 
Reply With Quote
 
James Kanze
Guest
Posts: n/a
 
      12-31-2007
On Dec 31, 5:45 am, "Jim Langston" <(E-Mail Removed)> wrote:
> fl wrote:


> > There is a question about nonstatic member. C++ primer says:
> > A nonstatic member is restricted to being declared as a
> > pointer or reference to an object of its class. It only
> > gives an example of pointer *b.


> > class Bar {
> > public:


> > private:
> > static Bar a; // OK
> > Bar *b; // OK
> > Bar c; // error


> > My question is how a nonstatic member is declared as a
> > reference to an object of its class. Because a reference is
> > legal only after the original variable has been declared,
> > where is the original object? I feel it is really bizarre.
> > Could you give me an example? Thanks in advance.


> Passing it as a parameter to the constructor is one way. this
> (the instance pointer) is another. In fact, class member
> references have to be initialized in the constructor
> initialization list (I know of no other way) and passing as a
> paramter would be the usuall way. Something like (untested
> code)


> class Bar {
> public:
> Bar( Bar& foo ): d( foo ) {}
> private:
> Bar& d;
> };


Note that if that's the only constructor, there's no way to
create an instance of the class, because in order to create an
instance, you have to have an instance. (Note too that your
constructor is a copy constructor. I'm not sure if this is
intentional or not---it doesn't have the classical copy
semantics, but on the other hand, I can't imagine any other
reasonable approach if you don't want to have to test for null
pointers, etc.)

About the only case I can imagine where a reference to the class
itself would make sense if if you provide a default constructor
which initializes it to *this. Given the usual way people
understand things, I rather suspect that in such cases, most of
the time, using pointers would result in more understandable
code. But that may just be me.

--
James Kanze (GABI Software) email:(E-Mail Removed)
Conseils en informatique orientée objet/
Beratung in objektorientierter Datenverarbeitung
9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34
 
Reply With Quote
 
fl
Guest
Posts: n/a
 
      12-31-2007
On 31 déc, 04:27, Salt_Peter <(E-Mail Removed)> wrote:
> On Dec 30, 11:24 pm, fl <(E-Mail Removed)> wrote:
>
>
>
>
>
> > Hi,
> > There is a question about nonstatic member. C++ primer says: A
> > nonstatic member is restricted to being declared as a pointer or
> > reference to an object of its class. It only gives an example of
> > pointer *b.

>
> > class Bar {
> > public:

>
> > private:
> > static Bar a; * * *// OK
> > Bar *b; * * * * * * *// OK
> > Bar c; * * * * * * * // error

>
> > My question is how a nonstatic member is declared as a reference to an
> > object of its class. Because a reference is legal only after the
> > original variable has been declared, where is the original object? I
> > feel it is really bizarre. Could you give me an example? Thanks in
> > advance.

>
> > private variable

>
> the original object, in a special case like this one, would have to
> refer to itself, which would then basicly mean that such a class could
> not have a static member since the static member has no 'this'.
> Its a special case, don't dissmiss references. They solve many, many
> problems.
>
> [10.7] Should you use the this pointer in the constructor?http://www.parashift.com/c++-faq-lit....html#faq-10.7
>
> #include <iostream>
>
> class A
> {
> * const A& r_a;
> public:
> * A() : r_a(*this) { }
> * A(const A& copy) : r_a(copy) { }
> * A& operator=(const A& rhv); // disabled
> * A const& get_r() const { return r_a; }
>
> };
>
> void foo(const A& r)
> {
> * std::cout << "&r = " << &r;
> * std::cout << "\tr.r_a = " << &r.get_r();
> * std::cout << std::endl;
>
> }
>
> int main()
> {
> * A a;
> * foo(a);
> * A another = a; // is NOT an assignment
> * foo(another);
>
> }
>
> /*
> &r = 0x7fff0f2e1930 * * r.r_a = 0x7fff0f2e1930
> &r = 0x7fff0f2e1920 * * r.r_a = 0x7fff0f2e1930
> */- Masquer le texte des messages précédents -
>
> - Afficher le texte des messages précédents -


Hi,
I find the modified code,see below, has the same output as yours.
Why the overload:
A another = a; // is NOT an assignment
does not take effect? Thank you very much.





---------------------
#include <iostream>


class A
{
const A& r_a;
public:
A() : r_a(*this) { }
// A(const A& copy) : r_a(copy) { }
// A& operator=(const A& rhv); // disabled
A const& get_r() const { return r_a; }



};


void foo(const A& r)
{
std::cout << "&r = " << &r;
std::cout << "\tr.r_a = " << &r.get_r();
std::cout << std::endl;


}


int main()
{
A a;
foo(a);
A another; // = a; // is NOT an assignment
foo(another);


}
 
Reply With Quote
 
Jim Langston
Guest
Posts: n/a
 
      12-31-2007
James Kanze wrote:
> On Dec 31, 5:45 am, "Jim Langston" <(E-Mail Removed)> wrote:
>> fl wrote:

>
>>> There is a question about nonstatic member. C++ primer says:
>>> A nonstatic member is restricted to being declared as a
>>> pointer or reference to an object of its class. It only
>>> gives an example of pointer *b.

>
>>> class Bar {
>>> public:

>
>>> private:
>>> static Bar a; // OK
>>> Bar *b; // OK
>>> Bar c; // error

>
>>> My question is how a nonstatic member is declared as a
>>> reference to an object of its class. Because a reference is
>>> legal only after the original variable has been declared,
>>> where is the original object? I feel it is really bizarre.
>>> Could you give me an example? Thanks in advance.

>
>> Passing it as a parameter to the constructor is one way. this
>> (the instance pointer) is another. In fact, class member
>> references have to be initialized in the constructor
>> initialization list (I know of no other way) and passing as a
>> paramter would be the usuall way. Something like (untested
>> code)

>
>> class Bar {
>> public:
>> Bar( Bar& foo ): d( foo ) {}
>> private:
>> Bar& d;
>> };

>
> Note that if that's the only constructor, there's no way to
> create an instance of the class, because in order to create an
> instance, you have to have an instance. (Note too that your
> constructor is a copy constructor. I'm not sure if this is
> intentional or not---it doesn't have the classical copy
> semantics, but on the other hand, I can't imagine any other
> reasonable approach if you don't want to have to test for null
> pointers, etc.)
>
> About the only case I can imagine where a reference to the class
> itself would make sense if if you provide a default constructor
> which initializes it to *this. Given the usual way people
> understand things, I rather suspect that in such cases, most of
> the time, using pointers would result in more understandable
> code. But that may just be me.


Yes, you are right. Although this compiles:

class Foo
{
public:
Foo( Foo& foo ): Ref( foo ) {}
Foo(): Ref( *this ) {}
private:
Foo& Ref;
Foo& operator=( Foo& foo ) {}
};

main()
{
Foo foo;
Foo bar( foo );
}

I could think of someone attempting to do something like this for a linked
list with the first declaration being the head, but I think the destructer
would cause problems as you can't reseat a reference. It could be done, but
probably shouldn't.


--
Jim Langston
(E-Mail Removed)


 
Reply With Quote
 
James Kanze
Guest
Posts: n/a
 
      12-31-2007
On Dec 31, 1:12 pm, "Jim Langston" <(E-Mail Removed)> wrote:
> James Kanze wrote:
> > On Dec 31, 5:45 am, "Jim Langston" <(E-Mail Removed)> wrote:
> >> fl wrote:


[...]
> >> class Bar {
> >> public:
> >> Bar( Bar& foo ): d( foo ) {}
> >> private:
> >> Bar& d;
> >> };


> > Note that if that's the only constructor, there's no way to
> > create an instance of the class, because in order to create an
> > instance, you have to have an instance. (Note too that your
> > constructor is a copy constructor. I'm not sure if this is
> > intentional or not---it doesn't have the classical copy
> > semantics, but on the other hand, I can't imagine any other
> > reasonable approach if you don't want to have to test for null
> > pointers, etc.)


> > About the only case I can imagine where a reference to the class
> > itself would make sense if if you provide a default constructor
> > which initializes it to *this. Given the usual way people
> > understand things, I rather suspect that in such cases, most of
> > the time, using pointers would result in more understandable
> > code. But that may just be me.


> Yes, you are right. Although this compiles:


> class Foo
> {
> public:
> Foo( Foo& foo ): Ref( foo ) {}
> Foo(): Ref( *this ) {}
> private:
> Foo& Ref;
> Foo& operator=( Foo& foo ) {}
> };


> main()
> {
> Foo foo;
> Foo bar( foo );
> }


As it should. (And BTW: you don't need the private operator=,
since the compiler won't generate one if the class contains a
reference member.)

> I could think of someone attempting to do something like this
> for a linked list with the first declaration being the head,
> but I think the destructer would cause problems as you can't
> reseat a reference. It could be done, but probably shouldn't.


It can't be used for a dynamic structure, that's for sure. On
the other hand, I can imagine it being used for a static tree,
although even then... Maybe it's just me, but when I'm
navigating through a tree, it feels strange to use references,
and not pointers, even if the tree is actually constructed by
the compiler, and you never need to reseat the references.
Also, of course, I'd generally prefer a nul pointer when there
is no corresponding entry (e.g. the parent of the root), rather
than a reference to the object itself.

--
James Kanze (GABI Software) email:(E-Mail Removed)
Conseils en informatique orientée objet/
Beratung in objektorientierter Datenverarbeitung
9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34
 
Reply With Quote
 
 
 
Reply

Thread Tools

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
Error: a nonstatic member reference must be relative to a specific object Computerjunkie C++ 0 04-06-2012 04:10 PM
static/nonstatic data member declaration/definition Jeffrey C++ 7 09-30-2008 09:01 AM
error: invalid use of nonstatic data member The|Godfather C++ 7 10-24-2006 10:26 PM
Returning a pointer to a nonstatic member function? Clay_Culver@yahoo.com C++ 3 11-04-2005 12:47 PM
Re: Can't make a static reference to nonstatic variable con in class X. Pedro López Java 0 10-13-2003 11:15 AM



Advertisments