C# hack: low level difference between interface an

2019-06-16 19:17发布

问题:

This is a philosophical question about C# fundamentals: I am wondering how close an interface may be simulated by fully abstract class. Assume we have following interface:

public interface INativeInterface
{
    void PerformAction();
    String Property { get; set; }
}

And following abstract class:

public abstract class ISimulatedInterface
{
    public abstract void PerformAction();
    public abstract String Property { get; set; }
}

They are having so much in common, aren't they? The differences I know are that:

  • Multiple inheritance does not work for abstract classes
  • Explicit implementation does not work abstract classes

Can these restrictions be skipped by using reflection or something like this?

I realize that interface and abstract class are different in root: interface declares a condition of "can behave like", abstract class - "is a kind of", but even this seems to be so close that a low level differences between these entities have to be discussed. This question can even sound like "What would you do to make an interface in C++".

回答1:

Can these restrictions be skipped by using reflection or something like this?

No. Abstract classes and interfaces are different concepts at the Common Language Runtime level. Hence it is neither possible in C# because of being ultimately limited be CLR's boundaries.

I am wondering how close an interface may be simulated by fully abstract class.

It is doable, but requires support (or 'allowance') from the underlying execution evironment (be it physical or managed).

In the past I designed a language that completely substituted abstract classes for interfaces. And yes, it did support multiple inheritance of such 'interfaces'. However, the implementation peculiarities are probably not worth the effort. The major 'low-level difference' was that an internal, embedded instance of the inherited abstract class had to be kept within the implementing class'es instance, and a chain of this pointers had to be maintained. Needless to say, it was a joyful experience :-)



回答2:

So, if I understand your question, you have two related issues.

The first is really "what's the difference between an abstract class and an interface"; the second is, "in C#, can I bypass the differences by making an abstract class without concrete methods behave like an interface?".

The first question is answered well in the link from @Todd Schiller.

The second question is more complicated.

You possibly could create a build-time task to convert all abstract classes without concrete implementations into an interface. I've never tried - because I see no benefit to doing this, and many, many downsides.

The biggest downside is that your code becomes more difficult to debug and maintain. Developers learn when to create an abstract class, and when to create an interface; it's an established, commonly agreed idiom. New developers working on your code base will heave a lot of new things to learn - and introducing a new way to think about interfaces and abstract classes will make that process harder and longer.

When debugging your application, a developer who sees an abstract class in the source code - but in the run-time code sees it's actually an interface - will likely get confused, and spend their time trying to work out why that is happening, rather than tracing down the real bug.

There's no obvious benefit as far as I can see.



回答3:

For me, it really boils down to their capabilties. An interface will NEVER provide an implementation for any of its operations; it only promises that anyone who uses it must provide something. An abstract class can provide implementations for any of its operations that can be overridden at the discretion of its subclasses. And no, you will never, ever be able to override those restrictions via reflection since they are core to the language itself.

As far as using an abstract class in place of an interface, it once again comes down to what you need to accomplish. If you need to provide some base implementation, you have to use an abstract class - otherwise, go with the interface.

Some of the other differences you already mentioned. You can implement multiple interfaces in C#, but you can only ever derive from a single class (abstract or otherwise).



回答4:

It may be hot subject in the context of OOPS Philosophy..like we know it has few technical difference like interface doesn't have constructor , and inherited class must implement all the methods etc. but i like to discuss it with real world scenario. actually i think interface is a contract between an object with its consumer.but abstract class is not a contract even though both can use to achieve "liskov substitution principle". i like to list two situation in real life..

1.) Imagine an drawing application ,which may contains shape ,rectangle,square etc. here shape can be abstract class or interface type. but if i need to ensure that every object inside my application must have a state while instantiating. i can't achieve this facility with interface so interface cant keep the state of an object.

2.) If my shapes are sharing common values (a static value), i cant achieve that using interface so i think abstract class can keep both state and behavior

but considering interface it is an agreement about the behavior, look a real example, animals and birds , both these objects have some similar behavior but we cant say they are sharing common properties, both birds and animal can walk,cry,eat ,the execution of these actions are completely different. in our programming interface is an ideal candidate in a situation where you only need agreement dont need any states. the good thing is consumer object can replace any other object which satisfy that agreement, D I is one best example.