【问题标题】:More elegant way to implement更优雅的实现方式
【发布时间】:2019-12-20 08:28:32
【问题描述】:
ArrayList<Boolean> values = new ArrayList<>(Arrays.asList(true, false, true, false, false, true));

List<String> filter = Arrays.asList("TRUE");
List<String> filter = Arrays.asList("FALSE");
List<String> filter = Arrays.asList("TRUE","FALSE");

if (!filter.isEmpty()) {
    List<Boolean> collect = values.stream()
            .filter(i -> i ? filter.contains("TRUE") : filter.contains("FALSE"))
            .collect(Collectors.toList());
    System.out.println(collect);
} else { System.out.println(values);}

使用过滤器值TRUEFALSETRUE,FALSE,我得到所需的结果[true, true, true][false, false, false][true, false, true, false, false, true]。如果过滤器为空,则应按原样返回列表。 “TRUE”或“FALSE”可以代表任何字符串..

有没有更优雅的实现方式?

【问题讨论】:

  • 用于改进工作代码的站点错误。最好在CodeReview 询问
  • 为什么你的过滤器值是字符串?您不能将它们映射到Boolean 吗? “任何字符串”是什么意思?此代码是否按预期工作?我不确定你的问题。
  • filter(b -&gt; filter.contains(b ? "TRUE" : "FALSE")) 会有所改进
  • 如何编译?
  • @Joe 出于某种原因,OP 选择为filter 显示三个可能的值,这也是我不清楚这个问题的部分原因。

标签: java java-stream predicate


【解决方案1】:

如果过滤器真的只能是4个有效组合,那么你可以作弊:

if (filter.size() == 1) {
    Boolean removeTrue = filter.contains("FALSE");
    values.removeIf(removeTrue::equals);
}
System.out.println(values);

【讨论】:

  • 相当整洁!我已经尝试过使用谓词,但从未到过这里..
  • 使用removeIf而不是让流创建一个新的列表实例在速度上有优势吗?
  • @tli 您要求“更优雅的方式”,而不是更快的方式。除非列表很大,否则您不会注意到性能差异。
【解决方案2】:

你可以:

  1. 测试谓词内部是否为空(性能成本非常小)
  2. 对包含值使用三元组

因此消除了if-else 和对contains() 的额外调用:

List<Boolean> collect = values.stream()
        .filter(i -> filter.isEmpty() || filter.contains(i ? "TRUE" : "FALSE"))
        .collect(Collectors.toList());

System.out.println(collect);

【讨论】:

    【解决方案3】:

    我不确定这里的目标是什么,但优雅可能在旁观者的眼中,所以,给你。

    public static void main(String[] args) {
        System.out.println(go(
                Arrays.asList(true, false, true, false, false, true), 
                Arrays.asList("TRUE")));
    }
    
    static List<Boolean> go(final List<Boolean> values, final List<String> filter) {
        if (filter.isEmpty())
            return values;
        return values
                .stream()
                .filter(i -> filter.contains(i.toString().toUpperCase()))
                .collect(Collectors.toList());
    }
    

    【讨论】:

    • 过滤条件可以是任何字符串,意味着 true 应该匹配例如 "X" 和 false 匹配 "Y"。
    猜你喜欢
    • 2022-01-23
    • 1970-01-01
    • 2013-06-28
    • 2021-03-05
    • 1970-01-01
    • 2015-06-22
    • 1970-01-01
    • 2014-05-15
    • 2018-06-27
    相关资源
    最近更新 更多