Originally I picked the correct User implementation, based on domain and realm data from the Java EE server. However that was company code, so I had to rewrite the example with numbers. I hope the underlying pattern is still understandable though. For those unfamiliar with CDI, @Inject Instance allows you to iterate through all implementations of an interface.
public class NumberPicker { @Inject private Instance<NumberMapper> mappers; public Number parse (String string) { for( NumberMapper mapper : mappers ){ if( mapper.isApplicable(string) ){ return mapper.apply(string); } } throw new InvalidArgumentException("Can not parse " + string); } } public interface NumberMapper { boolean isApplicable (String string); Number apply (String string); } public class ByteMapper implements NumberMapper { @Override public boolean isApplicable (String string) { return string.length() == 1; } @Override public Number apply (String string) { return (byte) string.charAt(0); } } public class IntegerMapper implements NumberMapper { @Override public boolean isApplicable (String string) { if( string.length() == 1 ){ return false; } try { Integer.parseInt(string); return true; }catch( NumberFormatException e ){ return false; } } @Override public Number apply (String string) { return Integer.parseInt(string); } } public class FloatMapper implements NumberMapper @Override public boolean isApplicable (String string) { if( string.length() == 1 ) { return false; } try { Integer.parseInt(string); return false; }catch( NumberFormatException e){ } try { Float.parseFloat(string); return true; }catch( NumberFormatException e){ return false; } } @Override public Number apply (String string) { return Float.parseFloat(string); } }
Advertisement
Answer
I think you are talking about the Strategy Pattern:
public interface Strategy { boolean test(); void execute(); } public class FirstStrategy implements Strategy{ @Override public boolean test() { //returns true or false } @Override public void execute() { //your custom implementation } } public class SecondStrategy implements Strategy{ @Override public boolean test() { //returns true or false } @Override public void execute() { //your custom implementation } }
Then you have your list of strategies:
List<Strategy> strategiesList = List.of(new FirstStrategy(), new SecondStrategy());
Thus:
strategiesList.stream() .filter(aStrategy -> aStrategy.test()) .findFirst() .ifPresent(aStrategy -> aStrategy.execute());