Java 8 列表处理 - 有条件地添加元素

2022-08-31 20:43:40

我有以下代码:

List<Object> list = new ArrayList<>();
list.addAll(method1());
if(list.isEmpty()) { list.addAll(method2()); }
if(list.isEmpty()) { list.addAll(method3()); }
if(list.isEmpty()) { list.addAll(method4()); }
if(list.isEmpty()) { list.addAll(method5()); }
if(list.isEmpty()) { list.addAll(method6()); }
return list;

有没有一种有条件地添加元素的好方法,也许使用流操作?我想从方法2添加元素,只有当列表为空时,否则返回等等。

编辑:值得一提的是,这些方法包含繁重的逻辑,因此需要阻止执行。


答案 1

您可以尝试检查 的返回值。每当列表被修改时,它就会返回,所以试试这个:addAlltrue

List<Object> list = new ArrayList<>();
// ret unused, otherwise it doesn't compile
boolean ret = list.addAll(method1())
    || list.addAll(method2()) 
    || list.addAll(method3())
    || list.addAll(method4())
    || list.addAll(method5())
    || list.addAll(method6());
return list;

由于惰性求值,添加至少一个元素的第一个操作将阻止调用其余元素。我喜欢“||”很好地表达了意图的事实。addAll


答案 2

我会简单地使用供应商流并过滤:List.isEmpty

Stream.<Supplier<List<Object>>>of(() -> method1(), 
                                  () -> method2(), 
                                  () -> method3(), 
                                  () -> method4(), 
                                  () -> method5(), 
                                  () -> method6())
    .map(Supplier<List<Object>>::get)
    .filter(l -> !l.isEmpty())
    .findFirst()
    .ifPresent(list::addAll);

return list;

findFirst()将防止在其中一个方法返回第一个非空列表时进行不必要的调用。methodN()

编辑:
如下面的注释中所述,如果您的对象未使用任何其他内容进行初始化,那么直接返回流的结果是有意义的:list

return  Stream.<Supplier<List<Object>>>of(() -> method1(), 
                                          () -> method2(), 
                                          () -> method3(), 
                                          () -> method4(), 
                                          () -> method5(), 
                                          () -> method6())
    .map(Supplier<List<Object>>::get)
    .filter(l -> !l.isEmpty())
    .findFirst()
    .orElseGet(ArrayList::new);