解决lambda中必须为final的方式

简介: 解决lambda中必须为final的方式

一个真正而且热切地工作的人总是有希望的——只有怠惰才是永恒的绝望。——卡莱尔

在开发中使用lambda经常出现一个问题

编译提示我们lambda中使用的变量必须为final或者effectively final

int i = 2;
BigDecimal j = BigDecimal.ZERO;
j = BigDecimal.TEN;
List<String> stringList = mpUserMapper.selectList(Wrappers.lambdaQuery()).stream().map(UserDataObject::getUsername).collect(Collectors.toList());
stringList = stringList.stream().distinct().collect(Collectors.toList());
List<String> strings = new ArrayList<>(10);
strings.stream().peek(s -> {
    stringList.add(s);
    i = 3;
    j.add(BigDecimal.ONE);
}).collect(Collectors.toList());

如何处理,我想大家一般都是直接点转换为自动

int转换为AtomicIntegerlist赋值给为finalList

之后就是这样子

AtomicInteger i = new AtomicInteger(2);
BigDecimal j = BigDecimal.ZERO;
j = BigDecimal.TEN;
List<String> stringList = mpUserMapper.selectList(Wrappers.lambdaQuery()).stream().map(UserDataObject::getUsername).collect(Collectors.toList());
stringList = stringList.stream().distinct().collect(Collectors.toList());
List<String> strings = new ArrayList<>(10);
List<String> finalStringList = stringList;
BigDecimal finalJ = j;
strings.stream().peek(s -> {
    finalStringList.add(s);
    i.set(3);
    finalJ.add(BigDecimal.ONE);
}).collect(Collectors.toList());

虽然上面的integeridea帮我们转换成了atomic原子类,但下面的stringList和变量j都赋值给了一个临时变量【final+变量名】

编译报错是解决了,但代码的可读性降低了

那么有没有更优雅的解决方案呢?其实是有的

我们这里出现变量必须为final或者effectively final的提示,造成的原因是因为我们对变量进行了二次赋值

我们这里可以像AtomicInteger一样使用原子类AtomicReference

再观察stringList,我们当然可以接连下面的去重操作,把两行变为一行去解决

但如果场景发生变化,我们要执行一些判断或者其他逻辑,再进行赋值

对于这种场景,使用两行变一行的方式就不好用了

我们就可以使用Lists.addAll代替我们的赋值操作

这种方式比一开始的使用一个临时变量赋值的方式感觉要好多了

特别是大量用到stream的时候,如果是一堆用于lambda的临时变量,很可能会犯晕

相关文章
|
10月前
|
前端开发 Java API
Spring MVC 数据绑定机制详解:@ModelAttribute vs. @RequestParam 和 @PathVariable
本文深入解析了Spring MVC的数据绑定机制,重点对比了`@RequestParam`、`@PathVariable`和`@ModelAttribute`三种注解的使用场景与功能。`@RequestParam`适用于从查询参数或表单数据中提取简单值;`@PathVariable`用于从URL路径中获取资源标识符;而`@ModelAttribute`则能将多个请求参数自动绑定到Java对象,支持复杂数据结构的处理。通过实际案例分析,帮助开发者根据需求选择合适的注解,提升API设计与表单处理效率。
796 9
|
存储 Java 编译器
【Java异常】Variable used in lambda expression should be final or effectively final
【Java异常】Variable used in lambda expression should be final or effectively final
676 0
|
程序员
【工具使用】Intellij IDEA 自动清除无效 import 包 和 清除无效 import包 的快捷键
【工具使用】Intellij IDEA 自动清除无效 import 包 和 清除无效 import包 的快捷键
4797 0
|
存储 Java 编译器
【Java异常】Variable used in lambda expression should be final or effectively final
【Java异常】Variable used in lambda expression should be final or effectively final
666 0
【Java异常】Variable used in lambda expression should be final or effectively final
|
Java 程序员 编译器
Java|如何正确地在遍历 List 时删除元素
从源码分析如何正确地在遍历 List 时删除元素。为什么有的写法会导致异常,而另一些不会。
430 3
|
Java 测试技术 数据库
Spring事务传播机制(最全示例)
在使用Spring框架进行开发时,`service`层的方法通常带有事务。本文详细探讨了Spring事务在多个方法间的传播机制,主要包括7种传播类型:`REQUIRED`、`SUPPORTS`、`MANDATORY`、`REQUIRES_NEW`、`NOT_SUPPORTED`、`NEVER` 和 `NESTED`。通过示例代码和数据库插入测试,逐一展示了每种类型的运作方式。例如,`REQUIRED`表示如果当前存在事务则加入该事务,否则创建新事务;`SUPPORTS`表示如果当前存在事务则加入,否则以非事务方式执行;`MANDATORY`表示必须在现有事务中运行,否则抛出异常;
1540 4
Spring事务传播机制(最全示例)
解决IDEA中 Could not autowire. No beans of 'xxxx' type found 的错误提示
解决IDEA中 Could not autowire. No beans of 'xxxx' type found 的错误提示
12907 3
解决IDEA中 Could not autowire. No beans of 'xxxx' type found 的错误提示
|
Java 编译器 Spring
面试突击78:@Autowired 和 @Resource 有什么区别?
面试突击78:@Autowired 和 @Resource 有什么区别?
16994 6
|
前端开发 小程序 Java
【规范】SpringBoot接口返回结果及异常统一处理,这样封装才优雅
本文详细介绍了如何在SpringBoot项目中统一处理接口返回结果及全局异常。首先,通过封装`ResponseResult`类,实现了接口返回结果的规范化,包括状态码、状态信息、返回信息和数据等字段,提供了多种成功和失败的返回方法。其次,利用`@RestControllerAdvice`和`@ExceptionHandler`注解配置全局异常处理,捕获并友好地处理各种异常信息。
7502 1
【规范】SpringBoot接口返回结果及异常统一处理,这样封装才优雅
|
Java Maven Spring
如何在idea中创建Springboot项目? 手把手带你创建Springboot项目,稳!
文章详细介绍了在IDEA中创建Spring Boot项目的过程,包括选择Spring Initializr、配置项目属性、选择Spring Boot版本、导入依赖、等待依赖下载以及项目结构简介。
18336 1