jeudi 31 mars 2016

How to get rid of the inheritance?

I have an algorithm, and I have 2 different implementations of the algorithm. These implementations should be called from many places, depending on the mode selected by the user. I wouldn't like to write conditional statements at all places where implementations called. So, I create an abstract class and Implementations inherit it. I can set the desired mode in one place like this:

if(firstMode){
    list = new ListForm1();
}
else{
    list = new LiastForm2();
}

And after that in all other places I can enjoy all the benefits of polymorphism. It works good but I want to get rid of the inheritance of the following reasons:

  1. I heard that composition is much better than inheritance.
  2. The first form of the algorith is much easier then the second form. In the first form I have only 3 methods and in second form I have 15 methods. The abstract class had to include all 15 (and 5 common methods). It turns out that the 12 methods not using by the first form.
  3. Theoretically, there may be a new form of the algorithm, which will have even less in common with the other two, but it will bring 10 new methods and all of them will have to add an abstract class.

The Strategy Pattern, as I understand, does not make sense to use here. Here is the example of Strategy Pattern:

//abstract strategy
    interface Strategy {
        int execute(int a, int b); 
    }

// concrete strategy1
class ConcreteStrategyAdd implements Strategy {

    public int execute(int a, int b) {
        return a + b;  
    }
}

// concrete strategy2
class ConcreteStrategySubtract implements Strategy {

    public int execute(int a, int b) {
        return a - b;  
    }
}

//concrete strategy3
class ConcreteStrategyMultiply implements Strategy {

    public int execute(int a, int b) {
        return a * b; 
    }    
}

class Context {

    private Strategy strategy;

    public Context() {
    }

    // Set new concrete strategy
    public void setStrategy(Strategy strategy) {
        this.strategy = strategy;
    }

    // use strategy
    public int executeStrategy(int a, int b) {
        return strategy.execute(a, b);
    }
}

It has the same problems. Strategies should be linked with each other. If I link them with the interface instead of an abstract class it will be even worse. Interface will contain a lot of methods but many of them will not be needed for the first form of the algorithm. In addition, general methods have to duplicate in all concrete strategies. I can not provide a default implementation in the interface.

Moreever, I don't understand how to use composition here. As I understand, Strategy Pattern already used composition. Class Context includes the instance of Strategy as a field. But maybe it is delegation.

So, here is my question:

Can I get rid of all the above problems (too many methods of an abstract class, the strong connection, because of which it will be difficult to add a new form of an algorithm), but still use conditional statements in only one place, not in all cases when I need some form of algorithm.

Aucun commentaire:

Enregistrer un commentaire