Question

I do not know the "correct" name of that pattern, so I'd like to describe it with a simple example.

In C#, System.Windows.Window contains a ShowDialog method. I can define an interface containing this method (plus some other functionality). When I create a new Window class, it will inherit from Window, and I can add my interface. Now, I do not need to care for the ShowDialog method at all: "magically" the method of Window is used, though Window does not know my interface.

A simple sample code:

public interface IMyWindow
{
    bool? ShowDialog();
    // some additional other methods/properties
}

public class MyWindow : Window, IMyWindow
{
    // ShowDialog is "magically" implemented by Window
    #region additional other methods/properties
    #endregion
}

public class MyClass
{
    public void DoSomething()
    {
        IWindow w = new MyWindow();
        bool? result = w.ShowDialog();
    }
}

How is that pattern called? How common is its use? Or is it just some side-effect of other functionality of .Net, actually nothing intentionally designed? How do other object-oriented languages deal with that?

Edit:

Long ago I asked the question https://stackoverflow.com/questions/23242308/combined-type-generics-something-else - I'd now use an approach based on the method described above.

Was it helpful?

Solution

This is an instance of the class adapter pattern, where you use multiple inheritance to inherit from both a base class, and from an interface that you want to adapt the base class to. That you do not have to explicitly implement the interface function is merely a side effect of how interfaces work in C#.

OTHER TIPS

This isn't actually "magic", and as far as I'm aware there is no specific name for it. It is the default behavior of interface implementation.

The core issue of your question is not that there is an explicit "duck typing like" feature that enables this behavior. The core issue is that you misunderstand what an interface contract stipulates and expects from any type that implements it.

public class MyWindow : Window, IMyWindow
{
    // ShowDialog is "magically" implemented by Window
}

The fact that you call it "magic" suggests that you expect an interface contract to require that this class must explicitly implement a certain method, but that is not the case.

A similar but slightly simpler example:

public interface ITest
{
    string ToString();
}

public class Test : ITest
{

}

The compiler does not complain. Because every class inherently inherits from object, and object already has a string ToString() method, the Test class satisfies the interface contract because Test has a string ToString() method.

It's a fairly common misunderstanding of inheritance, where developers think of a derived class and its base class as if they are two separate elements of "the full package". But that is not the case.

For all intents and purposes, when considering the derived class, the features that are defined in the base class are equal in every way to the features that are defined in the derived class itself. The derived class would work exactly the same way if you were to copy/paste the base class' definition inside of the derived class' definition (instead of using inheritance).

Think of it as a "one way partial classes". Two partial classes operate exactly as if they were a single class definition - there is no difference between the two whatsoever (other than the ability to spread it over multiple files). For the inheritance example, I call it "one way" because the derived class includes the base class, but the base class does not include the derived class.


From a comment you made:

System.Windows.Window does not know anything about my interface - from its point of view, the method declared in my interface just happens to coincide with one of its methods.

But you're not expecting System.Windows.Window to implement your interface - which is why your expectation is irrelevant.

All you are doing is expecting MyWindow to implement the IWindow interface, whose contract can be summarized as "must have a bool? ShowDialog() method".

MyWindow does in fact have a bool? ShowDialog() method. Whether it explicitly defines its own bool? ShowDialog() method or inherits one is absolutely irrelevant. The compiler doesn't care about the source of the method, only that it exists.

Therefore the contract (MyWindow : IMyWindow) is satisfied, and thus no error is encountered.

As a very simple (and somewhat oversimplified) analogy: when I want to buy a $5 drink, does the shopkeeper care where the money comes from? E.g. I could be paying from my inheritance, I could've earned the money myself, I could've borrowed it from a friend.
The shop keeper doesn't care where the money comes from. All the shopkeeper cares about is that I have $5 to pay for the drink.

I don't think this has a name.

C# interface implementation is based on available methods. Base methods are available. While this is in contrast to C++, where a method from one base doesn't override the abstract method from another, C++ doesn't have designated interfaces as such. Java works the same way as C#.

Unless you can find a language that has designated interfaces and behaves differently from C# and Java, there's no need to name this feature; it's just the way interfaces work.

If you really want to make the point of calling this out, you could call it explicit interface method binding vs implicit interface method binding. Note that C# has the "explicit interface implementation" feature.

I'm not sure what the point of this construction is. All that implementing an interface does is promise that a certain signature exists in that class - it doesn't matter whether the class defines the method itself or inherits it.

Now, MyWindow already guarantees that the method exists because it extends Window, so the additional promise made via IMyWindow does nothing. This makes sense only if you want to use such objects in a context where you prefer not having to know about Window objects, just about IMyWindow. This could be called a form of interface segregation.

But is this likely? Even if you don't want to deal with all the complexity of the API of Window, will you conceivably want to show dialogs without ultimately making use of the system Window class? Do you plan other classes which show dialogs via some completely different channel?

Licensed under: CC-BY-SA with attribution
scroll top