[comp.lang.c++] virtual static class functions

deb@svax.cs.cornell.edu (David Baraff) (03/14/90)

Why can't static class functions be virtual? That is,
is there some reason why allowing static virtual class functions
would be bad? I can't see that the implementation would pose
any problems.

	David Baraff
	deb@svax.cs.cornell.edu

bright@Data-IO.COM (Walter Bright) (03/15/90)

In article <38579@cornell.UUCP> deb@svax.cs.cornell.edu (David Baraff) writes:
<Why can't static class functions be virtual? That is,
<is there some reason why allowing static virtual class functions
<would be bad? I can't see that the implementation would pose
<any problems.

The virtual table is found through the this pointer. Static members, by
definition, aren't invoked for a specific instance of a class, so there
is no this pointer, and no way to get to the virtual table.

dsouza@optima.cad.mcc.com (Desmond Dsouza) (03/16/90)

   In article <38579@cornell.UUCP> deb@svax.cs.cornell.edu (David Baraff) writes:
   <Why can't static class functions be virtual? That is,
   <is there some reason why allowing static virtual class functions
   <would be bad? I can't see that the implementation would pose
   <any problems.
I agree with this observation. To elaborate:

  1. Static member functions can be invoked with OR without an object
     of that class. i.e. both of these are legal:
          (a)  Class::static_func(); // explicit "Class::" or by context
	  (b)  obj.static_func(); // or through a pointer p->static_func();
     Clearly, static_func() cannot access any non_static data or function
     members of Class because of case (a).

  2. The above restriction does NOT rule out permitting static_func()
     to be VIRTUAL.

     If the invocation is as in (a) above, the call is
     resolved statically, like any other member function call --
     virtual or non-virtual.

     If the invocation is as in (b) above, the call gets resolved
     dynamically through the virtual function table. Only VIRTUAL
     static member functions need be entered in this table.

     Whether or not am *implmentation* chooses to pass an implicit "this" pointer
     as a first argument to VIRTUAL static member functions is unimportant
     and may be decided by implementation convenience : the function
     cannot use any non-static members anyway so the value of "this"
     is irrelevant.

In summary, VIRTUAL static member functions are entered in the virtual
function table, may only access static data and functions, and may or
may not be actually passed a "this" pointer. Non-virtual static member
functions would remain unchanged.

It is easy to come up with examples where this is useful. 

Desmond.
--

-------------------------------------------------------------------------------
 Desmond D'Souza, MCC CAD Program | ARPA: dsouza@mcc.com | Phone: [512] 338-3324
 Box 200195, Austin, TX 78720 | UUCP: {uunet,harvard,gatech,pyramid}!cs.utexas.edu!milano!cadillac!dsouza

ark@alice.UUCP (Andrew Koenig) (03/17/90)

In article <38579@cornell.UUCP>, deb@svax.cs.cornell.edu (David Baraff) writes:

> Why can't static class functions be virtual? That is,
> is there some reason why allowing static virtual class functions
> would be bad? I can't see that the implementation would pose
> any problems.

A virtual function implies run-time dispatching based on the
type of the object used to call the function.

A static function implies that an object need not be supplied
to call it.

If no object is supplied, how would the implementation determine
which function to call?
-- 
				--Andrew Koenig
				  ark@europa.att.com

shopiro@alice.UUCP (Jonathan Shopiro) (03/18/90)

In article <10586@alice.UUCP>, ark@alice.UUCP (Andrew Koenig) writes:
- In article <38579@cornell.UUCP>, deb@svax.cs.cornell.edu (David Baraff) writes:
- 
- > Why can't static class functions be virtual? That is,
- > is there some reason why allowing static virtual class functions
- > would be bad? I can't see that the implementation would pose
- > any problems.
- 
- A virtual function implies run-time dispatching based on the
- type of the object used to call the function.
- 
- A static function implies that an object need not be supplied
- to call it.
- 
- If no object is supplied, how would the implementation determine
- which function to call?

The summary says it all.

Sample code:

	struct Foo {
		static virtual void f();
	};
	struct Bar : public Foo {
		static void f();
	};

	void zot() {
		Foo*  p = new Bar;
		Foo::f();       // calls Foo::f() (compiletime binding)
		p->f();         // calls Bar::f() (runtime binding)
	}

Note that there's similar syntax that allows you to call the ``wrong''
version of a non-static virtual function.

It's not obvious that this is worth doing, but it's certainly feasible.
-- 
		Jonathan Shopiro
		AT&T Bell Laboratories, Warren, NJ  07060-0908
		research!shopiro   (201) 580-4229

dsouza@optima.cad.mcc.com (Desmond Dsouza) (03/19/90)

I am re-posting this as I forgot to mark the Distribution last time.

   In  <38579@cornell.UUCP> deb@svax.cs.cornell.edu (David Baraff) writes:

   <Why can't static class functions be virtual? That is,
   <is there some reason why allowing static virtual class functions
   <would be bad? I can't see that the implementation would pose
   <any problems.


   In article <10586@alice.UUCP> ark@alice.UUCP (Andrew Koenig) replies:
   <If no object is supplied, how would the implementation determine
   <which function to call?

I agree with David Baraff. Virtual static member functions are useful 
and simple to implement. To elaborate:

  1. Static member functions can be invoked with OR without an object
     of that class. i.e. Given
     	class Base { public: virtual static foo() ; } ;
     both of these are legal:
          (a)  Base::foo(); // explicit "Base::" or by context e.g. used 
	  	 in a member function of Base.
	  (b)  obj.foo(); // or through a pointer p->foo();
     Clearly, foo() cannot access any non-static data or function
     members of Base because of case (a).

  2. The above restriction does NOT rule out permitting foo()
     to be VIRTUAL.

     If the invocation is as in (a) above, the call is
     resolved statically, like any other member function call --
     virtual or non-virtual.

     If the invocation is as in (b) above, the call gets resolved
     dynamically through the virtual function table. Only VIRTUAL
     static member functions need be entered in this table.

     Normally, virtual member functions receive an implicit "this" pointer
     as a first argument. Whether or not am *implmentation* chooses to
     routinely pass an implicit "this" pointer as a first argument to
     VIRTUAL static member functions is unimportant (so long as overloaded
     function calls are resolved consistently) and may be decided by
     implementation convenience and efficiency,The function cannot use
     any non-static members anyway, so the value of "this" is irrelevant.



In summary, VIRTUAL static member functions are entered in the virtual
function table, may only access static data and functions, and may or
may not be actually passed a "this" pointer. Non-virtual static member
functions would remain unchanged.

It is easy to come up with examples where this is useful. Suppose foo() 
was a static member function which describes class "Base".
  1. Base::foo(); uses foo() as a  "class" function, as opposed to an
     "object" function. This is ostensibly one of the reasons for having 
     static member functions.
  2. obj.foo(); is simply a way of getting to this "class" function for 
     the class which foo is an instance of. i.e. a way of doing
        obj.class.foo(); 
  3. Certainly a class "Der" derived from Base would have its own foo();
     Hence, any function which takes a Base& (or Base*) argument should be 
     able to access either Base::foo() or Der::foo(), to describe the 
     appropriate class. Virtual static functions would do this.

Desmond.

-------------------------------------------------------------------------------
 Desmond D'Souza, MCC CAD Program | ARPA: dsouza@mcc.com | Phone: [512] 338-3324
 Box 200195, Austin, TX 78720 | UUCP: {uunet,harvard,gatech,pyramid}!cs.utexas.edu!milano!cadillac!dsouza
--

-------------------------------------------------------------------------------
 Desmond D'Souza, MCC CAD Program | ARPA: dsouza@mcc.com | Phone: [512] 338-3324
 Box 200195, Austin, TX 78720 | UUCP: {uunet,harvard,gatech,pyramid}!cs.utexas.edu!milano!cadillac!dsouza

roger@procase.UUCP (Roger H. Scott) (03/29/90)

In article <2380@dataio.Data-IO.COM> bright@Data-IO.COM (Walter Bright) writes:
>In article <38579@cornell.UUCP> deb@svax.cs.cornell.edu (David Baraff) writes:
><Why can't static class functions be virtual?...
>The virtual table is found through the this pointer. Static members, by
>definition, aren't invoked for a specific instance of a class, so there
>is no this pointer, and no way to get to the virtual table.
Not so fast!  Static member functions *may* be invoked without a pointer, in
which case they must be "de-virtualized" by explicit qualification with a
class name, e.g. "klass::static_member_function();", but they may *also* be
invoked through a pointer, e.g. "klass *k = ...; k->static_member_function();".
Such an invocation, while legal, is pointless today because no use whatsoever
is made of the object involved.  If static member functions could be virtual
then the object involved would be used to determine which function to call.
The called routine would still have no automatic connection to the object.
I think I asked Bjarne S. about this a while back, and he said that, while
reasonable, this was not high on the list of priorities.  Another interesting
thing to think about is virtual static *data* members (virtual non-static
data members make no sense).