Trying to inherit three base classes and can’t

In the first example you’re not actually inheriting from two classes, but from one class and an interface.

C# doesn’t allow multiple inheritance from classes, but does allow you to implement multiple interfaces. See this MSDN blog post (link is dead so text is pasted below) for more information on why.

You will have to make an IMembershipUser interface and implement that in your User class.

Interfaces are usually given names based on the concrete class name prefixed by an I. So the class MembershipUser would have an interface IMembershipUser. There’s nothing stopping you using some other name, but everyone who uses interfaces is used to this naming convention.

There are a number of reasons we don’t implement Multiple
Implementation Inheritance directly. (As you know, we support Multiple
Interface Inheritance).

However, I should point out that it’s possible for compilers to create
MI for their types inside the CLR. There are a few rough edges if you
go down this path: the result is unverifiable, there is no interop
with other languages via the CLS, and in V1 and V1.1 you may run into
deadlocks with the OS loader lock. (We’re fixing that last problem,
but the first two problems remain). The technique is to generate some
VTables in RVA-based static fields. In order to deposit the addresses
of managed methods (which probably haven’t been JITted yet), you use
the VTFixup construct. This construct is a table of triplets. The
triplets consist of a token to a managed method, an address in your
image that should be fixed up (in this case, a slot of the VTable you
are creating in the RVA-based static), and some flags. The possible
flags are described in corhdr.h and they allow you to specify 32- vs.
64-bit pointer sizes, control over virtual behavior, and whether some
reverse-PInvoke behavior should be applied in the form of a thunk that
eventually dispatches to the managed method. If we are performing an
unmanaged->managed transition, you also have some control over which
AppDomain should be selected for us to dispatch the call. However, one
of these options (COR_VTABLE_FROM_UNMANAGED_RETAIN_APPDOMAIN) doesn’t
exist in V1. We added it in V1.1.

There are several reasons we haven’t provided a baked-in, verifiable,
CLS-compliant version of multiple implementation inheritance:

  1. Different languages actually have different expectations for how MI works. For example, how conflicts are resolved and whether duplicate
    bases are merged or redundant. Before we can implement MI in the CLR,
    we have to do a survey of all the languages, figure out the common
    concepts, and decide how to express them in a language-neutral manner.
    We would also have to decide whether MI belongs in the CLS and what
    this would mean for languages that don’t want this concept (presumably
    VB.NET, for example). Of course, that’s the business we are in as a
    common language runtime, but we haven’t got around to doing it for MI
    yet.

  2. The number of places where MI is truly appropriate is actually quite small. In many cases, multiple interface inheritance can get the
    job done instead. In other cases, you may be able to use encapsulation
    and delegation. If we were to add a slightly different construct, like
    mixins, would that actually be more powerful?

  3. Multiple implementation inheritance injects a lot of complexity into the implementation. This complexity impacts casting, layout,
    dispatch, field access, serialization, identity comparisons,
    verifiability, reflection, generics, and probably lots of other
    places.

It’s not at all clear that this feature would pay for itself. It’s
something we are often asked about. It’s something we haven’t done due
diligence on. But my gut tells me that, after we’ve done a deep
examination, we’ll still decide to leave the feature unimplemented.

Leave a Comment