Abstract Base Classes vs Interfaces?

  • Thread starter Thread starter Sean Kirkpatrick
  • Start date Start date
S

Sean Kirkpatrick

To my eye, there doesn't seem to be a whole lot of difference between
the two of them from a functional point of view. Can someone give me a
good explanation of why one vs the other?

Sean
 
Hi

Here is something quoted from MSDN.
"Abstract classes are closely related to interfaces. They are classes that
cannot be instantiated, and are frequently either partially implemented, or
not at all implemented. One key difference between abstract classes and
interfaces is that a class may implement an unlimited number of interfaces,
but may inherit from only one abstract (or any other kind of) class. A
class that is derived from an abstract class may still implement
interfaces. Abstract classes are useful when creating components because
they allow you specify an invariant level of functionality in some methods,
but leave the implementation of other methods until a specific
implementation of that class is needed. They also version well, because if
additional functionality is needed in derived classes, it can be added to
the base class without breaking code."

http://msdn.microsoft.com/library/default.asp?url=/library/en-us/vbcon/html/
vbconabstractclasses.asp


Best regards,

Peter Huang
Microsoft Online Partner Support

Get Secure! - www.microsoft.com/security
This posting is provided "AS IS" with no warranties, and confers no rights.
 
Despite the documentations views Abstract classes and Interfaces are
completely dissimilar and have very specific roles in an OO system.

An abstract class forces a specific chain of inheritance onto the classes
that are derived from it. Effectively they say that if you want to play in
my playground you MUST have this particular minimum concrete implementation.
You MUST be a member of my family. This is useful for example if you wish to
be able to pass around references to an abstract type yet assume that the
derived class, that you don't know or care about the actual type of, has
implemented the missing functionality. The GDI+ Brush class is a classic
example of this. You cannot instantiate a brush but you can instantiate a
SolidBrush, LinearGradientBrush, PathGradientBrush or TextureBrush and store
it in a Brush variable.

Interfaces specifically enforce the method / property contract without
enforcing the class derivation relationships. Effectively they say if you
want to play in my playground I don't care who you are as long as you obey
my rules. You can take any class and derive from it adding in an interface
implementation. This is useful if you want to do something like enable
third-party developers to adhere to rules in your application or system
without necessarily providing them with a DLL or a concrete class from which
to derive their own. A good example of this is the ICollection interface
that enables you to create a class that conforms to a specific contract yet
doesn't have to be derived from any particular base class.

--
Bob Powell [MVP]
Visual C#, System.Drawing

Ramuseco Limited .NET consulting
http://www.ramuseco.com

Find great Windows Forms articles in Windows Forms Tips and Tricks
http://www.bobpowell.net/tipstricks.htm

Answer those GDI+ questions with the GDI+ FAQ
http://www.bobpowell.net/faqmain.htm

All new articles provide code in C# and VB.NET.
Subscribe to the RSS feeds provided and never miss a new article.
 
Despite the documentations views Abstract classes and Interfaces are
completely dissimilar and have very specific roles in an OO system.

They really don't.

Sure, there are circumstances where one or the other is the obvious
choice, and in those circumstances they do have specific roles. The
most obvious is mixin functionality which pretty much has to be defined
as an interface in .Net. Or when you want to provide a base
implementation, an abstract class is the only choice.

But there's a lot of gray area in between those two, and a great many
situations where either would do just as well. And in those situations
choosing between the two can be tricky and subtle.
An abstract class forces a specific chain of inheritance onto the classes
that are derived from it. Effectively they say that if you want to play in
my playground you MUST have this particular minimum concrete implementation.
You MUST be a member of my family.

That's kind of a strange definition of "concrete implementation", since
of course a pure abstract class has no implementation at all. I don't
*think* you're suggesting that one should never have a "pure" abstract
class (i.e., a class where all methods are MustOverride), but I'm not
sure from your post.
This is useful for example if you wish to
be able to pass around references to an abstract type yet assume that the
derived class, that you don't know or care about the actual type of, has
implemented the missing functionality. The GDI+ Brush class is a classic
example of this. You cannot instantiate a brush but you can instantiate a
SolidBrush, LinearGradientBrush, PathGradientBrush or TextureBrush and store
it in a Brush variable.

Interfaces specifically enforce the method / property contract without
enforcing the class derivation relationships. Effectively they say if you
want to play in my playground I don't care who you are as long as you obey
my rules. You can take any class and derive from it adding in an interface
implementation. This is useful if you want to do something like enable
third-party developers to adhere to rules in your application or system
without necessarily providing them with a DLL or a concrete class from which
to derive their own.

OK, that eluded me. How does an interface let you do this? You still
need to provide third-party developers with a DLL to reference,
otherwise how are they going to implement the interface?
.A good example of this is the ICollection interface
that enables you to create a class that conforms to a specific contract yet
doesn't have to be derived from any particular base class.

Actually, I think ICollection is a good example of the ambiguity between
interfaces and abstract base classes. ICollection really cries out to
be an abstract base class with a built-in SyncRoot and a default
IsSynchronized implementation. But you can't do that in .Net because the
contract of ICollection is essentially a mixin pattern. So it has to
be an interface.

That's the kind of design trade-off one comes across all the time. I'm
not disagreeing with any of your definitions above, I'm just saying that
choosing between the two is often quite tricky.
 
Inline...

--
Bob Powell [MVP]
Visual C#, System.Drawing

Ramuseco Limited .NET consulting
http://www.ramuseco.com

Find great Windows Forms articles in Windows Forms Tips and Tricks
http://www.bobpowell.net/tipstricks.htm

Answer those GDI+ questions with the GDI+ FAQ
http://www.bobpowell.net/faqmain.htm

All new articles provide code in C# and VB.NET.
Subscribe to the RSS feeds provided and never miss a new article.





david said:
They really don't.

Sure, there are circumstances where one or the other is the obvious
choice, and in those circumstances they do have specific roles. The
most obvious is mixin functionality which pretty much has to be defined
as an interface in .Net. Or when you want to provide a base
implementation, an abstract class is the only choice.

But there's a lot of gray area in between those two, and a great many
situations where either would do just as well. And in those situations
choosing between the two can be tricky and subtle.

It's true to say that the details are subtle and one can be substituted for
the other in many sutuations however, there are very clear-cut reasons why
one would chose an interface and reject an abstract class and vice-versa.
That's kind of a strange definition of "concrete implementation", since
of course a pure abstract class has no implementation at all. I don't
*think* you're suggesting that one should never have a "pure" abstract
class (i.e., a class where all methods are MustOverride), but I'm not
sure from your post.

Even a pure abstract class forces a specific type heirarchy. The details of
this are even more important for .NET classes written in VB or C# because
there is no multiple-inheritance mechanism.
A class derived from an abstract will always be guaranteed to be part of
that class derivation chain. This is not the case for interfaces and, IMO,
the line between the two is as clear as night and day.
OK, that eluded me. How does an interface let you do this? You still
need to provide third-party developers with a DLL to reference,
otherwise how are they going to implement the interface?

This is the point. You absolutely do not need to provide a DLL or any
concrete imlementation in order to hand an interface around to anyone who
might wish to use it. Take for example a .NET implemented plug-in
architecture. It is quite possible to define component interactions in terms
of a set of interfaces and allow anyone to implement them using whatever
concrete class heirarchy they think fit. As long as the contract of the
interface is adhered to you never need to give a DLL, which may contain your
valuable trade secrets, to a third-party.
Actually, I think ICollection is a good example of the ambiguity between
interfaces and abstract base classes. ICollection really cries out to
be an abstract base class with a built-in SyncRoot and a default
IsSynchronized implementation. But you can't do that in .Net because the
contract of ICollection is essentially a mixin pattern. So it has to
be an interface.

That's the kind of design trade-off one comes across all the time. I'm
not disagreeing with any of your definitions above, I'm just saying that
choosing between the two is often quite tricky.
Architecture choice is almost impossible to get right first time and often
refactoring rears its ugly head. From experience I can say that I have had
to refactor far less when I employed an interface based architecture than
when I used a class-heirarchy. I don't say that Abstract classes are not to
be used, just that the implications of using one enforces a pattern that
becomes inflexible as soon as you chose that architecture.
 
Inline...
Bob Powell [MVP]
Visual C#, System.Drawing

A minor off-topic point, but putting text after your sig really screws
up newsreaders that are sig-aware.

It's true to say that the details are subtle and one can be substituted for
the other in many sutuations however, there are very clear-cut reasons why
one would chose an interface and reject an abstract class and vice-versa.

Before we get into this, I guess it might be nice to actually mention to
the OP reasons for choosing one or the other...

Advantages of abstract base class...
Can force base concrete implementation
Can allow default implemention
Easily extensible

Advantages of Interfaces
Doesn't force inheritance tree, can act as mixin
Fits well with "prefer composition to inheritance"
Not easily extensible.

Yes, I'm being a bit flippant with the "extensible" thing. But one
advantage of interfaces is that it defines a stronger contract. In
practice, this usually forces lazy programmers (like me) to think harder
during both design and maintenance.

We both agree on something later that I'll state upfront: when in doubt,
use an interface.


Even a pure abstract class forces a specific type heirarchy.

True, my point though is that's not what is usually meant by "concrete
implementation", which has a very specific meaning. Base classes *can*
enforce a "concrete implementation", but they don't have to.

This is the point. You absolutely do not need to provide a DLL or any
concrete imlementation in order to hand an interface around to anyone who
might wish to use it. Take for example a .NET implemented plug-in
architecture. It is quite possible to define component interactions in terms
of a set of interfaces and allow anyone to implement them using whatever
concrete class heirarchy they think fit. As long as the contract of the
interface is adhered to you never need to give a DLL, which may contain your
valuable trade secrets, to a third-party.

I'm not sure here if we're being ambiguous about the meaning of
"interface", or if you or I are simply wrong about something. Usually
if you implement a .Net plugin architecture you deliver a DLL with your
interface in it and have others reference the dll and implement the
interface. This works identically with abstract base classes as well.
Usually this DLL doesn't have anything in it *except* the interface or
base class, so there's no issue with trade secrets.

There's a couple of alternatives, but I generally don't like either.
You could ask the client to create their own interface dll from a
definition you give them (although this requires strong naming be turned
off). Or you could publish a written spec of your "interface", then
load their plugin class and call all methods through reflection or late
binding.

Alternatively I suppose the interface could be a standard .Net interface
from the framework, but that's irrelevant here and you could of course
do the same thing with base classes anyway.

Did you have something else in mind? Am I missing something?
Architecture choice is almost impossible to get right first time and often
refactoring rears its ugly head.

I actually think refactoring has a rather attractive visage :-)

But then, I'm kind of TDD-oriented.
From experience I can say that I have had
to refactor far less when I employed an interface based architecture than
when I used a class-heirarchy. I don't say that Abstract classes are not to
be used, just that the implications of using one enforces a pattern that
becomes inflexible as soon as you chose that architecture.

Agreed.

PS. This is a very interesting and timely topic to me because this
weekend I need to decide between an interface and a base class for a
plugin system I'm writing. On the one hand I have a natural tendency
toward interfaces, on the other hand there's some default functionality
I'd like to enforce for performance reasons.
 
I've been out for a few days and am just getting back to this. I confess
that as interesting as the thread is, I realize that I don't understand
the topic well enough to follow the discussion. This is good - knowing
what I don't know is direction forward. Can you suggest a reference that
will give me some additional background?

I do think there is one point that I understand:
plugin system I'm writing. On the one hand I have a natural tendency
toward interfaces, on the other hand there's some default functionality
I'd like to enforce for performance reasons.

This makes sense.

Sean
 
inline... :-) no sig.
david said:
Advantages of abstract base class...
Can force base concrete implementation
Can allow default implemention
Easily extensible

Advantages of Interfaces
Doesn't force inheritance tree, can act as mixin
Fits well with "prefer composition to inheritance"
Not easily extensible.

Ok we agree. Remember however that interfaces are not extensible by design
but you can always add another interface.
Yes, I'm being a bit flippant with the "extensible" thing. But one
advantage of interfaces is that it defines a stronger contract. In
practice, this usually forces lazy programmers (like me) to think harder
during both design and maintenance.

We both agree on something later that I'll state upfront: when in doubt,
use an interface.




True, my point though is that's not what is usually meant by "concrete
implementation", which has a very specific meaning. Base classes *can*
enforce a "concrete implementation", but they don't have to.

My use of the phrase "Concrete implementation" was not good in this context.
The point I'm trying to make is that interfaces specifically free you from
the restraints of an imposed heirarchy. An abstract class in any single
inheritance system puts a link in a chain that has implications for the
architecture. If you inherit anywhere downstream of class A you can always
cast to A even when you have an object of type Z. If you have an object A
that implements any of a known set of interfaces you can discover the
capabilities by trying to cast to an interface to see what happens. Remember
that Interfaces are also about discovery without a type-aware structure
underneath.

This discussion may be getting too esoteric.

I'm not sure here if we're being ambiguous about the meaning of
"interface", or if you or I are simply wrong about something. Usually
if you implement a .Net plugin architecture you deliver a DLL with your
interface in it and have others reference the dll and implement the
interface. This works identically with abstract base classes as well.
Usually this DLL doesn't have anything in it *except* the interface or
base class, so there's no issue with trade secrets.

There's a couple of alternatives, but I generally don't like either.
You could ask the client to create their own interface dll from a
definition you give them (although this requires strong naming be turned
off). Or you could publish a written spec of your "interface", then
load their plugin class and call all methods through reflection or late
binding.

Alternatively I suppose the interface could be a standard .Net interface
from the framework, but that's irrelevant here and you could of course
do the same thing with base classes anyway.

Did you have something else in mind? Am I missing something?

Ok, I concede that a convenient way to distribute an interface is in a
stand-alone .NET assembly but theres nothing wrong with a type library. Give
'em a TLB and the system will build a wrapper DLL for them. Even simpler,
send them the 50 line source file...
 
I hesitate to point you in the direction of a COM tome. These are possibly
too overloaded with the intricasies of COM to really do justice to the
simple elegance of an interface.

Maybe Don Box has some useful stuff for you. Maybe Richard Grimes.

--
Bob Powell [MVP]
Visual C#, System.Drawing

Ramuseco Limited .NET consulting
http://www.ramuseco.com

Find great Windows Forms articles in Windows Forms Tips and Tricks
http://www.bobpowell.net/tipstricks.htm

Answer those GDI+ questions with the GDI+ FAQ
http://www.bobpowell.net/faqmain.htm

All new articles provide code in C# and VB.NET.
Subscribe to the RSS feeds provided and never miss a new article.
 
I've been out for a few days and am just getting back to this. I confess
that as interesting as the thread is, I realize that I don't understand
the topic well enough to follow the discussion. This is good - knowing
what I don't know is direction forward. Can you suggest a reference that
will give me some additional background?

Actually, from what you've written in this thread I suspect that you
understand the language points pretty well. Pure abstract base classes
are fairly similar to interfaces. The side-thread to this has been more
about how and when the two should be used. And I'd suggest the
references to that aren't .Net books but rather books that focus on
design patterns.

Off the top of my head, I'd suggest

Head First Design Patterns (a fun java-based introductory book)

Design Patterns Explained, by Alan Shalloway

Patterns of Enterprise Application Architecture, by Martin Fowler

Design Patterns, by Erich Gamma et al. (the Gang of Four book)
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Back
Top