Saturday 20 June 2015

Real difference between an Interface and an Abstract Class

This is one of the most frequently asked questions in a java interview and sadly most of the candidates give the wrong answer(my personal experience).

The first answer is a class can extends only one Abstract class but it can implements more than one interface. But this is not the sufficient answer.

The second answer people give is 'Abstract class can have an implemented method which an Interface can't have'. This is true but this makes Abstract class more desirable than an Interface, so why we use Interface more often(or almost always) for Abstraction than we use an Abstract class? 

The real answer is for defining the 'Contract'.

So what is the 'Contract' in terms of software design?

In a very plain language, contract is something which gives the client(user) code a guarantee of not failing.

For example, if you have designed a system for an ATM machine and have the following methods:

getAccountBalance();
withdrawMoney();
getLastTenTransactions();

The code which is using your ATM machine code will want the guarantee that it doesn't get into trouble any time in the future. This commitment is the contract.

So why Interface can provide it and an Abstract class could fail?

OK, let's find the answer by defining and implementing in the both cases.

Let's first do it by defining by an Abstract Class.


public abstract class ATMMachineAbstract {
public abstract int getAccountBalance();
public abstract int withdrawMoney();
public abstract String[] getLastTenTransactions();

}

The implementation of this class should look like this:

public class ATMMachine extends ATMMachineAbstract{


public int getAccountBalance() {
return 0;
}


public int withdrawMoney() {
return 0;
}


public String[] getLastTenTransactions() {
return null;
}

}

Now let's do the same thing by using an Interface:


public interface ATMMachineInterface {
public int getAccountBalance();
public int withdrawMoney();
public String[] getLastTenTransactions();

}

And the implementation of this should look like:


public class ATMMachineImplementingInterface implements ATMMachineInterface{


public int getAccountBalance() {
return 0;
}


public int withdrawMoney() {
return 0;
}


public String[] getLastTenTransactions() {
return null;
}

}

Now the client code may use these codes something like this:


public class Main {

/**
* @param args
*/
public static void main(String[] args) {
ATMMachineInterface atmi=new ATMMachineImplementingInterface();
atmi.getAccountBalance();
ATMMachineAbstract atmabs=new ATMMachine();
atmabs.getAccountBalance();

}

}

Both of the ways look similar until we some crazy guy do the magic.
So here the magic goes.

One fine day a crazy guy change the abstract class like this:


public abstract class ATMMachineAbstract {
private  int getAccountBalance(){
return 0;
};
public abstract int withdrawMoney();
public abstract String[] getLastTenTransactions();

}

In this situation, the implementation code(class ATMMachine) doesn't complain at all but the client code start giving errors.

But this situation can never arise in case of an Interface.

That is the reason Interface is used to define the contract.

I hope, i have explained the concept.








No comments:

Post a Comment