Re: a case for multiple inheritance



Ben Voigt [C++ MVP] wrote:


"Tom Spink" <tspink@xxxxxxxxx> wrote in message
news:O8o0sm8sHHA.1416@xxxxxxxxxxxxxxxxxxxxxxx
John wrote:

Tom Spink wrote:

1) Create a generic ProtectedList<T> class which inherits from List<T>
and overrides the write functions (using the new modifier) to change
the
access level from public to protected.

Mhm. FYI The 'new' modifier will define a method as hiding a derived
one,

Sorry, I didn't complete the description, the 'new protected' modified
functions would delegate to the base implementation. I would assume that
the compiler would optimize it so that the double function call would be
reduced to a single function call resulting in no performance hit.

however, take a look at this:

public class A
{
public void Foo ()
{
Console.WriteLine("Foo in A");
}
}

public class B : A
{
private new void Foo ()
{
Console.WriteLine("Foo in B");
}
}

public class E
{
public static void Main ()
{
B b = new B();
b.Foo();
}
}

The output of this will be "Foo in A", because the accessible method
from
A
is called. If you change the scope of 'Foo' in B to public, the output
will be "Foo in B" as is expected. And, even more interestingly, if
you cast b to A and call 'Foo':

((A)b).Foo();

You'll get A's implementation of 'Foo'. So, as you can see, using the
new keyword will not give you the desired effect here.

The automatic fallback to the public base implementation, after
specifically overriding it, is very disturbing to me. The cast not much
of a surprise, assuming you are allowed to perform that cast, I would
expect that behavior.


2) Inherit both specialized List<T> by the high-level class
Can you explain this a bit more? I'm not sure why you need multiple
inheritance here. If you want to expose two read-only lists from your
high-level class, you can expose them as properties that return an
array of your list's type, then call the ToArray method of the
associated list.

Thanks for the advice, as you can tell, I'm new to C# and I'm looking
for these kinds of tips. The idea of multiple inheritance is to not
require this kind of massaging and wrapping for every 'ProtectedList'
you want to expose. I want to expose all the useful read-only List
interface like Exists, Equals, access methods, including custom sort
iterators with Predicate, etc., in as simple a way to program as
possible. Aggregating, and exposing wrappers is not, in my mind, an
efficient way to do this.

Hi John,
Sorry, I didn't complete the description, the 'new protected' modified
functions would delegate to the base implementation. I would assume that
the compiler would optimize it so that the double function call would be
reduced to a single function call resulting in no performance hit.

Not really. Remember, C# gets compiled to a form of intermediate
language,
with all OO constructs preserved, i.e. namespaces, classes, methods,
interfaces and etc. This means that if method A1 (in a subclass)
overrides
method A2 (in a superclass), and A1 simply calls the superclass'
implementation, the call stack will still go from A1 to A2, there'll be
no optimisation like in a native language (such as C).

The JIT is perfectly capable of inlining the function call mentioned.


The automatic fallback to the public base implementation, after
specifically overriding it, is very disturbing to me. The cast not much
of a surprise, assuming you are allowed to perform that cast, I would
expect that behavior.

Now, this is an example of compiler inference. In truth, I didn't test
this
on Microsoft's compiler (I used gmcs), but this is an example of where
the
compiler can infer what you're trying to do. The compiler can infer that
if you're requesting a method call to 'Foo', and 'Foo' exists as private
in
the class you are referencing, however a superclass has a public
implementation, then the compiler will route the call to the superclass'
implementation, and will indeed perform the cast that I described above
to force an invocation of a specific implementation of the method.

And, in my example, of course the cast is valid since B subclasses A.

Thanks for the advice, as you can tell, I'm new to C# and I'm looking
for these kinds of tips. The idea of multiple inheritance is to not
require this kind of massaging and wrapping for every 'ProtectedList'
you want to expose. I want to expose all the useful read-only List
interface like Exists, Equals, access methods, including custom sort
iterators with Predicate, etc., in as simple a way to program as
possible. Aggregating, and exposing wrappers is not, in my mind, an
efficient way to do this.

No problem. However, I'm still trying to understand where multiple
inheritance relates to your problem. Can you provide an example of how
you'd use multiple inheritance?

Thanks,
--
Tom Spink
University of Edinburgh

Hi Ben,

The JIT is perfectly capable of inlining the function call mentioned.

I guess so... perhaps my wording wasn't the best, as I meant this sort of
optimisation won't happen at the IL compilation stage. It will be a
runtime optimisation.

--
Tom Spink
University of Edinburgh
.



Relevant Pages

  • Re: a case for multiple inheritance
    ... and overrides the write functions to change ... the compiler would optimize it so that the double function call would be ... private new void Foo ... The cast not much ...
    (microsoft.public.dotnet.languages.csharp)
  • Re: a case for multiple inheritance
    ... the compiler would optimize it so that the double function call would be ... private new void Foo ... The cast not much ... This means that if method A1 overrides ...
    (microsoft.public.dotnet.languages.csharp)
  • Re: (trivia) remove useless typecast around `jif variable
    ... cast in place, compiler will be completely silent, while w/o the cast ... struct somestruct *foo; ... foo = (struct somestruct *)kmalloc); ...
    (Linux-Kernel)
  • Re: new virtual functions
    ... B.foverrides A.f, which is basically what you're calling when you ... and B.fas far as the compiler is concerned. ... Foo() as well, which might be meant to do something completely ... because then the library class would be expecting it to do one thing ...
    (microsoft.public.dotnet.languages.csharp)
  • Re: new virtual functions
    ... > B.foverrides A.f, which is basically what you're calling when ... > and B.fas far as the compiler is concerned. ... You've put in a method called Foo(), ... > because then the library class would be expecting it to do one thing ...
    (microsoft.public.dotnet.languages.csharp)