1

I'm starting to use C# 8.0 and default interface implementations. According to the official C# documentation, we can call the default implementation of an interface method from another object derived from it using the syntax IBaseInterface.base.Method(), as shown in this code snippet from the official documentation

interface I0
{
   void M() { Console.WriteLine("I0"); }
}
interface I1 : I0
{
   override void M() { Console.WriteLine("I1"); }
}
interface I2 : I0
{
   override void M() { Console.WriteLine("I2"); }
}
interface I3 : I1, I2
{
   // an explicit override that invoke's a base interface's default method
   void I0.M() { I2.base.M(); }
}

However, the syntax I2.base.M() gives an error. Can anyone confirm if there's an error in the documentation? Also, the override keyword cannot be used in the definition of an interface method, and I can't find any additional information on the topic.

If this code is invalid, does C# have a way to execute { Console.WriteLine("I0"); }, i.e., the default implementation of I0.M(), from an instance of the I3 interface?

EDIT: So far, the only way I have been able to do it is by using this tricky code with the static method DefaultM().

interface I0
{
   protected static void DefaultM() { Console.WriteLine("I0"); } 
   void M() { DefaultM(); }
}
interface I1 : I0
{
   void IO.M() { Console.WriteLine("I1"); }
}
interface I2 : I0
{
   void IO.M() { Console.WriteLine("I2"); }
}
interface I3 : I1, I2
{
   // an explicit override that invoke's a base interface's default method
   void I0.M() { I0.DefaultM(); }
}
  • 1
    _"How to call default implementation of overridden interface method"_ - you don't. That's the point. – Fildor Apr 27 '23 at 12:36
  • Does this mean that it is simply not possible? Or is it that, in addition to not being possible, I am trying to do something that should be resolved with a different pattern than the one I am proposing and that is why I have arrived at this mess. – Rubén Cantón Apr 27 '23 at 12:41
  • 1
    See [this](https://learn.microsoft.com/en-us/dotnet/csharp/language-reference/proposals/csharp-8.0/default-interface-methods#base-interface-invocations-closed) – Nikola Markovinović Apr 27 '23 at 12:46
  • Since you talk about patterns, default implementations are meant for API versioning or implementing traits. It's quite similar to how default interface methods are used in Java and Android. There are quite a few examples in the [tag's documentation](https://stackoverflow.com/tags/default-interface-member/info) – Panagiotis Kanavos Apr 27 '23 at 12:47
  • While base invocation was discussed in the past, it was never implemented. There's simply no way to call the default implementation of a base interface. The question's first snippet doesn't compile in any C# version either, DIMs or not. You can't use `override` in I2 to replace the method *declared* in another interface. Interfaces aren't abstract classes, they only specify declarations. If a class or interface *implements* two interfaces with similar methods it *must* specify which one is implemented at any point. The second snippet is far cleaner and less tricky than the first one – Panagiotis Kanavos Apr 27 '23 at 13:21

1 Answers1

2

Can anyone confirm if there's an error in the documentation?

Kind of. This is actually text from feature proposal (source path: csharplang/proposals/csharp-8.0/default-interface-methods.md) since currently there is no full spec for C# 8+ (as far as I understand draft one for C# 7 is currently worked on).

From C# LDM for Oct 17, 2018:

Does an override in an interface introduce a new member?

No override keyword in interfaces. This should resolve all listed questions.

From C# LDM for April 29, 2019:

Conclusion

Cut base() syntax for C# 8. We intend to bring this back in the next major release.

Guru Stron
  • 102,774
  • 10
  • 95
  • 132
  • 1
    That page isn't the official documentation, it's the discussions. That same page includes the other snippets as well. Base invocation was never implemented – Panagiotis Kanavos Apr 27 '23 at 13:23