这是另一种方法:这种方法允许转换步骤产生一个列表。例如,转换可以将一个字符串拆分为多个子字符串。此外,如果转换任何值产生异常,它允许通用异常处理代码。它还允许使用空列表作为返回值,而不是必须测试以避免 NullPointerException 的模棱两可的空值。这个问题的主要问题是它在移动到下一步之前完整地完成了每个转换步骤,这可能不是内存效率。
public class Chain<IN, MEDIAL, OUT> {
private final Chain<IN, ?, MEDIAL> head;
private final Transformer<MEDIAL, OUT> tail;
public static <I, O> Chain<I, I, O> makeHead(@Nonnull Transformer<I, O> tail) {
return new Chain<>(null, tail);
}
public static <I, M, O> Chain<I, M, O> append(@Nonnull Chain<I, ?, M> head, @Nonnull Transformer<M, O> tail) {
return new Chain<>(head, tail);
}
private Chain(@Nullable Chain<IN, ?, MEDIAL> head, @Nonnull Transformer<MEDIAL, OUT> tail) {
this.head = head;
this.tail = tail;
}
public List<OUT> run(List<IN> input) {
List<OUT> allResults = new ArrayList<>();
List<MEDIAL> headResult;
if (head == null) {
headResult = (List<MEDIAL>) input;
} else {
headResult = head.run(input);
}
for (MEDIAL in : headResult) {
// try/catch here
allResults.addAll(tail.transform(in));
}
return allResults;
}
public static void main(String[] args) {
Transformer<String, Integer> pipe1 = new Transformer<String, Integer>() {
@Override
public List<Integer> transform(String s) {
return Collections.singletonList(Integer.valueOf(s) * 3);
}
};
Transformer<Integer, Long> pipe2 = new Transformer<Integer, Long>() {
@Override
public List<Long> transform(Integer s) {
return Collections.singletonList(s.longValue() * 5);
}
};
Transformer<Long, BigInteger> pipe3 = new Transformer<Long, BigInteger>() {
@Override
public List<BigInteger> transform(Long s) {
return Collections.singletonList(new BigInteger(String.valueOf(s * 7)));
}
};
Chain<String, ?, Integer> chain1 = Chain.makeHead(pipe1);
Chain<String, Integer, Long> chain2 = Chain.append(chain1, pipe2);
Chain<String, Long, BigInteger> chain3 = Chain.append(chain2, pipe3);
List<BigInteger> result = chain3.run(Collections.singletonList("1"));
System.out.println(result);
}
}