Java обобщение цепочки - PullRequest
       7

Java обобщение цепочки

0 голосов
/ 25 ноября 2018

У меня есть класс, который реализует беглый шаблон интерфейса следующим образом:

Class Rules {

  private List<Map<String, String>> listOfMap;

public Rules getListAddresses(List<Map<String, String>> listAddresses) {
    listOfMap = new ArrayList<>(listAddresses);
    return this;
}

  public List<Map<String, String>> fOut() {
    return listOfMap;
  }

  public Rules f1() {
      listOfMap = ....;
      return this;
  }

  public Rules f2() {
      listOfMap = ....;
      return this;
  }

...
...

}

У меня есть несколько классов, которые используют цепочку следующим образом.

Class A extends Rules{

        List<Map<String, String>> listOfMap = dropActiveStatus(listOfMapInout);

        //TODO make some king of CONSTANT to function name mapping
        List<Map<String, String>> listOfMapOut = this.getListAddresses(listOfMap)
            .f1()
            .f2()
            .f3()
            .f4()
            .fOut();

....
}

Class B extends Rules{

        List<Map<String, String>> listOfMap = dropActiveStatus(listOfMapInout);

        //TODO make some king of CONSTANT to function name mapping
        List<Map<String, String>> listOfMapOut = this.getListAddresses(listOfMap)
            .f5()
            .f6()
            .fOut();

....
}

Я хочу определитьуниверсальный класс вместо нескольких классов A, B, C ....

Как я могу обеспечить это?

Если бы я мог определить некоторые константы для каждого вызова метода и определить константы по порядку во время конструктора каждого класса, тогда я мог бы использовать эти константы для вызова метода в соответствии со спецификацией класса.

Ответы [ 2 ]

0 голосов
/ 14 декабря 2018

Мне кажется, что решение можно упростить:

public class RuleApplier {
    private UnaryOperator<Rules> operator;

    public RuleApplier(UnaryOperator<Rules> operator) {
        Objects.requireNonNull(operator);
        this.operator = operator;
    }

    public List<Map<String, String>> apply(List<Map<String, String>> listOfMap) {
        Rules rules = new Rules().getListAddresses(listOfMap);
        return operator.apply(rules).fOut();
    }
}

А затем использование:

RuleApplier applierA = new RuleApplier(rules -> rules.f1().f2().f3().f4());
List<Map<String, String>> listOfMapOutA = applierA.apply(listOfMap);
0 голосов
/ 25 ноября 2018

С функциональным интерфейсом, который соответствует вашим функциям правил f1, f2, f3 ...:

interface RuleFunction extends Function<Rules, Rules> { }

Вы можете написать один класс, который будет применять любую комбинацию правил, которые выпередайте его:

public class RuleApplier {
    private RuleFunction[] steps;

    public RuleApplier(RuleFunction... steps) {
        Objects.requireNonNull(steps);
        this.steps = steps;
    }

    public List<Map<String, String>> apply(List<Map<String, String>> listOfMap) {
        Rules rules = new Rules().getListAddresses(listOfMap);
        for (RuleFunction step : steps) {
            rules = step.apply(rules);
        }
        return rules.fOut();
    }
}

Когда вы создаете ссылки на метод класса, предоставьте удобное сокращение, которое можно использовать для ссылки на применяемые правила:

List<Map<String, String>> listOfMap = dropActiveStatus(listOfMapInout);

RuleApplier applierA = new RuleApplier(Rules::f1, Rules::f2, Rules::f3, Rules::f4);
List<Map<String, String>> listOfMapOutA = applierA.apply(listOfMap);

RuleApplier applierB = new RuleApplier(Rules::f5, Rules::f6);
List<Map<String, String>> listOfMapOutB = applierB.apply(listOfMap);
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...