简体   繁体   中英

Java Relationship between interfaces/abstract classes

I am trying to build an algorithm that works in different ways depending on a traversal strategy and an update strategy . However, not every update Strategy works with every traversal strategy. Hence, I figured that an update strategy must only be instantiated with a corresponding traversal strategy. I wanted to force a constructor for that (see below). So that the subclasses would have to check if they support the strategy.

I am currently having an Interface

public interface TraversalStrategy {
...
}

And an (invalid) abstract class

public abstract class UpdateStrategy {
protected TraversalStrategy travStrategy;

public abstract UpdateStrategy(TraversalStrategy travStrategy);
}

What is the correct way to imply such a dependency? I could of course add an empty body to this constructor but that seemed wrong to me.

Update: Inspired by the Answer of @Kayaman, I created a new class TestcaseGenerator that is used to construct a valid combination.

public TestcaseGenerator(TraversalStrategy travStrategy, UpdateStrategy updStrategy){
    if (updStrategy.supports(travStrategy)){
        this.travStrategy = travStrategy;
        this.updStrategy = updStrategy;
    }
}

当前类图

What I don't like about this yet is, that it would now be unnecessary to give the instance of TraversalStrategy to the UpdateStrategy in order to check if it is supported. I would rather only need the class name. Can you tell me how to achieve that? Experiments with .getClass().getName() seemed horrible. Currently I am doing:

public boolean supports(TraversalStrategy travStrategy){
   if(travStrategy instanceof UpstreamTraversalStrategy){ 
       return true; 
   }
   return false;
}

One common way is to have the superclass constructor call an abstract method such as isSupported(TraversalStrategy t); and fail if it's not true.

\n

The subclasses would then implement the method accordingly by using instanceof or any other way to determine if the strategy is a supported one.

One approach would be to create a third class with a Builder pattern approach. Instead of providing TraversalStrategy as a parameter to UpdateStrategy , they would both be included in the third object (and they could be checked at build() to prevent incompatible strategies).

You could then have general functionality in the third class, with the strategy classes becoming lighter.

Even an abstract class must have a valid constructor. Even through it is not possible to create an instance of an abstract class, a non abstract subclass always calls the constructor of the super class first. Therefore your constructor on the abstract class needs a body to initialize the TraversalStrategy .

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM