Topic: Virutal Function Hiding


Author: swf@elsegundoca.ncr.com (Stan Friesen)
Date: 1996/08/23
Raw View
In article <199608191932.MAA04427@taumet.eng.sun.com>,
clamage@pacific-88.Eng.Sun.COM (Steve Clamage) writes:

|> (If your compiler doesn't support namespaces yet, you have to write
|> "forwarding functions" instead, which is not as convenient or efficient.)

I agree it is not as convenient.  It is, however just as efficient.

To whit:

inline int foo(int x) { return Base::foo(x); };

has absolutely NO overhead in the generated code.

--
swf@elsegundoca.ncr.com  sarima@ix.netcom.com

The peace of God be with you.
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: Trevor Yann <ty@kodak.com.au>
Date: 1996/08/24
Raw View
Stan Friesen wrote:
>
> In article <199608191932.MAA04427@taumet.eng.sun.com>,
> clamage@pacific-88.Eng.Sun.COM (Steve Clamage) writes:
>
> |> (If your compiler doesn't support namespaces yet, you have to write
> |> "forwarding functions" instead, which is not as convenient or efficient.)
>
> I agree it is not as convenient.  It is, however just as efficient.
>
> To whit:
>
> inline int foo(int x) { return Base::foo(x); };
>
> has absolutely NO overhead in the generated code.

In the case where foo is a virtual function most compilers will have trouble
inlining the function where the object used is a pointer or a reference.

It is also possible that any function parameters could be copied, involving
construction/destruction of temporary objects.


Trevor Yann
Software Engineer
ty@kau1.kodak.com
---
[ comp.std.c++ is moderated.  To submit articles: Try just posting with your
                newsreader.  If that fails, use mailto:std-c++@ncar.ucar.edu
  comp.std.c++ FAQ: http://reality.sgi.com/austern/std-c++/faq.html
  Moderation policy: http://reality.sgi.com/austern/std-c++/policy.html
  Comments? mailto:std-c++-request@ncar.ucar.edu
]





Author: kanze@gabi-soft.fr (J. Kanze)
Date: 1996/08/26
Raw View
Trevor Yann <ty@kodak.com.au> writes:

> Stan Friesen wrote:
> >
> > In article <199608191932.MAA04427@taumet.eng.sun.com>,
> > clamage@pacific-88.Eng.Sun.COM (Steve Clamage) writes:
> >
> > |> (If your compiler doesn't support namespaces yet, you have to
> > |> write "forwarding functions" instead, which is not as convenient
> > |> or efficient.)
> >
> > I agree it is not as convenient.  It is, however just as efficient.
> >
> > To whit:
> >
> > inline int foo(int x) { return Base::foo(x); };
> >
> > has absolutely NO overhead in the generated code.
>
> In the case where foo is a virtual function most compilers will have trouble
> inlining the function where the object used is a pointer or a reference.
>
> It is also possible that any function parameters could be copied, involving
> construction/destruction of temporary objects.

It is also possible that the compiler, seeing the definition of the
virtual function, simply puts an entry to Base::foo in the vtbl.

Of course, if the function passes a parameter with a constructor by
value, then this is not legal.  The copy of the parameter must take
place (I think).

--
James Kanze           (+33) 88 14 49 00          email: kanze@gabi-soft.fr
GABI Software, Sarl., 8 rue des Francs Bourgeois, 67000 Strasbourg, France
Conseils en informatique industrielle --
                            -- Beratung in industrieller Datenverarbeitung
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: swf@elsegundoca.ncr.com (Stan Friesen)
Date: 1996/08/28
Raw View
In article <321F69AF.77D3@kodak.com.au>, Trevor Yann <ty@kodak.com.au> writes:
|> Stan Friesen wrote:
|> > I agree it is not as convenient.  It is, however just as efficient.
|> >
|> > To whit:
|> >
|> > inline int foo(int x) { return Base::foo(x); };
|> >
|> > has absolutely NO overhead in the generated code.
|>
|> In the case where foo is a virtual function most compilers will have trouble
|> inlining the function where the object used is a pointer or a reference.

I would think a good optimizing compiler would recognize that this was just
an inlined forwarding function, and make the virtual function table for the
derived class point directly to "Base::foo", with appropriate pointer conversion
indicators.

In short it could be "inlined" at the vtable level, not the call level.

--
swf@elsegundoca.ncr.com  sarima@ix.netcom.com

The peace of God be with you.


[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: Bret Pehrson <bretp@strata3d.com>
Date: 1996/08/19
Raw View
I have encountered virtual function hiding several times, and always
wondered why it exists in C++.  I finally decided to find out and found
it mentioned in the Design and Evolution of C++.  It mentions that
virtual function hiding exists to help reduce run-time virtual function
location (or something like that, don't quote me!).  Unfortunately, I
didn't quite understand the reason.

With name mangling and all, I don't quite see why virtual function
hiding exists.  To me, the benefits of a language that *doesn't* have
the virtual function hiding 'problem' of C++ would be worthwhile.

Any answers?...

--
Bret Pehrson        mailto:BretP@strata3d.com
*Please respond to newsgroup unless specified otherwise
--


[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: clamage@pacific-88.Eng.Sun.COM (Steve Clamage)
Date: 1996/08/20
Raw View
In article 15E0@strata3d.com, Bret Pehrson <bretp@strata3d.com> writes:
>I have encountered virtual function hiding several times, and always
>wondered why it exists in C++.

Virtual functions are not special as regards name hiding in C++. As in
probably all block-structured languages, a name declared in an inner scope
hides all instances of that name in all outer scopes. In C++, a derived
class is considered an inner scope relative to all its base classes.

If you declare the name "foo" in a derived class, every name "foo" in
all base classes is hidden. You can refer to a base-class "foo" with
explicit qualification, such as Base::foo.

If this seems controversial so far, you should examine the consequences of
not having this basic rule of scopes. That is, you might as well not have
scopes at all if an inner name doesn't hide an outer name.

Overloading in C++ does not occur across scopes. Otherwise, overloading
would be much more difficult to use. You couldn't safely name a function
without examining all outer scopes in case unintended overloading or
other conflicts occurred. Once again, you would lose the benefit of scopes.

In the case where you deliberately want to add a new overload to
existing base-class functions, you simply bring the base-class functions
into the current scope with a using-declaration. Example:

 class Base {
  ...
  int  foo(int);
  long foo(long);
 };
 class Derived : public Base {
  ...
  using Base::foo; // all "foo"s in Base are now in this scope
  double foo(double); // new overload
 };
 Base b;
 b.foo(2); // calls Base::foo(int)

(If your compiler doesn't support namespaces yet, you have to write
"forwarding functions" instead, which is not as convenient or efficient.)

Whether any or all of these functions are virtual is not relevant to name
hiding. Virtual functions and name hiding are independent issues.
---
Steve Clamage, stephen.clamage@eng.sun.com
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: clamage@pacific-88.Eng.Sun.COM (Steve Clamage)
Date: 1996/08/21
Raw View
In article MAA04427@taumet.eng.sun.com, clamage@pacific-88.Eng.Sun.COM
(Steve Clamage) writes:
>
>In the case where you deliberately want to add a new overload to
>existing base-class functions, you simply bring the base-class functions
>into the current scope with a using-declaration. Example:
>
> class Base {
>  ...
>  int  foo(int);
>  long foo(long);
> };
> class Derived : public Base {
>  ...
>  using Base::foo; // all "foo"s in Base are now in this scope
>  double foo(double); // new overload
> };
> Base b;
> b.foo(2); // calls Base::foo(int)

Oops. Not a very good example. I meant to say:

 Derived d;
 d.foo(2);   // calls Base::foo(int)
 d.foo(2L);  // calls Base::foo(long)
 d.foo(2.0); // calls Derived::foo(double)

Again, if any or all of these are virtual, it doesn't affect what
functions get called in this example.
---
Steve Clamage, stephen.clamage@eng.sun.com
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]