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 

overloading of virtual functions
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
DMan
Guest





PostPosted: Thu Oct 09, 2003 8:40 pm    Post subject: overloading of virtual functions Reply with quote



Hi, All!

Suppose we have the following code:

class A
{
public:
virtual void f(){}
virtual void f( int ){}
};

class B: public A
{
public:
void f( char * ){} //Warinig: B::f(char*) hides virtual functions
A::f() and A::f(int)
};

int main()
{
A * a = new B;
B * b = new B;

a->f(); //ok
a->f( 1 ); //ok

b->f(); //Error: B::f() is not accessible
b->f( 1 ); //Error: B::f(int) is not accessible

delete a; delete b;

return 0;
}

Is this so by C++ standart or it is the problem of specific compiler?

I thought that when I declare void B::f(char*) I just create a new
version of function f (I mean overloading) that comes to B from it's
base class A!
I know one workaround for this situation:
if i bring declaration of A::f() and A::f(int) to the scope of class B
everything will be fine; here is an example of what I mean:

class B: public A
{
public:
using A::f;
void f(char*){};
};

Please, advise.


--
Best regards,
Dmitry Sidorchuk.

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





PostPosted: Fri Oct 10, 2003 7:47 pm    Post subject: Re: overloading of virtual functions Reply with quote



DMan wrote:
Quote:
Hi, All!

Suppose we have the following code:

struct A {
virtual void f(){}
virtual void f( int ){}
};

struct B: A {
void f( char * ){} //Warning: B::f(char*) hides
// virtual functions A::f() and A::f(int)
};
[SNIP]
Is this so by C++ standart or it is the problem of specific compiler?

It is standard.

Quote:
I thought that when I declare void B::f(char*) I just create a new
version of function f (I mean overloading) that comes to B from it's
base class A!
I know one workaround for this situation:
if i bring declaration of A::f() and A::f(int) to the scope of class
B everything will be fine; here is an example of what I mean:

class B: public A
{
public:
using A::f;
void f(char*){};
};

Perfect, AFAIK. And Bjarne Stroustup has this issue on his C++ FAQ page:

http://www.research.att.com/~bs/bs_faq2.html#overloadderived

--
Attila aka WW



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

Back to top
Josephine Schafer
Guest





PostPosted: Fri Oct 10, 2003 7:53 pm    Post subject: Re: overloading of virtual functions Reply with quote




"DMan" <yasidor (AT) yahoo (DOT) com> wrote

Quote:
Hi, All!

Suppose we have the following code:

class A
{
public:
virtual void f(){}
virtual void f( int ){}
};

class B: public A
{
public:
void f( char * ){} //Warinig: B::f(char*) hides virtual functions
A::f() and A::f(int)
};

int main()
{
A * a = new B;
B * b = new B;

a->f(); //ok
a->f( 1 ); //ok

b->f(); //Error: B::f() is not accessible
b->f( 1 ); //Error: B::f(int) is not accessible

delete a; delete b;

return 0;
}

Is this so by C++ standart or it is the problem of specific compiler?

Compiler is correct.
b->f() tries to invoke void f() in class B.
But this function has been hidden by void B::f(char*) and hence the compiler
error .
Note that b is not polymorphic and so the call gets evaluated statically.
Instead if you write
A *p = b;
p->f() //ok

A good compiler would warn you that you have hidden virtual base class function
and may be you wanted to override it.

HTH,
J.Schafer




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

Back to top
Christoph Schulz
Guest





PostPosted: Sat Oct 11, 2003 3:09 pm    Post subject: Re: overloading of virtual functions Reply with quote

Hello!

DMan <yasidor (AT) yahoo (DOT) com> wrote:

Quote:
Hi, All!

Suppose we have the following code:

class A
{
public:
virtual void f(){}
virtual void f( int ){}
};

class B: public A
{
public:
void f( char * ){} //Warinig: B::f(char*) hides virtual
functions A::f() and A::f(int)
};

int main()
{
A * a = new B;
B * b = new B;

a->f(); //ok
a->f( 1 ); //ok

b->f(); //Error: B::f() is not accessible
b->f( 1 ); //Error: B::f(int) is not accessible

delete a; delete b;

return 0;
}

Is this so by C++ standart or it is the problem of specific
compiler?

You're compiler is right. B and A are different scopes, although
B is a subclass of A. Overloading typically only works in a single
scope.

Quote:

I thought that when I declare void B::f(char*) I just create a new
version of function f (I mean overloading) that comes to B from
it's base class A!
I know one workaround for this situation:
if i bring declaration of A::f() and A::f(int) to the scope of
class B everything will be fine; here is an example of what I
mean:

class B: public A
{
public:
using A::f;
void f(char*){};
};


"using A::f" brings the name "f" into the scope of B, hence it
is available fo overloading.

By the way, the virtuality of "f" is not important in the example.
The behaviour (with regard to the semantics of overloading) would
be the same if both A::f methods were non-virtual.

Regards,
Christoph



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

Back to top
Matthias Hofmann
Guest





PostPosted: Sat Oct 11, 2003 3:19 pm    Post subject: Re: overloading of virtual functions Reply with quote


Josephine Schafer <no_spam_josschafer (AT) hotmail (DOT) com> schrieb in im
Newsbeitrag: bm5hrq$ievu7$1 (AT) ID-192448 (DOT) news.uni-berlin.de...
Quote:

"DMan" <yasidor (AT) yahoo (DOT) com> wrote in message
news:bm3mn2$20c$1 (AT) delta (DOT) teleportsv.net...
Hi, All!

Suppose we have the following code:

class A
{
public:
virtual void f(){}
virtual void f( int ){}
};

class B: public A
{
public:
void f( char * ){} //Warinig: B::f(char*) hides virtual functions
A::f() and A::f(int)
};

int main()
{
A * a = new B;
B * b = new B;

a->f(); //ok
a->f( 1 ); //ok

b->f(); //Error: B::f() is not accessible
b->f( 1 ); //Error: B::f(int) is not accessible

delete a; delete b;

return 0;
}

Is this so by C++ standart or it is the problem of specific compiler?

Compiler is correct.
b->f() tries to invoke void f() in class B.
But this function has been hidden by void B::f(char*) and hence the
compiler
error .
Note that b is not polymorphic and so the call gets evaluated statically.
Instead if you write
A *p = b;
p->f() //ok


What do you mean, "b is not polymorphic and so the call gets evaluated
statically"? Class B inherits two virtual functions from class A, so it IS
polymorphic.

Regards,

Matthias




[ 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 Oct 12, 2003 12:43 am    Post subject: Re: overloading of virtual functions Reply with quote

In article <bm7f6c$d8r$1 (AT) news1 (DOT) nefonline.de>, Matthias Hofmann
<hofmann (AT) anvil-soft (DOT) com> writes
Quote:
class A
{
public:
virtual void f(){}
virtual void f( int ){}
};

class B: public A
{
public:
void f( char * ){} //Warinig: B::f(char*) hides virtual
functions
A::f() and A::f(int)
};

int main()
{
A * a = new B;
B * b = new B;

a->f(); //ok
a->f( 1 ); //ok

b->f(); //Error: B::f() is not accessible
b->f( 1 ); //Error: B::f(int) is not accessible

delete a; delete b;

return 0;
}

Is this so by C++ standart or it is the problem of specific
compiler?

Compiler is correct.
b->f() tries to invoke void f() in class B.
But this function has been hidden by void B::f(char*) and hence the
compiler
error .
Note that b is not polymorphic and so the call gets evaluated
statically.
Instead if you write
A *p = b;
p->f() //ok


What do you mean, "b is not polymorphic and so the call gets evaluated
statically"? Class B inherits two virtual functions from class A, so it
IS
polymorphic.

There are two entirely distinct issues with the original code. The first

concerns name hiding. The declaration of an f in B hides all the
declarations of f's in A. To bring the declarations in A into the scope
of B (so overloading will happen) needs a using declaration.

The second issue is whether the compiler needs to use late binding to
determine the function to be called through b. The answer in the case
quoted is that it does not because it can determine the dynamic type of
b at compile time. There is no opportunity to rebind b to some other
object so b really is a pointer to a B.



--
Francis Glassborow ACCU
If you are not using up-to-date virus protection you should not be
reading
this. Viruses do not just hurt the infected but the whole community.


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

Back to top
Matthias Hofmann
Guest





PostPosted: Sun Oct 12, 2003 10:37 pm    Post subject: Re: overloading of virtual functions Reply with quote


----- Original Message -----
From: Francis Glassborow <francis (AT) robinton (DOT) demon.co.uk>
Newsgroups: comp.lang.c++.moderated
Sent: Sunday, October 12, 2003 2:43 AM
Subject: Re: overloading of virtual functions


Quote:
In article <bm7f6c$d8r$1 (AT) news1 (DOT) nefonline.de>, Matthias Hofmann
[email]hofmann (AT) anvil-soft (DOT) com[/email]> writes
class A
{
public:
virtual void f(){}
virtual void f( int ){}
};

class B: public A
{
public:
void f( char * ){} //Warinig: B::f(char*) hides virtual
functions
A::f() and A::f(int)
};

int main()
{
A * a = new B;
B * b = new B;

a->f(); //ok
a->f( 1 ); //ok

b->f(); //Error: B::f() is not accessible
b->f( 1 ); //Error: B::f(int) is not accessible

delete a; delete b;

return 0;
}

Is this so by C++ standart or it is the problem of specific
compiler?

Compiler is correct.
b->f() tries to invoke void f() in class B.
But this function has been hidden by void B::f(char*) and hence the
compiler
error .
Note that b is not polymorphic and so the call gets evaluated
statically.
Instead if you write
A *p = b;
p->f() //ok


What do you mean, "b is not polymorphic and so the call gets evaluated
statically"? Class B inherits two virtual functions from class A, so it
IS
polymorphic.

There are two entirely distinct issues with the original code. The first

concerns name hiding. The declaration of an f in B hides all the
declarations of f's in A. To bring the declarations in A into the scope
of B (so overloading will happen) needs a using declaration.

The second issue is whether the compiler needs to use late binding to
determine the function to be called through b. The answer in the case
quoted is that it does not because it can determine the dynamic type of
b at compile time. There is no opportunity to rebind b to some other
object so b really is a pointer to a B.


I am a little confused know. As far as I see things, the reason that the
compiler does not need to use late binding in the case mentioned is, that
due to the fact that B::f() is hiding all A::f() functions, there is only a
single f() in B, and it is not virtual. Thus, b->f() tries to call the only
available B::f( char* ), and as the arguments do not match, you get an
error.

Please explain how the compiler can "determine the dynamic type of b at
compile time". As far as I know, the dynamic type can never be determined at
compile time when dealing with pointers to class objects. Of course, the
dynamic type is only of interest for virtual functions.

Regards,

Matthias




[ 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: Mon Oct 13, 2003 8:50 pm    Post subject: Re: overloading of virtual functions Reply with quote

In article <bmbe59$j71$1 (AT) news1 (DOT) nefonline.de>, Matthias Hofmann
<hofmann (AT) anvil-soft (DOT) com> writes
Quote:
Please explain how the compiler can "determine the dynamic type of b at
compile time". As far as I know, the dynamic type can never be determined at
compile time when dealing with pointers to class objects. Of course, the
dynamic type is only of interest for virtual functions.

int main(){
base * b_ptr = new derived;
b_ptr->something();
...
}

The compiler can determine that b_ptr necessarily has the dynamic type
derived*. Even when there are intervening statements such determinations
are possible whenever the pointer variable is not passed by reference or
by pointer to another function. Of course we rarely use entirely local
dynamic polymorphic objects, but that is beside the point. The compiler
is allowed to apply static binding wherever it can determine the dynamic
type unambiguously.

--
Francis Glassborow ACCU
If you are not using up-to-date virus protection you should not be reading
this. Viruses do not just hurt the infected but the whole community.


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

Back to top
Matthias Hofmann
Guest





PostPosted: Tue Oct 14, 2003 9:09 am    Post subject: Re: overloading of virtual functions Reply with quote


Francis Glassborow <francis (AT) robinton (DOT) demon.co.uk> schrieb in im Newsbeitrag:
wsy5$SDjMoi$EwRO (AT) robinton (DOT) demon.co.uk...
Quote:
In article <bmbe59$j71$1 (AT) news1 (DOT) nefonline.de>, Matthias Hofmann
[email]hofmann (AT) anvil-soft (DOT) com[/email]> writes
Please explain how the compiler can "determine the dynamic type of b at
compile time". As far as I know, the dynamic type can never be determined
at
compile time when dealing with pointers to class objects. Of course, the
dynamic type is only of interest for virtual functions.

int main(){
base * b_ptr = new derived;
b_ptr->something();
...
}

The compiler can determine that b_ptr necessarily has the dynamic type
derived*. Even when there are intervening statements such determinations
are possible whenever the pointer variable is not passed by reference or
by pointer to another function. Of course we rarely use entirely local
dynamic polymorphic objects, but that is beside the point. The compiler
is allowed to apply static binding wherever it can determine the dynamic
type unambiguously.



Oh, I see. Then the compiler might even be able to inline a virtual function
in this case?

Regards,

Matthias



[ 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: Tue Oct 14, 2003 8:46 pm    Post subject: Re: overloading of virtual functions Reply with quote

In article <bmf78o$kp$1 (AT) news1 (DOT) nefonline.de>, Matthias Hofmann
<hofmann (AT) anvil-soft (DOT) com> writes
Quote:
int main(){
base * b_ptr = new derived;
b_ptr->something();
...
}

The compiler can determine that b_ptr necessarily has the dynamic type
derived*. Even when there are intervening statements such determinations
are possible whenever the pointer variable is not passed by reference or
by pointer to another function. Of course we rarely use entirely local
dynamic polymorphic objects, but that is beside the point. The compiler
is allowed to apply static binding wherever it can determine the dynamic
type unambiguously.



Oh, I see. Then the compiler might even be able to inline a virtual function
in this case?

In simple terms, yes. And I think some do. Note that the only practical
use (that I know of) for this kind of code is to place an object with a
large base footprint off the stack. This has become increasingly
unnecessary as class designers switch to using a PImpl when designing
such types.


--
Francis Glassborow ACCU
If you are not using up-to-date virus protection you should not be reading
this. Viruses do not just hurt the infected but the whole community.


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

Back to top
Ben Hutchings
Guest





PostPosted: Tue Oct 14, 2003 8:59 pm    Post subject: Re: overloading of virtual functions Reply with quote

In article <bm3mn2$20c$1 (AT) delta (DOT) teleportsv.net>, DMan wrote:
Quote:
Hi, All!

Suppose we have the following code:

class A
{
public:
virtual void f(){}
virtual void f( int ){}
};

class B: public A
{
public:
void f( char * ){} //Warinig: B::f(char*) hides virtual functions
A::f() and A::f(int)
};
snip
Is this so by C++ standart or it is the problem of specific compiler?

This is standard behaviour. By the way, it doesn't matter whether the
hidden functions are virtual.

Quote:
I thought that when I declare void B::f(char*) I just create a new
version of function f (I mean overloading) that comes to B from it's
base class A!

But it can be confusing if a function name is overloaded to refer to
functions defined in several different classes. So that is not the
normal behaviour.

Also the warning will appear if you intend to override a virtual
function but get the signature (aside from the name) wrong.

Quote:
I know one workaround for this situation:
if i bring declaration of A::f() and A::f(int) to the scope of class B
everything will be fine; here is an example of what I mean:

class B: public A
{
public:
using A::f;
void f(char*){};
};

Please, advise.

That is the standard and correct way to do what you want.

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

Back to top
Thomas Richter
Guest





PostPosted: Tue Oct 14, 2003 9:07 pm    Post subject: Re: overloading of virtual functions Reply with quote


Hi,

Quote:
The compiler can determine that b_ptr necessarily has the dynamic type
derived*. Even when there are intervening statements such determinations
are possible whenever the pointer variable is not passed by reference or
by pointer to another function. Of course we rarely use entirely local
dynamic polymorphic objects, but that is beside the point. The compiler
is allowed to apply static binding wherever it can determine the dynamic
type unambiguously.


Quote:
Oh, I see. Then the compiler might even be able to inline a virtual function
in this case?

Yes, indeed. Some compilers actually do; IIRC, I've seen the GNU g++
doing this.

So long,
Thomas


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

Back to top
Josephine Schafer
Guest





PostPosted: Wed Oct 15, 2003 12:45 pm    Post subject: Re: overloading of virtual functions Reply with quote

Quote:
Please explain how the compiler can "determine the dynamic type of b at
compile time". As far as I know, the dynamic type can never be determined at
compile time when dealing with pointers to class objects. Of course, the
dynamic type is only of interest for virtual functions.


The question to ask is whether compiler can bind b to some other object at run
time ?
Ans : No

So,
1. What is the static type of b?
Ans :B*
2. What is the dynamic type of b?
Ans :B*

HTH,
J.Schafer



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

Back to top
Matthias Hofmann
Guest





PostPosted: Thu Oct 16, 2003 2:43 pm    Post subject: Re: overloading of virtual functions Reply with quote


Josephine Schafer <no_spam_josschafer (AT) hotmail (DOT) com> schrieb in im
Newsbeitrag: bmde2l$l87am$1 (AT) ID-192448 (DOT) news.uni-berlin.de...
Quote:
Please explain how the compiler can "determine the dynamic type of b at
compile time". As far as I know, the dynamic type can never be
determined at
compile time when dealing with pointers to class objects. Of course,
the
dynamic type is only of interest for virtual functions.


The question to ask is whether compiler can bind b to some other object at
run
time ?
Ans : No

So,
1. What is the static type of b?
Ans :B*
2. What is the dynamic type of b?
Ans :B*


This brings me to an idea. If the compiler can determine the dynamic type in
the case described, then the following could theorectically work:

struct A {};

struct B : public A
{
void f();
};

int main()
{
A* pa = new B;

pa->f(); // Error, there's no f() in A!
}

Actually, the call to A::f() could work, making a dynamic_cast redundant.
But of course, optimizations should not undermine legality of code...

Regards,

Matthias




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

Back to top
Josephine Schafer
Guest





PostPosted: Fri Oct 17, 2003 11:19 am    Post subject: Re: overloading of virtual functions Reply with quote


"Matthias Hofmann" <hofmann (AT) anvil-soft (DOT) com> wrote

Quote:

Josephine Schafer <no_spam_josschafer (AT) hotmail (DOT) com> schrieb in im
Newsbeitrag: bmde2l$l87am$1 (AT) ID-192448 (DOT) news.uni-berlin.de...
Please explain how the compiler can "determine the dynamic type of b at
compile time". As far as I know, the dynamic type can never be
determined at
compile time when dealing with pointers to class objects. Of course,
the
dynamic type is only of interest for virtual functions.


The question to ask is whether compiler can bind b to some other object at
run
time ?
Ans : No

So,
1. What is the static type of b?
Ans :B*
2. What is the dynamic type of b?
Ans :B*


This brings me to an idea. If the compiler can determine the dynamic type in
the case described, then the following could theorectically work:

struct A {};

struct B : public A
{
void f();
};

int main()
{
A* pa = new B;

pa->f(); // Error, there's no f() in A!
}

Actually, the call to A::f() could work, making a dynamic_cast redundant.
But of course, optimizations should not undermine legality of code...

See in the case you have quoted compiler can clearly see that the static type of
pa is A*.
It can also see that it can rebind it to some other object at run time.
But as far as the compilation is concerned it will look for f() in struct A only
i.e using the static type only.
Hence you get the error.

HTH,
J.Schafer

(Remove no_spam_ to contact by mail.)






[ 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.