Topic: Virtual Private Class Member Functions
Author: maxtal@physics.su.OZ.AU (John Max Skaller)
Date: Tue, 31 May 1994 15:09:51 GMT Raw View
In article <DOUG.94May24111533@monet.ads.com> doug@monet.ads.com (Doug Morgan) writes:
>Another nice thing about public nonvirtuals inline calling private
>virtuals is that you needn't wait for your favorite compiler vendors
>to all implement covariant type returns for virtual functions. You
>can "do it yourself" on the nonvirtual functions (e.g., by using down
>casts inside the public inline nonvirtual members that call the
UPCASTS! The root of a the tree is at the bottom
of the paper and is the complete object. You cast UP to bases <grin>
>private virtual members). You can even implement covariant returns of
>actual objects, not just pointers and references (as John has pointed
>out is a safe thing to do, but not allowed in the current ANSI
>thinking about virtual members). You will likely have to create a
>private virtual function of a brand new name (to prevent slicing) and
>redefine the old private virtual too, but that may not be too bad.
Wow. I've actually been building models of inheritance,
it never occurred to me to use the technique in real programs!
Hm. This is worth trying, if only to prove it can be implemented
easily.
class A : B;
class X { virtual A f(); public: A F(){return f();} };
class Y : X {
virtual B g(); // covariant
virtual A f() { return g(); }
public:
B F() { return g(); }
};
I see. The covariant return is only useful when called
with the right static type. Its just overloading.
But the call through the base X is still polymorphic.
Nice. Thanks!
This makes me wonder why the committee did not choose to support
covariant value returns. Is there something wrong with
the above technique implemented by a compiler automatically?
--
JOHN (MAX) SKALLER, INTERNET:maxtal@suphys.physics.su.oz.au
Maxtal Pty Ltd, CSERVE:10236.1703
6 MacKay St ASHFIELD, Mem: SA IT/9/22,SC22/WG21
NSW 2131, AUSTRALIA
Author: kinnucan@hq.ileaf.com (Paul Kinnucan)
Date: Fri, 27 May 1994 17:55:57 GMT Raw View
In article <CqFq2p.JB5@ucc.su.OZ.AU> maxtal@physics.su.OZ.AU (John Max Skaller) writes:
In article <KINNUCAN.94May25153416@candide.hq.ileaf.com> kinnucan@hq.ileaf.com (Paul Kinnucan) writes:
>
>Doesn't private virtual inheritance prevent reuse of a base method in
>the derived method?
Yes, it prevent calling the base virtual directly.
>If so, this would seem to be a drawback.
That depends on whether you want to prevent calling the
base virtual directly. If you read some of the previous posts
in this thread you would see some reasons why you may want to do
this outlined.
The reasons stated for the desirability of private virtual inheritance
were abstract and theoretical. I have difficulty envisioning a concrete
application where it would be desirable to let a descendant class override, but
not incorporate, a base method. I'd be very interested to see a specific
example of the use of PriVI presented here along with a justification for
its use in that application.
As a potential user of a class library, I'd
be concerned that private virtual inheritance is being used by the designer
to cover up a poorly thought-out and/or implemented design. In essence, the designer
could be saying: "If you don't like my method, yes, you can override it, but if you
have to duplicate the code in my method in the process, well that's tough because I want to
reserve the right (through PriVI) to change the spec or the implementation whenever I like
(because I don't have the time to really think this design out, or implement it well,
or I'm a perfectionist, or whatever my excuse of the moment is)."
ProVI, on the other hand, at least provides the class designer with an incentive
to give sufficient thought to the design of a class to be confident
that the logical behavior of the base methods will not change, though the
implementations might (i.e., it might get faster and smaller), and therefore ensure that it's
safe for the base methods to be reused by people who need to specialize the class.
I think it's incumbent on the class designer to make a good case for
the use of PriVI in a particular app, because, whatever its benefits, it does block code reuse,
ostensibly a major benefit of C++ (and one that I take advantage of all the
time in my use of class libraries).
IMHO, a good case has yet to be made for PriVI in this thread.
- Paul
P.S. Thanks for stimulating a very interesting and thought-provoking
thread.
Author: mikey@mcs.com (Mike Young)
Date: Fri, 27 May 1994 00:48:12 Raw View
In article <9414313.5637@mulga.cs.mu.OZ.AU> fjh@munta.cs.mu.OZ.AU (Fergus Henderson) writes:
>From: fjh@munta.cs.mu.OZ.AU (Fergus Henderson)
>Subject: Re: Virtual Private Class Member Functions
>Date: Mon, 23 May 1994 03:22:01 GMT
>achoi@soda.berkeley.edu (Andrew Choi) writes:
>> Has anyone actually tried to use a virtual private class member
>>function????
>Yes.
>>Is it an oversight of the committee to allow such a feature???
>No.
>>Or is it there because there are actually some use for it???
>The fact that a combination of features (e.g. private & virtual) does
>not seem useful is not a good reason to disallow it.
----------
The private virtual is called from a member function in the base. Derived
classes typically override the private virtual to provide the desired
behavior. For example:
class fooBase
{
private:
virtual void bar( )
{ cout << "fooBase::bar()";
}
public:
doSomething( )
{ bar( );
}
};
class fooDerived
{
void bar ( )
{ cout << "fooDerived::bar()";
};
Author: mikey@mcs.com (Mike Young)
Date: Fri, 27 May 1994 00:54:34 Raw View
In article <Cq9A8u.DLC@ucc.su.OZ.AU> maxtal@physics.su.OZ.AU (John Max Skaller) writes:
> ((Base*)d) ->mem(); // OK, base method is public
I would've written that as:
d->Base::mem();
Its meaning clearer, IMO, but I'm suddenly uncertain if it's equivalent in
the sense of privateness. (?)
Mike.
Author: doug@monet.ads.com (Doug Morgan)
Date: 27 May 94 10:39:42 Raw View
In article <CqFquw.M1B@ucc.su.OZ.AU> maxtal@physics.su.OZ.AU (John Max Skaller) writes:
>In article <DOUG.94May25232400@deimos.ads.com> doug@deimos.ads.com (Doug Morgan) writes:
>>
>>... More fundamental, I think, is your original point that
>>virtuals are an implementation detail that the user shouldn't
>>necessarily be exposed to.
>Could be: how do you judge what is "more fundamental"?
That's just too difficult to answer. I'm embarrased to find it hard
to back up my highfalutin phrase.
>Yes, virtuals are just a special case of delegation,
>use of function pointers, and other dispatching techniques.
>Including "none" <grin>
An important case, no grin needed.
>>Also, another interesting organization for many purposes could be to
>>make all properties be global functions and all axioms be public
>>member functions....
>Yes, I suggested it, and Andrew Koenig jumped on me.
>He had a very good argument which I would summarise as saying
>that you dont want to fix the "representation" to be a basis
>because that makes changing the basis difficult and visible.
I think with namespaces, there isn't a really good case for jumping on
you. (Even without namespaces, I don't think there was.) With
namespaces, a developer can layer global functions even more precisely
(more levels and with more control of what goes into each level) than
normal access levels of class members. It is easier to circumvent
compiler-stopping restrictions, but it still should be reasonably easy
to document who should use what namespaces for what purposes, to
follow the rules, and to recognize when someone steps outside their
proper set of namespaces or access to class members. I don't think a
strong argument can be made to say one of the two following
organizations are more "stable." Other discriminators could still be
quite important.
Axioms Immediate Properties Less Immediate Properties etc.
------ -------------------- -------------------------
1 private public global ...
2 public global-namespace1 global-namespace2 ...
>>Anyway, being a fan of
>>multimethods and leaning toward encapsulation by syntactic hints and
>>audit tools, such a structure looks pretty reasonable.
>More sophisticated structures exist. For example,
>class A has a large set of pure virtuals, and you derive
>from it a particular axiom scheme by defining all but
>the chosen basis in terms of the basis: that class,
>A1, is but one representation of the class A.
>
>class Colour {
>virtual int Red()const =0;
>virtual int Blue()const =0;
>virtual int Green()const =0;
>virtual int Hue()const =0;
>virtual int Saturation()const =0;
>virtual int Value()const =0;
>};
>
>class RGB : public virtual Colour {
>int Hue()const;
>int Saturation()const;
>int Value()const;
>};
>
>class HSV : public virtual Colour {
>int Red()const;
>int Blue()const;
>int Green()const;
>};
This does look like it would enhance stability and code reuse for the
properties. I wonder a bit whether properties calling other
properties couldn't be organized for similar stability/ruse, with
perhaps fewer total functions. However, without working through some
details I don't know how real that possibility might be.
One comment on the specific example: a weird pre/postfix on the axiom
names would allow the nice names to be public (maybe the public names
would be lower case versions?).
Doug
--------------------------------------------------------------------
Doug Morgan, doug@ads.com, (415) 960-7444
Advanced Decision Systems (a division of Booz-Allen & Hamilton Inc.)
1500 Plymouth St., Mountain View, CA 94043-1230
--------------------------------------------------------------------
Author: maxtal@physics.su.OZ.AU (John Max Skaller)
Date: Fri, 27 May 1994 00:16:00 GMT Raw View
In article <KINNUCAN.94May25153416@candide.hq.ileaf.com> kinnucan@hq.ileaf.com (Paul Kinnucan) writes:
>
>Doesn't private virtual inheritance prevent reuse of a base method in
>the derived method?
Yes, it prevent calling the base virtual directly.
>If so, this would seem to be a drawback.
That depends on whether you want to prevent calling the
base virtual directly. If you read some of the previous posts
in this thread you would see some reasons why you may want to do
this outlined.
--
JOHN (MAX) SKALLER, INTERNET:maxtal@suphys.physics.su.oz.au
Maxtal Pty Ltd, CSERVE:10236.1703
6 MacKay St ASHFIELD, Mem: SA IT/9/22,SC22/WG21
NSW 2131, AUSTRALIA
Author: maxtal@physics.su.OZ.AU (John Max Skaller)
Date: Fri, 27 May 1994 00:32:56 GMT Raw View
In article <DOUG.94May25232400@deimos.ads.com> doug@deimos.ads.com (Doug Morgan) writes:
>
>I agree with the idea that axioms should be private, but am not so
>sure that this idea is fundamentally related to how "virtual" should
>be used.
I think you are right in principle, yes. The connection
with virtuals comes from the notion that axiomatic (formal) systems
are abstractions, and one uses abstract classes to represent them.
>I think the idea would apply even if C++ had no virtual
>functions. More fundamental, I think, is your original point that
>virtuals are an implementation detail that the user shouldn't
>necessarily be exposed to.
Could be: how do you judge what is "more fundamental"?
I see virtuals as just one of many ways of
>achieving dispatch on the first argument.
Yes, virtuals are just a special case of delegation,
use of function pointers, and other dispatching techniques.
Including "none" <grin>
>Also, another interesting organization for many purposes could be to
>make all properties be global functions and all axioms be public
>member functions. I think you may have recommended this structure way
>back (I don't remember, maybe it was Piercarlo Grande, or somebody who
>posted about his own C-like OOPL?).
Yes, I suggested it, and Andrew Koenig jumped on me.
He had a very good argument which I would summarise as saying
that you dont want to fix the "representation" to be a basis
because that makes changing the basis difficult and visible.
>Anyway, being a fan of
>multimethods and leaning toward encapsulation by syntactic hints and
>audit tools, such a structure looks pretty reasonable.
More sophisticated structures exist. For example,
class A has a large set of pure virtuals, and you derive
from it a particular axiom scheme by defining all but
the chosen basis in terms of the basis: that class,
A1, is but one representation of the class A.
class Colour {
virtual int Red()const =0;
virtual int Blue()const =0;
virtual int Green()const =0;
virtual int Hue()const =0;
virtual int Saturation()const =0;
virtual int Value()const =0;
};
class RGB : public virtual Colour {
int Hue()const;
int Saturation()const;
int Value()const;
};
class HSV : public virtual Colour {
int Red()const;
int Blue()const;
int Green()const;
};
--
JOHN (MAX) SKALLER, INTERNET:maxtal@suphys.physics.su.oz.au
Maxtal Pty Ltd, CSERVE:10236.1703
6 MacKay St ASHFIELD, Mem: SA IT/9/22,SC22/WG21
NSW 2131, AUSTRALIA
Author: maxtal@physics.su.OZ.AU (John Max Skaller)
Date: Fri, 27 May 1994 08:30:45 GMT Raw View
In article <mikey.8.0000E8DD@mcs.com> mikey@mcs.com (Mike Young) writes:
>In article <Cq9A8u.DLC@ucc.su.OZ.AU> maxtal@physics.su.OZ.AU (John Max Skaller) writes:
>
>> ((Base*)d) ->mem(); // OK, base method is public
>
>I would've written that as:
>
> d->Base::mem();
>
>Its meaning clearer, IMO, but I'm suddenly uncertain if it's equivalent in
>the sense of privateness. (?)
I'm uncertain if its SEMANTICALLY equivalent. Normally,
using a scope override operator disables the virtual call mechanism.
--
JOHN (MAX) SKALLER, INTERNET:maxtal@suphys.physics.su.oz.au
Maxtal Pty Ltd, CSERVE:10236.1703
6 MacKay St ASHFIELD, Mem: SA IT/9/22,SC22/WG21
NSW 2131, AUSTRALIA
Author: maxtal@physics.su.OZ.AU (John Max Skaller)
Date: Wed, 25 May 1994 14:01:38 GMT Raw View
In article <DOUG.94May24094906@monet.ads.com> doug@monet.ads.com (Doug Morgan) writes:
>In article <Cq9A8u.DLC@ucc.su.OZ.AU> maxtal@physics.su.OZ.AU (John Max Skaller) writes:
>>
>>Why is this 'correct' and public virtuals wrong?
>>
>>Because it allows you to change the set of specialisations
>>you have, and prevents dumb programmers explicitly
>>accessing a method which is an implementation detail
>>and part of the specialisation of the representation:
>>that is, I as a library designer, might want to remove
>>the method (because it turned out to be not enough faster
>>to warrant the hassle maintaining it, or the extra code
>>space required).
>
>I came to this same conclusion, for the same reasons, plus one more.
>If you want to make a member function for some derived class run very
>fast, it has to be inline.
>However, if the public member starts out in the base class as an
>inline call to a private virtual, it can be overriden in derived
>classes with other inline operations, and have the inlining actually
>done (if the declarations are right).
Why, thats an interesting observation! It only works
for calls through the derived class -- but thats right!
You use your static knowledge of the type to enhance efficiency.
>I find that libraries written without using private
>virtuals are messier than necessary to extend.
Thanks for that data. This _ought_ to be the case,
otherwise the theory that says loose coupling is good is suspect.
Here's another way to look at these advantages of
using private virtuals: suppose you have some properties
of an entity: P1, P2, .. Pn. Typically, these properties are
related, and one can often find a smaller set of properties
A1, A2 .. Am, which form a basis from which P1..Pn can be
derived. A1..Am are called axioms, and can conveniently be
represented as private virtuals.
As in most mathematical systems, there is more
than one way to choose a set of axioms. I happen to know,
for example, there are three "standard" axiomatisations
of topological spaces; which ever set you start from, you
end up with the same common set of basic properties
after preliminary lemmas are proved.
So the axiom scheme itself is really at the
"representation" level. I owe part of this analysis
to comments by Andrew Koenig that chosing members
as the axioms and making everything else global is
not very stable if you want to change the axiom scheme.
The basic (redundant) methods are the public non-virtuals.
This facilitates changing the private virtuals, which may
be some minimum set of axioms, or may be some larger set.
As Doug then noted, we can specialise in derived
classes not only polymorphically, but statically as well.
--------------------------------------------------------------
Is C++ a good language? Well, the fact that OO is
not well understood, and generally C++ does NOT try to
force a style on you, is one of its best attributes.
Without changing the language much, we may well
be able to write better and better C++ programs as we
learn how to do so.
When we know much of what there is to know about C++,
it will be time to move on to the next language.
We are not there yet. The biggest problem with C++ is not that its
complex or C compatible. Its that not enough people know enough
about it to train others. Most of us are still learning.
--
JOHN (MAX) SKALLER, INTERNET:maxtal@suphys.physics.su.oz.au
Maxtal Pty Ltd, CSERVE:10236.1703
6 MacKay St ASHFIELD, Mem: SA IT/9/22,SC22/WG21
NSW 2131, AUSTRALIA
Author: doug@monet.ads.com (Doug Morgan)
Date: 24 May 94 09:49:06 Raw View
In article <Cq9A8u.DLC@ucc.su.OZ.AU> maxtal@physics.su.OZ.AU (John Max Skaller) writes:
>
>Why is this 'correct' and public virtuals wrong?
>
>Because it allows you to change the set of specialisations
>you have, and prevents dumb programmers explicitly
>accessing a method which is an implementation detail
>and part of the specialisation of the representation:
>that is, I as a library designer, might want to remove
>the method (because it turned out to be not enough faster
>to warrant the hassle maintaining it, or the extra code
>space required).
I came to this same conclusion, for the same reasons, plus one more.
If you want to make a member function for some derived class run very
fast, it has to be inline. (Say Set at some point becomes specialized
to SingletonSet where most members should be lightning fast.)
However, once virtual is specified for a member function, the compiler
is rarely free to inline any derived versions no matter what the
declared object type (because objects of unknown further derived types
may be passed in to functions from anywhere on the "outside").
However, if the public member starts out in the base class as an
inline call to a private virtual, it can be overriden in derived
classes with other inline operations, and have the inlining actually
done (if the declarations are right). Of course, at that point in the
class derivation, the implementation is fully exposed to the user and
further derivation is under strong constraints to make all calls to
the public member consistent. However, when the implementation
details of a derived class becomes sufficiently constrained, exposing
some aspect of the implementation may be exactly what you are trying
to do.
Using private virtuals seems appropriate for lots of C++ code (I think
it is generally the "right thing" to do), yet is really pretty rarely
used. One consequence of not using private virtuals can be having to
introduce extra public member functions that are almost (but not
quite) redundant. I find that libraries written without using private
virtuals are messier than necessary to extend.
Doug
--------------------------------------------------------------------
Doug Morgan, doug@ads.com, (415) 960-7444
Advanced Decision Systems (a division of Booz-Allen & Hamilton Inc.)
1500 Plymouth St., Mountain View, CA 94043-1230
--------------------------------------------------------------------
Author: kinnucan@hq.ileaf.com (Paul Kinnucan)
Date: Wed, 25 May 1994 15:34:42 GMT Raw View
In article <DOUG.94May24094906@monet.ads.com> doug@monet.ads.com (Doug Morgan) writes:
>In article <Cq9A8u.DLC@ucc.su.OZ.AU> maxtal@physics.su.OZ.AU (John Max Skaller) writes:
>>Why is this 'correct' and public virtuals wrong?
>> ...
> [... agree and expand ...]
Another nice thing about public nonvirtuals inline calling private
virtuals is that you needn't wait for your favorite compiler vendors
to all implement covariant type returns for virtual functions. You
can "do it yourself" on the nonvirtual functions (e.g., by using down
casts inside the public inline nonvirtual members that call the
private virtual members). You can even implement covariant returns of
actual objects, not just pointers and references (as John has pointed
out is a safe thing to do, but not allowed in the current ANSI
thinking about virtual members). You will likely have to create a
private virtual function of a brand new name (to prevent slicing) and
redefine the old private virtual too, but that may not be too bad.
Doesn't private virtual inheritance prevent reuse of a base method in the derived
method? If so, this would seem to be a drawback.
- Paul
Author: doug@deimos.ads.com (Doug Morgan)
Date: 25 May 94 23:24:00 Raw View
In article <CqD2yr.9Mz@ucc.su.OZ.AU> maxtal@physics.su.OZ.AU (John Max Skaller) writes:
>In article <DOUG.94May24094906@monet.ads.com> doug@monet.ads.com (Doug Morgan) writes:
>>In article <Cq9A8u.DLC@ucc.su.OZ.AU> maxtal@physics.su.OZ.AU (John Max Skaller) writes:
>>>
>>>Why is this 'correct' and public virtuals wrong?
>>>...
>>[... agree and expand ...]
>[... double agree and further expand on axiom structures ...]
I agree with the idea that axioms should be private, but am not so
sure that this idea is fundamentally related to how "virtual" should
be used. I think the idea would apply even if C++ had no virtual
functions. More fundamental, I think, is your original point that
virtuals are an implementation detail that the user shouldn't
necessarily be exposed to. I see virtuals as just one of many ways of
achieving dispatch on the first argument. Why should "virtual," with
its attendant implementation details and limitations, be forced on
someone who just wants call a reasonably named function and have the
"right thing" always happen? Like any implementation detail, virtual
is often best left private.
Also, another interesting organization for many purposes could be to
make all properties be global functions and all axioms be public
member functions. I think you may have recommended this structure way
back (I don't remember, maybe it was Piercarlo Grande, or somebody who
posted about his own C-like OOPL?). Anyway, being a fan of
multimethods and leaning toward encapsulation by syntactic hints and
audit tools, such a structure looks pretty reasonable.
Doug
--------------------------------------------------------------------
Doug Morgan, doug@ads.com, (415) 960-7444
Advanced Decision Systems (a division of Booz-Allen & Hamilton Inc.)
1500 Plymouth St., Mountain View, CA 94043-1230
--------------------------------------------------------------------
Author: doug@deimos.ads.com (Doug Morgan)
Date: 25 May 94 23:34:27 Raw View
In article <KINNUCAN.94May25153416@candide.hq.ileaf.com> kinnucan@hq.ileaf.com (Paul Kinnucan) writes:
>In article <DOUG.94May24094906@monet.ads.com> doug@monet.ads.com (Doug Morgan) writes:
>>Another nice thing about public nonvirtuals inline calling private
>>virtuals is that ....
>
>Doesn't private virtual inheritance prevent reuse of a base method in the derived
>method? If so, this would seem to be a drawback.
>
>- Paul
Good point. It does make it hard (impossible?) to call the explicitly
base-qualified function in a derived method. With some foresight, you
could make that function available as a differently named protected or
public non-virtual member. However, that is extra work that wouldn't
be needed when using public virtuals.
Doug
--------------------------------------------------------------------
Doug Morgan, doug@ads.com, (415) 960-7444
Advanced Decision Systems (a division of Booz-Allen & Hamilton Inc.)
1500 Plymouth St., Mountain View, CA 94043-1230
--------------------------------------------------------------------
Author: jkwlee@csd.hku.hk (Joseph K.W. LEE)
Date: Thu, 19 May 1994 08:44:17 GMT Raw View
Andrew Choi (achoi@soda.berkeley.edu) wrote:
: Hi netters,
:
: Has anyone actually tried to use a virtual private class member
: function???? Is it an oversight of the committee to allow such
: a feature??? Or is it there because there are actually some use
: for it???
:
: Anyway, thanks for your response.
:
: -- Andrew Choi (achoi@soda.berkeley.edu)
:
Though I can't construct a meaningful use of such feature, the following
code may show that this feature can be used in a meaningful manner.
;-)
friend to
D -----------> A
/ \
B C
#include <iostream.h>
class A {
friend D;
private:
virtual void foo() { cout << "I'm a fool\n"; }
};
class B : public A {
public:
virtual void foo() { cout << "I'm the son of fool\n"; }
};
class C : public A {
// nothing more than a fool :-P
};
class D {
public:
void foo_a(A* a) { a->foo(); }
};
int main()
{
A* a = new A;
B* b = new B;
C* c = new C;
D d;
d.foo_a(a); // I'm a fool
d.foo_a(b); // I'm the son of fool
d.foo_a((A*) b); // I'm the son of fool
d.foo_a((A*) c); // I'm a fool
c->foo(); // main() cannot access A::foo(), private mbr
return 1;
}
Now you can see that the use of A::foo() is allowed only in the
scope of D (or any friend of A), and within this context it may
in fact invoke B::foo() due to polymorphism.
In real life examples, ABC represent objects that are used to
implement objects of class D. So their uses outside D are usually
[partially] restricted. e.g. D is a tree object while A, B, C are
different kinds of tree node objects
--
Cheers.
- joseph
If the facts don't fit the theory, change the facts.
Albert Einstein
Author: mikey@mcs.com (Mike Young)
Date: Fri, 27 May 1994 01:04:57 Raw View
In article <2rr8k9$6ch@f111.iassf.easams.com.au> rjl@f111.iassf.easams.com.au (Rohan LENARD) writes:
>From: rjl@f111.iassf.easams.com.au (Rohan LENARD)
>Subject: Re: Virtual Private Class Member Functions
>Date: 24 May 1994 07:53:13 +1000
>In article <Cq9A8u.DLC@ucc.su.oz.au>,
>John Max Skaller <maxtal@physics.su.OZ.AU> wrote:
>>
>>Would I REQUIRE all virtuals to be private?
>> ...
>Why not just use protected ones and be done with it. At least then the
>specialisation doesn't have to call the do_axiom() function to get at the
>axiom function (whether it is specialised or not).
There are times when only the base should know about axiom(). If we extend the
examples to show multiple complex methods that in turn call axiom, it becomes
clearer that this partitioning makes maintenance EASIER, not harder. axiom is
concerned with only one task, not the context of that task. By virtue of it's
privateness, we can more easily ensure that its pre-conditions are met. The
simple example of a single base method acting only as a front for the private
virtual doesn't do this partitioning justice.
Mike.
Author: fjh@munta.cs.mu.OZ.AU (Fergus Henderson)
Date: Mon, 23 May 1994 03:22:01 GMT Raw View
achoi@soda.berkeley.edu (Andrew Choi) writes:
> Has anyone actually tried to use a virtual private class member
>function????
Yes.
>Is it an oversight of the committee to allow such a feature???
No.
>Or is it there because there are actually some use for it???
The fact that a combination of features (e.g. private & virtual) does
not seem useful is not a good reason to disallow it.
--
Fergus Henderson - fjh@munta.cs.mu.oz.au
Author: anders@nork.auc.dk (Anders Pedersen)
Date: 23 May 1994 09:45:11 GMT Raw View
>>>>> "FH" == Fergus Henderson <fjh@munta.cs.mu.OZ.AU> writes:
FH> achoi@soda.berkeley.edu (Andrew Choi) writes:
>> Has anyone actually tried to use a virtual private class member
>> function????
FH> Yes.
>> Is it an oversight of the committee to allow such a feature???
FH> No.
>> Or is it there because there are actually some use for it???
FH> The fact that a combination of features (e.g. private &
FH> virtual) does not seem useful is not a good reason to disallow
FH> it.
I have found it useful in combination with friends.
--Anders.
--
anders@nork.auc.dk
This posting was typed in front of a large studio audience.
Author: maxtal@physics.su.OZ.AU (John Max Skaller)
Date: Mon, 23 May 1994 12:48:30 GMT Raw View
In article <9414313.5637@mulga.cs.mu.OZ.AU> fjh@munta.cs.mu.OZ.AU (Fergus Henderson) writes:
>achoi@soda.berkeley.edu (Andrew Choi) writes:
>
>> Has anyone actually tried to use a virtual private class member
>>function????
>
>Yes.
YES! Its the CORRECT way to do it! <grin>
>
>>Is it an oversight of the committee to allow such a feature???
>
>No.
Dont be too sure. Some very distinguished members
proposed banning it!
>
>>Or is it there because there are actually some use for it???
>
>The fact that a combination of features (e.g. private & virtual) does
>not seem useful is not a good reason to disallow it.
Private virtuals are not onbly useful, but in my opinion
they are probably the correct way to use virtual functions.
Here's the argument: first, when you override a virtual
function, you are just specialising an existant function
or implementin a pure one. In either case, its an implementation
detail and of no consequence to the public. They should NOT
know whether or not a method has been specialised. The overriding
virtual should, in principle, be HIDDEN and not just private.
Well, how do you call it? Through the base of course.
But, I dont WANT to cast:
d->mem(); // inacessible: derived method is private
((Base*)d) ->mem(); // OK, base method is public
Thats right! The base virtual should be private too.
But HOW DO I CALL IT????
You use a PUBLIC nonvirtual method of the base class.
class Base {
virtual void axiom()=0;
public:
do_axiom() { axiom(); }
};
class Derived : public virtulal Base {
void axiom(){ .. implementation details }
};
The biggest problem with this is that you are ALLOWED to
override a private virtual with a public one!
Why is this 'correct' and public virtuals wrong?
Because it allows you to change the set of specialisations
you have, and prevents dumb programmers explicitly
accessing a method which is an implementation detail
and part of the specialisation of the representation:
that is, I as a library designer, might want to remove
the method (because it turned out to be not enough faster
to warrant the hassle maintaining it, or the extra code
space required).
Would I REQUIRE all virtuals to be private?
Heck no, that would break almost all my older code!
And use of public virtuals is not always wrong.
But private virtuals MIGHT JUST BE WORTH RETAINING IN THE LANGUAGE.
Because SOME of my code uses them. And I'm happy with that code--
more so than some of my older code :-)
Moral: In C++, nothing is clear cut.
--
JOHN (MAX) SKALLER, INTERNET:maxtal@suphys.physics.su.oz.au
Maxtal Pty Ltd, CSERVE:10236.1703
6 MacKay St ASHFIELD, Mem: SA IT/9/22,SC22/WG21
NSW 2131, AUSTRALIA
Author: pete@genghis.interbase.borland.com (Pete Becker)
Date: Mon, 23 May 1994 16:17:25 GMT Raw View
In article <9414313.5637@mulga.cs.mu.oz.au>,
Fergus Henderson <fjh@munta.cs.mu.OZ.AU> wrote:
>achoi@soda.berkeley.edu (Andrew Choi) writes:
>
>> Has anyone actually tried to use a virtual private class member
>>function????
>
>Yes.
>
>>Is it an oversight of the committee to allow such a feature???
>
>No.
>
>>Or is it there because there are actually some use for it???
>
>The fact that a combination of features (e.g. private & virtual) does
>not seem useful is not a good reason to disallow it.
>
Or, more strongly, the fact that a combination of features does not
seem useful does not mean that it is not useful.
-- Pete
Author: pete@genghis.interbase.borland.com (Pete Becker)
Date: Mon, 23 May 1994 16:23:07 GMT Raw View
In article <ANDERS.94May23114511@tuborg.nork.auc.dk>,
Anders Pedersen <anders@nork.auc.dk> wrote:
>>>>>> "FH" == Fergus Henderson <fjh@munta.cs.mu.OZ.AU> writes:
>
>FH> achoi@soda.berkeley.edu (Andrew Choi) writes:
>>> Has anyone actually tried to use a virtual private class member
>>> function????
>
>FH> Yes.
>
>>> Is it an oversight of the committee to allow such a feature???
>
>FH> No.
>
>>> Or is it there because there are actually some use for it???
>
>FH> The fact that a combination of features (e.g. private &
>FH> virtual) does not seem useful is not a good reason to disallow
>FH> it.
>
>I have found it useful in combination with friends.
>
I have found it useful without friends. A private virtual function
can be called by a member of the class that defines it, and can be overridden
by a class derived from that class.
class Sample
{
public:
void Show() const;
private:
virtual string GetData() const = 0;
};
void Sample::Show() const
{
cout << "Data is '" << GetData() << '\'' << endl;
}
class Derived : public Sample
{
public:
Derived() : Text("sample text") {}
private:
string Text;
string GetData() const { return Text; }
};
-- Pete
Author: rjl@f111.iassf.easams.com.au (Rohan LENARD)
Date: 24 May 1994 07:53:13 +1000 Raw View
In article <Cq9A8u.DLC@ucc.su.oz.au>,
John Max Skaller <maxtal@physics.su.OZ.AU> wrote:
>
>Would I REQUIRE all virtuals to be private?
>Heck no, that would break almost all my older code!
>And use of public virtuals is not always wrong.
>
Why not just use protected ones and be done with it. At least then the
specialisation doesn't have to call the do_axiom() function to get at the
axiom function (whether it is specialised or not).
Regards,
Rohan
--
------------------------------------------------------------------------
rjl@iassf.easams.com.au |
Rohan Lenard | .sig on holiday
+61-2-367-4555 |
Author: maxtal@physics.su.OZ.AU (John Max Skaller)
Date: Tue, 24 May 1994 09:40:56 GMT Raw View
In article <2rr8k9$6ch@f111.iassf.easams.com.au> rjl@f111.iassf.easams.com.au (Rohan LENARD) writes:
>In article <Cq9A8u.DLC@ucc.su.oz.au>,
>John Max Skaller <maxtal@physics.su.OZ.AU> wrote:
>>
>>Would I REQUIRE all virtuals to be private?
>>Heck no, that would break almost all my older code!
>>And use of public virtuals is not always wrong.
>>
>
>Why not just use protected ones and be done with it.
I may not want to allow the derived class to call it either.
Really, I dont want the derived class to be able to call its own
specialisation, if it supplies one, but that cant be enforced.
Vectoring all the calls to a (possibly inline) non-static non-virtual
base class method is an example of loose coupling. There is a single
fixed access path. To debug it, for example, a single trap
or output statement in the non-static non-virtual base method is
all that is needed. I'd LIKE to guarrantee it trapped all calls.
>At least then the
>specialisation doesn't have to call the do_axiom() function to get at the
>axiom function (whether it is specialised or not).
If you mean the derived class -- I may want it to.
If you mean the overriding virtual of the derived class, it had
better NOT because that would be a recursion. (Unless that is
desired, in which case calling yourself is an option I suppose)
--
JOHN (MAX) SKALLER, INTERNET:maxtal@suphys.physics.su.oz.au
Maxtal Pty Ltd, CSERVE:10236.1703
6 MacKay St ASHFIELD, Mem: SA IT/9/22,SC22/WG21
NSW 2131, AUSTRALIA
Author: doug@monet.ads.com (Doug Morgan)
Date: 24 May 94 11:15:33 Raw View
In article <DOUG.94May24094906@monet.ads.com> doug@monet.ads.com (Doug Morgan) writes:
>In article <Cq9A8u.DLC@ucc.su.OZ.AU> maxtal@physics.su.OZ.AU (John Max Skaller) writes:
>>Why is this 'correct' and public virtuals wrong?
>> ...
> [... agree and expand ...]
Another nice thing about public nonvirtuals inline calling private
virtuals is that you needn't wait for your favorite compiler vendors
to all implement covariant type returns for virtual functions. You
can "do it yourself" on the nonvirtual functions (e.g., by using down
casts inside the public inline nonvirtual members that call the
private virtual members). You can even implement covariant returns of
actual objects, not just pointers and references (as John has pointed
out is a safe thing to do, but not allowed in the current ANSI
thinking about virtual members). You will likely have to create a
private virtual function of a brand new name (to prevent slicing) and
redefine the old private virtual too, but that may not be too bad.
Doug
--------------------------------------------------------------------
Doug Morgan, doug@ads.com, (415) 960-7444
Advanced Decision Systems (a division of Booz-Allen & Hamilton Inc.)
1500 Plymouth St., Mountain View, CA 94043-1230
--------------------------------------------------------------------
Author: achoi@soda.berkeley.edu (Andrew Choi)
Date: 18 May 1994 01:19:00 GMT Raw View
Hi netters,
Has anyone actually tried to use a virtual private class member
function???? Is it an oversight of the committee to allow such
a feature??? Or is it there because there are actually some use
for it???
Anyway, thanks for your response.
-- Andrew Choi (achoi@soda.berkeley.edu)
Author: rcorbish@brtph897.bnr.ca (Richard Corbishley P090)
Date: Wed, 18 May 1994 16:37:47 GMT Raw View
You can publish private methods so they must be allowed virtual status.
Rick
Author: rfg@netcom.com (Ronald F. Guilmette)
Date: Thu, 19 May 1994 09:46:51 GMT Raw View
In article <2rbqe4$8ns@agate.berkeley.edu> achoi@soda.berkeley.edu (Andrew Choi) writes:
>Hi netters,
>
> Has anyone actually tried to use a virtual private class member
>function???? Is it an oversight of the committee to allow such
>a feature??? Or is it there because there are actually some use
>for it???
>
> Anyway, thanks for your response.
>
>-- Andrew Choi (achoi@soda.berkeley.edu)
>
I use it, and I don't believe it was an oversight to allow it.
The virtual function calling mechanism is useful regardless of whether or
not the called function is private. Why would you think otherwise?
--
-- Ron Guilmette, Sunnyvale, CA ---------- RG Consulting -------------------
---- domain addr: rfg@netcom.com ----------- Purveyors of Compiler Test ----
---- uucp addr: ...!uunet!netcom!rfg ------- Suites and Bullet-Proof Shoes -
Author: kanze@us-es.sel.de (James Kanze)
Date: 19 May 1994 13:36:27 GMT Raw View
In article <2rbqe4$8ns@agate.berkeley.edu> achoi@soda.berkeley.edu
(Andrew Choi) writes:
|> Has anyone actually tried to use a virtual private class member
|> function???? Is it an oversight of the committee to allow such
|> a feature??? Or is it there because there are actually some use
|> for it???
I've used it lots of times. I find it particularly useful in
conjunction with templates. All of the type independant activity is
factored out into a non-templated base class. Often however, there
will be a need for a small type-dependant activity in the middle of a
function which would otherwise be type independant. In this case, the
non-template base class calls a private virtual function (almost
always pure virtual, in fact) to do this activity; the template class
overloads it with the type specific behavior.
--
James Kanze email: kanze@lts.sel.alcatel.de
GABI Software, Sarl., 8 rue du Faisan, F-67000 Strasbourg, France
Conseils en informatique industrielle --
-- Beratung in industrieller Datenverarbeitung