在java8中,如何在lambdas foreach块中设置全局值?

2022-09-01 08:45:42
    public void test(){
       String x;
       List<String> list=Arrays.asList("a","b","c","d");

       list.forEach(n->{
          if(n.equals("d"))
            x="match the value";
       });
    }

1.像上面的代码一样,我想在foreach块旁边设置一个变量的值,它能工作吗?

2.为什么?

3.前迭代器是有序的还是无序的?

4.我认为 lamdas foreach 块对于迭代器来说很酷,很简单,但这确实是一件复杂的事情,而不是 java 7 或之前的相同工作。


答案 1

当然,你可以通过一个技巧“使外部值可变”:

public void test() {
    String[] x = new String[1];
    List<String> list = Arrays.asList("a", "b", "c", "d");

    list.forEach(n -> {
        if (n.equals("d"))
            x[0] = "match the value";
    });
}

不过,准备好迎接团队中功能纯粹主义者的殴打。然而,更好的是使用一种功能更强大的方法(类似于Sleiman的方法):

public void test() {
    List<String> list = Arrays.asList("a", "b", "c", "d");
    String x = list.stream()
                   .filter("d"::equals)
                   .findAny()
                   .map(v -> "match the value")
                   .orElse(null);
}

答案 2
  1. 不,你不能这样做。(虽然你应该自己尝试一下)
  2. 因为匿名内部类和 lambda 表达式中使用的变量必须是 。effectively final
  3. 您可以使用 和 更简洁地实现相同的效果。filtermap

    Optional<String> d = list.stream()
                             .filter(c -> c.equals("d"))
                             .findFirst()
                             .map(c -> "match the value");