I am actually working on my first VBA project. (come from C++)
I would like to improve an existing VBA project used by a Microsoft Excel workbook by implementing classes and polymorphism.
My problem is:
1 - I read a lot of articles/forums which explain that VBA is not an Object Oriented Programming (OOP) language and do not support Polymorphism.
Some of them propose a workaround using the keyword Implements.
2 - I also found some webpages like this one which explain how to perform OOP and polymorphism in VBA using keywords like Inherits, Overrides, Overridable, MustOverrides.
So my question is :
Is VBA an OOP language, and does it support polymorphism ?
OOP is sitting on 4 "pillars":
Abstraction - Abstracting logic and concepts can easily be done by defining objects in class modules. Strictly speaking, abstraction is also achieved by using meaningful identifiers and extracting procedural code into methods (class members).
Here's an example of a procedure written in VBA that demonstrates abstraction:
Public Sub Test(ByVal checkin As Date, ByVal checkout As Date, ByVal custType As CustomerType)
Dim finder As New HotelFinder
InitializeHotels finder
Debug.Print finder.FindCheapestHotel(checkin, checkout, custType)
End Sub
It's easy to tell what this Test procedure does at a glance, because the abstraction level is very high: the implementation details are abstracted away into more specialized objects and methods.
Encapsulation - Classes can have private fields exposed by properties; classes can be made PublicNotCreatable, effectively exposing types to other VBA projects - and with a little bit of effort (by exporting the class module, opening it in your favorite text editor, manually editing class attributes, and re-importing the module), you can achieve actual read-only types. The fact that there are no parameterized constructors is irrelevant - just write a factory method that takes all the parameters you like and return an instance. This is COM, and COM likes factories anyway.
Here's an example of how the HotelFinder class from the above snippet encapsulates a Collection object and only exposes it through a Property Get accessor - code outside this class simply cannot Set this reference, it's encapsulated:
Private Type TFinder
Hotels As Collection
End Type
Private this As TFinder
Public Property Get Hotels() As Collection
Set Hotels = this.Hotels
End Property
Private Sub Class_Initialize()
Set this.Hotels = New Collection
End Sub
Private Sub Class_Terminate()
Set this.Hotels = Nothing
End Sub
Polymorphism - Implements lets you implement abstract interfaces (and concrete classes, too), and then you can write code against an ISomething abstraction that can just as well be a Foo or a Bar (given Foo and Bar both implement ISomething) - and all the code ever needs to see is ISomething. Method overloading is a language feature that VBA lacks, but overloading has nothing to do with polymorphism, which is the ability to present the same interface for differing underlying forms (data types).
Here's an example of applied polymorphism - the LogManager.Register method is happy to work with any object that implements the ILogger interface; here a DebugLogger and a FileLogger - two wildly different implementations of that interface, are being registered; when LogManager.Log(ErrorLevel, Err.Description) is invoked later, the two implementations will each do their own thing; DebugLogger will output to the immediate toolwindow, and FileLogger will write an entry into a specified log file:
LogManager.Register DebugLogger.Create("MyLogger", DebugLevel)
LogManager.Register Filelogger.Create("TestLogger", ErrorLevel, "C:\Dev\VBA\log.txt")
Inheritance - VBA does not let you derive a type from another: inheritance is not supported.
Now the question is, can a language that doesn't support inheritance be qualified as "object-oriented"? It turns out composition is very often preferable to inheritance, which has a number of caveats. And VBA will let you compose objects to your heart's content.
Is VBA an OOP language?
Given all that's missing is inheritance, and that composition is preferable to inheritance, I'm tempted to answer "Yes". I've written full-blown OOP VBA code before (Model-View-Presenter with Unit-of-Work and Repository, anyone?), that I wouldn't have written any differently in a "real OOP" language that supports inheritance.
Here are a few examples, all 100% VBA:
Model-View-ViewModel infrastructure & example (proof-of-concept)
Full-blown OOP Battleship game with Model-View-Controller (MVC) architecture
A reusable progress indicator
Model-View-Presenter pattern
UnitOfWork with Repository pattern
Polymorphic logger
Automagic Unit Testing framework
The code in this last link was eventually ported to C#, and quickly evolved into a COM add-in for the VBA IDE that gives you refactorings, better navigation, code inspections, and other tools.
VBA is only as limiting as you make it.
The short answers are no and no.
VBA is object based, allowing you to define classes and create instances of objects but it lacks the features that would normally be associated with a fully fledged OOP language, for example:
Encapsulation and abstraction: VBA provides this to an extent. Classes can be kept private with public interfaces defined, however there is no provision for constructors within classes. Classes have a Class_Inititalize event which can do some construction but cannot take arguments. Passing arguments would require a public factory function workarounds are still required to create a constructor-style design pattern.
Inheritance: Doesn't really exist in VBA but can be almost replicated
Polymorphism: Can be achieved to an extent through interfaces (using Implements) although the ability to overload functions (for example) doesn't exist and each "overload" would technically require a unique function name. You can work around this by passing in an object as the only parameter to a function or sub and vary the procedure depending on the values of the properties.
So while you can work with objects to an extent and MS Office applications are based around an object model, VBA is not truely an Object Oriented language. Polymorphism cannot be achieved to the extent that you would be familiar with in C++.
Related
I need to access class A 's private member in class B 's function and I want to use friend class. however, it seems can not be used as the c++ way .
"error C3816" class Class2 was previously declared or defined with a different WinRT modifier
How can I do to solve it?
P.S.: I can not write get/set function in public area, for I do not want class user to know private member .
Keep in mind why you'd declare a C++/CX ref class, it is to allow a program written in another language to use your C++ code. Such a language will not have any notion of the friend keyword, it is highly specific to the C++ language. Only a C++ compiler is capable of enforcing the friend contract. And in fact will not work at all when, say, that client code is written in C#, the CLR strongly enforces accessibility. Accordingly, the metadata format of the .winmd file that's generated by your project doesn't support expressing the notion of friend at all. So the compiler doesn't either.
First check to make sure you are using C++/CX appropriately, only use the ref class keyword if you actually intended to make the class accessible to other languages. Use a regular C++ class, plain class without the ref contextual keyword, if the class is only going to be used by your own code. If it is truly intended to be used as an interop class then you will have no other option but to make the member public.
Access specifiers are precautionary to prevent accidental access and so std C++ & stl performance with specific select CX friends- for say holding xaml binding datacontext containers- is straightforward approach. For whichever reason, VC++ is racist w. r. t. WinRT ABI mingling through OOP. One known alternative is to switch to generative meta programming instead of OO. To do this, keep template member function in the class that wants to befriend the consumer, and specialize this in the scope of the consumer and then onwards use the specialized version from within the consumer. Its sort of hidden from Microsoft family friendship affair.
You can solve this by using
friend ref class Class2;
instead of
friend class Class2
In OOP, there are entities (e.g. Person) which has attributes (e.g. name, address, etc) and it has methods. How do you describe new? Is it a method or just special token to bring an abstract entity to real one?
Sometimes it's a method, sometimes it's just syntactic sugar that invokes an allocator method. The language matters.
To your CS student? Don't sugar-coat it, they need to be able to get their heads around the concepts pretty quickly and using metaphors unrelated to the computer field, while fine for trying to explain it to your 80-year-old grandmother, will not help out a CS student much.
Simply put, tell them that a class is a specification for something and that an object is a concrete instance of that something. All new does is create a concrete instance based on the specification. This includes both creation (not necessarily class-specific, which is why I'd hesitate to call it a method, reserving that term for class-bound functions) and initialisation (which is class-specific).
Depending on the language new is a keyword which can be used as an operator or as a modifier. For instance in C# new can be used:
new operator - used to create objects on the heap and invoke constructors.
new modifier - used to hide an inherited member from a base class member
For brand new students I would describe new only as a keyword and leave the modifier out of the discussion. I describe classes as blueprints and new as the mechanism by which those blueprints turn into something tangible - objects.
You may want to checkout my question: How to teach object oriented programming to procedural programmers for other great answers on teaching OOP to new developers.
In most object-oriented languages, new is simply a convention for naming a factory method. But it's only one of many conventions.
In Ruby, for example, it is conventional to name the factory method [] for collection classes. In Python, classes are simply their own factories. In Io, the factory method is generally called clone, in Ioke and Seph it is called mimic.
In Smalltalk, factory methods often have more descriptive names than just new:. Something like fromList: or with:.
Here's a simile that has worked for me in the past.
An object definition is a Jello Mold. "new" is the process that actually makes a Jello snack from that mold. Each Goopy Jello thing that you give to your new neighbors can be different, this one's green, this one has bits of fruit in it, etc. It's its own unique "object." But the mold is the same.
Or you can use a factory analogy or something, (or blueprints vs building).
As far as its role in the syntax, it's just a keyword that lets the compiler know the allocate memory on the heap and run the constructor. There's not much more to it.
Smalltalk: it's an instance method on the metaclass. So "new is a method that returns a newly-allocated instance."
I tell people that a class is like a plan on how to make an object. An object is made from the class by new. If they need more than that, well, I just don't know what to say. ;-)
new is a keyword that calls the class constructor of the class to the right of it with the arguments listed inside ().
String str = new String("asdf");
str is defined as being a String class variable using the constructor and argument "asdf"
At least that's how it was presented to me.
In Ruby, I believe it's a instance method on the metaclass. In CLOS it's a generic function called make-instance but otherwise roughly the same.
In some languages, like Java, new has special syntax, and the metaclass part is hidden. In the case where you have to teach somebody OO with such a language, I don't know that there's much you can do. (Taking a break from teaching OO and Java to teach a second object system would almost certainly just confuse them further!) Just explain what it does, and that it's a special case.
You can say that a class is a prototype/blueprint for an object. When you give it the keyword new, that prototype/blueprint comes to life. It's like you're giving a breath of life to those dead instance.
In Java,
new allocates memory for a new class instance (object)
new runs a class's constructor to initialize that instance
new returns a reference to that new instance
As far as the relationship between object/instance and class, I sometimes think:
class is to instance as blueprint is to building
new in most languages does some variation of the following:
designate some memory region for a class instance, and if neccesary, inform the garbage collector about how to free that memory later.
initialize that memory region in the manner specific to that class, transforming the bytes of raw memory into bytes of a valid instance of the class
return a reference to the memory location to the caller.
Here is the problem statement: Calling a setter on the object should result in the object to change to an object of a different class, which language can support this?
Ex. I have a class called "Man" (Parent Class), and two children namely "Toddler" and "Old Man", they are its children because they override a behaviour in Man called as walk. ( i.e Toddler sometimes walks using both his hands and legs kneeled down and the Old man uses a stick to support himself).
The Man class has a attribute called age, I have a setter on Man, say setAge(int ageValue). I have 3 objects, 2 toddlers, 1 old-Man. (The system is up and running, I guess when we say objects it is obvious). I will make this call, toddler.setAge(80), I expect the toddler to change to an object of type Old Man. Is this possible? Please suggest.
Thanks,
This sounds to me like the model is wrong. What you have is a Person whose relative temporal grouping and some specific behavior changes with age.
Perhaps you need a method named getAgeGroup() which returns an appropriate Enum, depending on what the current age is. You also need an internal state object which encapsulates the state-specific behavior to which your Person delegates behavior which changes with age.
That said, changing the type of an instantiated object dynamically will likely only be doable only with dynamically typed languages; certainly it's not doable in Java, and probably not doable in C# and most other statically typed languages.
This is a common problem that you can solve using combination of OO modelling and design patterns.
You will model the class the way you have where Toddler and OldMan inherit from Man base class. You will need to introduce a Proxy (see GoF design pattern) class as your access to your Man class. Internally, proxy hold a man object/pointer/reference to either Toddler or OldMan. The proxy will expose all the interfaces that is exposed by Man class so that you can use it as it is and in your scenario, you will implement setAge similar to the pseudo code below:
public void setAge(int age)
{
if( age > TODDLER_MAX && myMan is Toddler)
myMan = new OldMan();
else
.....
myMan.setAge(age);
}
If your language does not support changing the classtype at runtime, take a look at the decorator and strategy patterns.
Objects in Python can change their class by setting the __class__ attribute. Otherwise, use the Strategy pattern.
I wonder if subclassing is really the best solution here. A property (enum, probably) that has different types of people as its possible values is one alternative. Or, for that matter, a derived property or method that tells you the type of person based on the age.
Javascript can do this. At any time you can take an existing object and add new methods to it, or change its existing methods. This can be done at the individual object level.
Douglas Crockford writes about this in Classical Inheritance in JavaScript:
Class Augmentation
JavaScript's dynamism allows us to add
or replace methods of an existing
class. We can call the method method
at any time, and all present and
future instances of the class will
have that method. We can literally
extend a class at any time.
Inheritance works retroactively. We
call this Class Augmentation to avoid
confusion with Java's extends, which
means something else.
Object Augmentation
In the static object-oriented
languages, if you want an object which
is slightly different than another
object, you need to define a new
class. In JavaScript, you can add
methods to individual objects without
the need for additional classes. This
has enormous power because you can
write far fewer classes and the
classes you do write can be much
simpler. Recall that JavaScript
objects are like hashtables. You
can add new values at any time. If the
value is a function, then it becomes a
method.
Common Lisp can: use the generic function CHANGE-CLASS.
I am surprised no one so far seemed to notice that this is the exact case for the State design pattern (although #Fadrian in fact described the core idea of the pattern quite precisely - without mentioning its name).
The state pattern is a behavioral software design pattern, also known as
the objects for states pattern. This pattern is used in computer
programming to represent the state of an object. This is a clean way for an
object to partially change its type at runtime.
The referenced page gives examples in Java and Python. Obviously it can be implemented in other strongly typed languages as well. (OTOH weakly typed languages have no need for State, as these support such behaviour out of the box.)
I've noticed that getting started with design patterns is pretty difficult for beginners. Understanding the design patterns structure requires a lot of time. Applying the design patterns to your practice requires a lot of time too. Agree, you can't see the differences between various types of the design patterns for the first time if you're not familiar to them. This problem is partially solved, if your classes have the suitable names. Also you can break the design patterned class structure you implement, if you're missing some rules writing your code by chance or you're not so experienced in the design patterns. The compilers can protect you and help you to implement the interfaces - if you're not implementing interface, you can't compile your application. It's a good and safe approach. And if the compilers could protect you when you implement design patterns classes too? Look, a lot of programming languages supports "foreach" statement. And if the programming languages could provide support for the factories, bridges, proxies, mementos, etc? If it could be true, you could use something like the following to apply abstract and concrete factory pattern (I prefer C# as the base language for the pseudocode; it's assumed that the contextual keywords are used):
public abstract factory class AF {
public product AP1 GetProduct1();
public product AP2 GetProduct2();
};
public concrete factory class CF1 : AF {
public product CP1 GetProduct1() { ... }
public product CP2 GetProduct2() { ... }
};
It think it could help you to understand the new sources and keep the application source code structure integrity. What do you think about this?
If I understand what you're saying, you think that new language features ought to overcome the need for the boilerplate code usually associated with implementing design patterns.
This is already happening, it is nothing new.
Take the singleton, for example, one of the most well known patterns. Everyone knows how to implement it: you declare the constructor private, you keep a single global instance of the object as a static property, and add a public method to retrieve it.
It's quite a few lines of code for what is conceptually very simple.
In Scala, you don't need any boilerplate to create a singleton. To complement the class keyword, Scala has an object keyword, which declares a singleton object:
object MainApp {
def main(args: Array[String]) {
println("Hello, world!")
}
}
At runtime there will be one single, global instance of MainApp. There is no need to instantiate it using new; in fact, you can't use new MainApp at all.
There is an argument that the existence of a design pattern in a language demonstrates a weakness in the design of the language itself, and that the next generation of languages should learn from the design patterns that were common in the previous generation.
For example, see Peter Norvigs famous presentation about Design Patterns being invisible in Dynamic languages.
In fact, it's easy to come up with examples of this process already happening - as you say, foreach loops are arguably embedded iterators, Ruby has a Singleton mixin to inherit from, any language with multimethods doesn't need a Visitor pattern. Groovy has built-in Builders.
Your specific example of a factory sounds a bit like Noops integration of Dependency Injection into the language spec.
Of course there's only so far a type-checker can go in assuring correctness of code (at the moment). And embedding design patterns into the language isn't going to obviate the need for familiarity with the core concepts, or to think hard about the application to the problem at hand.
Your example is interesting, you suggest adding several keywords and rules to the language that (and I'm not that familiar with C#) add no clear benefit. What would the "factory" keyword tell the type checker (or another programmer) that isn't clear from declaring "AF" as the equivalent of a Java interface, and having "product" as the return type for its methods?
I think you are on to something. But where you miss the point (in my opinion) is that you're trying to specify a design pattern, which, as MHarris said, they tend to become deprecated or obsolete as time passes, making the language dependent of them is not such a good idea.
What I think is that, there could be a 'composite' language, where you have two artifacts: the design specification language (coupled to the implementation language, don't think UML) and the implementation. So taking your example, it could be done like this:
Design specification:
single public Factory
methods:
T Get[T]
Notice that if done like this, because the design specification is meant to be abstract (no need to specify low level details right there and then), it can have constructs that facilitate writing specifications. Know that in the specification you don't need to say if a method is public or private, design specifications (not included algorithm pseudocode) only cares about publicly visible behavior, not private implementation details.
Implementation:
public class ConcreteFactory : Factory {
public Product1 GetProduct1() { ... }
public Product2 GetProduct2() { ... }
};
Here two approaches could be used:
The compiler could take the design as an artifact, and then check if the implementation code is congruent with it.
The compiler or runtime could provide part of the implementation that can be automatically generated (like the singleton implementation), and the code itself could assume its a singleton and not need to re-specify, for example:
class ConcreteFactory : Factory {
Product1 GetProduct1 { new ConcreteProduct1 }
Product2 GetProduct2 { new ConcreteProduct2 }
}
Notice that the implementation can overlook higher-level stuff like the visibility of the class and visibility of the methods, because this is already specified at the design level (DRY). If you ask me, this type of language would have to come with a specialized IDE too, so as to provide context information about the design for a type. As Jeff Atwood has commented, any new language should come with its specialized IDE.
Almost every Java book I read talks about using the interface as a way to share state and behaviour between objects that when first "constructed" did not seem to share a relationship.
However, whenever I see architects design an application, the first thing they do is start programming to an interface. How come? How do you know all the relationships between objects that will occur within that interface? If you already know those relationships, then why not just extend an abstract class?
Programming to an interface means respecting the "contract" created by using that interface. And so if your IPoweredByMotor interface has a start() method, future classes that implement the interface, be they MotorizedWheelChair, Automobile, or SmoothieMaker, in implementing the methods of that interface, add flexibility to your system, because one piece of code can start the motor of many different types of things, because all that one piece of code needs to know is that they respond to start(). It doesn't matter how they start, just that they must start.
Great question. I'll refer you to Josh Bloch in Effective Java, who writes (item 16) why to prefer the use of interfaces over abstract classes. By the way, if you haven't got this book, I highly recommend it! Here is a summary of what he says:
Existing classes can be easily retrofitted to implement a new interface. All you need to do is implement the interface and add the required methods. Existing classes cannot be retrofitted easily to extend a new abstract class.
Interfaces are ideal for defining mix-ins. A mix-in interface allows classes to declare additional, optional behavior (for example, Comparable). It allows the optional functionality to be mixed in with the primary functionality. Abstract classes cannot define mix-ins -- a class cannot extend more than one parent.
Interfaces allow for non-hierarchical frameworks. If you have a class that has the functionality of many interfaces, it can implement them all. Without interfaces, you would have to create a bloated class hierarchy with a class for every combination of attributes, resulting in combinatorial explosion.
Interfaces enable safe functionality enhancements. You can create wrapper classes using the Decorator pattern, a robust and flexible design. A wrapper class implements and contains the same interface, forwarding some functionality to existing methods, while adding specialized behavior to other methods. You can't do this with abstract methods - you must use inheritance instead, which is more fragile.
What about the advantage of abstract classes providing basic implementation? You can provide an abstract skeletal implementation class with each interface. This combines the virtues of both interfaces and abstract classes. Skeletal implementations provide implementation assistance without imposing the severe constraints that abstract classes force when they serve as type definitions. For example, the Collections Framework defines the type using interfaces, and provides a skeletal implementation for each one.
Programming to interfaces provides several benefits:
Required for GoF type patterns, such as the visitor pattern
Allows for alternate implementations. For example, multiple data access object implementations may exist for a single interface that abstracts the database engine in use (AccountDaoMySQL and AccountDaoOracle may both implement AccountDao)
A Class may implement multiple interfaces. Java does not allow multiple inheritance of concrete classes.
Abstracts implementation details. Interfaces may include only public API methods, hiding implementation details. Benefits include a cleanly documented public API and well documented contracts.
Used heavily by modern dependency injection frameworks, such as http://www.springframework.org/.
In Java, interfaces can be used to create dynamic proxies - http://java.sun.com/j2se/1.5.0/docs/api/java/lang/reflect/Proxy.html. This can be used very effectively with frameworks such as Spring to perform Aspect Oriented Programming. Aspects can add very useful functionality to Classes without directly adding java code to those classes. Examples of this functionality include logging, auditing, performance monitoring, transaction demarcation, etc. http://static.springframework.org/spring/docs/2.5.x/reference/aop.html.
Mock implementations, unit testing - When dependent classes are implementations of interfaces, mock classes can be written that also implement those interfaces. The mock classes can be used to facilitate unit testing.
I think one of the reasons abstract classes have largely been abandoned by developers might be a misunderstanding.
When the Gang of Four wrote:
Program to an interface not an implementation.
there was no such thing as a java or C# interface. They were talking about the object-oriented interface concept, that every class has. Erich Gamma mentions it in this interview.
I think following all the rules and principles mechanically without thinking leads to a difficult to read, navigate, understand and maintain code-base. Remember: The simplest thing that could possibly work.
How come?
Because that's what all the books say. Like the GoF patterns, many people see it as universally good and don't ever think about whether or not it is really the right design.
How do you know all the relationships between objects that will occur within that interface?
You don't, and that's a problem.
If
you already know those relationships,
then why not just extend an abstract
class?
Reasons to not extend an abstract class:
You have radically different implementations and making a decent base class is too hard.
You need to burn your one and only base class for something else.
If neither apply, go ahead and use an abstract class. It will save you a lot of time.
Questions you didn't ask:
What are the down-sides of using an interface?
You cannot change them. Unlike an abstract class, an interface is set in stone. Once you have one in use, extending it will break code, period.
Do I really need either?
Most of the time, no. Think really hard before you build any object hierarchy. A big problem in languages like Java is that it makes it way too easy to create massive, complicated object hierarchies.
Consider the classic example LameDuck inherits from Duck. Sounds easy, doesn't it?
Well, that is until you need to indicate that the duck has been injured and is now lame. Or indicate that the lame duck has been healed and can walk again. Java does not allow you to change an objects type, so using sub-types to indicate lameness doesn't actually work.
Programming to an interface means respecting the "contract" created by
using that interface
This is the single most misunderstood thing about interfaces.
There is no way to enforce any such contract with interfaces. Interfaces, by definition, cannot specify any behaviour at all. Classes are where behaviour happens.
This mistaken belief is so widespread as to be considered the conventional wisdom by many people. It is, however, wrong.
So this statement in the OP
Almost every Java book I read talks about using the interface as a way
to share state and behavior between objects
is just not possible. Interfaces have neither state nor behaviour. They can define properties, that implementing classes must provide, but that's as close as they can get. You cannot share behaviour using interfaces.
You can make an assumption that people will implement an interface to provide the sort of behaviour implied by the name of its methods, but that's not anything like the same thing. And it places no restrictions at all on when such methods are called (eg that Start should be called before Stop).
This statement
Required for GoF type patterns, such as the visitor pattern
is also incorrect. The GoF book uses exactly zero interfaces, as they were not a feature of the languages used at the time. None of the patterns require interfaces, although some can use them. IMO, the Observer pattern is one in which interfaces can play a more elegant role (although the pattern is normally implemented using events nowadays). In the Visitor pattern it is almost always the case that a base Visitor class implementing default behaviour for each type of visited node is required, IME.
Personally, I think the answer to the question is threefold:
Interfaces are seen by many as a silver bullet (these people usually labour under the "contract" misapprehension, or think that interfaces magically decouple their code)
Java people are very focussed on using frameworks, many of which (rightly) require classes to implement their interfaces
Interfaces were the best way to do some things before generics and annotations (attributes in C#) were introduced.
Interfaces are a very useful language feature, but are much abused. Symptoms include:
An interface is only implemented by one class
A class implements multiple interfaces. Often touted as an advantage of interfaces, usually it means that the class in question is violating the principle of separation of concerns.
There is an inheritance hierarchy of interfaces (often mirrored by a hierarchy of classes). This is the situation you're trying to avoid by using interfaces in the first place. Too much inheritance is a bad thing, both for classes and interfaces.
All these things are code smells, IMO.
It's one way to promote loose coupling.
With low coupling, a change in one module will not require a change in the implementation of another module.
A good use of this concept is Abstract Factory pattern. In the Wikipedia example, GUIFactory interface produces Button interface. The concrete factory may be WinFactory (producing WinButton), or OSXFactory (producing OSXButton). Imagine if you are writing a GUI application and you have to go look around all instances of OldButton class and changing them to WinButton. Then next year, you need to add OSXButton version.
In my opinion, you see this so often because it is a very good practice that is often applied in the wrong situations.
There are many advantages to interfaces relative to abstract classes:
You can switch implementations w/o re-building code that depends on the interface. This is useful for: proxy classes, dependency injection, AOP, etc.
You can separate the API from the implementation in your code. This can be nice because it makes it obvious when you're changing code that will affect other modules.
It allows developers writing code that is dependent on your code to easily mock your API for testing purposes.
You gain the most advantage from interfaces when dealing with modules of code. However, there is no easy rule to determine where module boundaries should be. So this best practice is easy to over-use, especially when first designing some software.
I would assume (with #eed3s9n) that it's to promote loose coupling. Also, without interfaces unit testing becomes much more difficult, as you can't mock up your objects.
Why extends is evil. This article is pretty much a direct answer to the question asked. I can think of almost no case where you would actually need an abstract class, and plenty of situations where it is a bad idea. This does not mean that implementations using abstract classes are bad, but you will have to take care so you do not make the interface contract dependent on artifacts of some specific implementation (case in point: the Stack class in Java).
One more thing: it is not necessary, or good practice, to have interfaces everywhere. Typically, you should identify when you need an interface and when you do not. In an ideal world, the second case should be implemented as a final class most of the time.
There are some excellent answers here, but if you're looking for a concrete reason, look no further than Unit Testing.
Consider that you want to test a method in the business logic that retrieves the current tax rate for the region where a transaction occurrs. To do this, the business logic class has to talk to the database via a Repository:
interface IRepository<T> { T Get(string key); }
class TaxRateRepository : IRepository<TaxRate> {
protected internal TaxRateRepository() {}
public TaxRate Get(string key) {
// retrieve an TaxRate (obj) from database
return obj; }
}
Throughout the code, use the type IRepository instead of TaxRateRepository.
The repository has a non-public constructor to encourage users (developers) to use the factory to instantiate the repository:
public static class RepositoryFactory {
public RepositoryFactory() {
TaxRateRepository = new TaxRateRepository(); }
public static IRepository TaxRateRepository { get; protected set; }
public static void SetTaxRateRepository(IRepository rep) {
TaxRateRepository = rep; }
}
The factory is the only place where the TaxRateRepository class is referenced directly.
So you need some supporting classes for this example:
class TaxRate {
public string Region { get; protected set; }
decimal Rate { get; protected set; }
}
static class Business {
static decimal GetRate(string region) {
var taxRate = RepositoryFactory.TaxRateRepository.Get(region);
return taxRate.Rate; }
}
And there is also another other implementation of IRepository - the mock up:
class MockTaxRateRepository : IRepository<TaxRate> {
public TaxRate ReturnValue { get; set; }
public bool GetWasCalled { get; protected set; }
public string KeyParamValue { get; protected set; }
public TaxRate Get(string key) {
GetWasCalled = true;
KeyParamValue = key;
return ReturnValue; }
}
Because the live code (Business Class) uses a Factory to get the Repository, in the unit test you plug in the MockRepository for the TaxRateRepository. Once the substitution is made, you can hard code the return value and make the database unneccessary.
class MyUnitTestFixture {
var rep = new MockTaxRateRepository();
[FixtureSetup]
void ConfigureFixture() {
RepositoryFactory.SetTaxRateRepository(rep); }
[Test]
void Test() {
var region = "NY.NY.Manhattan";
var rate = 8.5m;
rep.ReturnValue = new TaxRate { Rate = rate };
var r = Business.GetRate(region);
Assert.IsNotNull(r);
Assert.IsTrue(rep.GetWasCalled);
Assert.AreEqual(region, rep.KeyParamValue);
Assert.AreEqual(r.Rate, rate); }
}
Remember, you want to test the business logic method only, not the repository, database, connection string, etc... There are different tests for each of those. By doing it this way, you can completely isolate the code that you are testing.
A side benefit is that you can also run the unit test without a database connection, which makes it faster, more portable (think multi-developer team in remote locations).
Another side benefit is that you can use the Test-Driven Development (TDD) process for the implementation phase of development. I don't strictly use TDD but a mix of TDD and old-school coding.
In one sense, I think your question boils down to simply, "why use interfaces and not abstract classes?" Technically, you can achieve loose coupling with both -- the underlying implementation is still not exposed to the calling code, and you can use Abstract Factory pattern to return an underlying implementation (interface implementation vs. abstract class extension) to increase the flexibility of your design. In fact, you could argue that abstract classes give you slightly more, since they allow you to both require implementations to satisfy your code ("you MUST implement start()") and provide default implementations ("I have a standard paint() you can override if you want to") -- with interfaces, implementations must be provided, which over time can lead to brittle inheritance problems through interface changes.
Fundamentally, though, I use interfaces mainly due to Java's single inheritance restriction. If my implementation MUST inherit from an abstract class to be used by calling code, that means I lose the flexibility to inherit from something else even though that may make more sense (e.g. for code reuse or object hierarchy).
One reason is that interfaces allow for growth and extensibility. Say, for example, that you have a method that takes an object as a parameter,
public void drink(coffee someDrink)
{
}
Now let's say you want to use the exact same method, but pass a hotTea object. Well, you can't. You just hard-coded that above method to only use coffee objects. Maybe that's good, maybe that's bad. The downside of the above is that it strictly locks you in with one type of object when you'd like to pass all sorts of related objects.
By using an interface, say IHotDrink,
interface IHotDrink { }
and rewrting your above method to use the interface instead of the object,
public void drink(IHotDrink someDrink)
{
}
Now you can pass all objects that implement the IHotDrink interface. Sure, you can write the exact same method that does the exact same thing with a different object parameter, but why? You're suddenly maintaining bloated code.
Its all about designing before coding.
If you dont know all the relationships between two objects after you have specified the interface then you have done a poor job of defining the interface -- which is relatively easy to fix.
If you had dived straight into coding and realised half way through you are missing something its a lot harder to fix.
You could see this from a perl/python/ruby perspective :
when you pass an object as a parameter to a method you don't pass it's type , you just know that it must respond to some methods
I think considering java interfaces as an analogy to that would best explain this . You don't really pass a type , you just pass something that responds to a method ( a trait , if you will ).
I think the main reason to use interfaces in Java is the limitation to single inheritance. In many cases this lead to unnecessary complication and code duplication. Take a look at Traits in Scala: http://www.scala-lang.org/node/126 Traits are a special kind of abstract classes, but a class can extend many of them.