PageQuery<ConflictInfo> page = new PageQuery<>(queryDTO.getCurrent(), queryDTO.getSize()); List<ConflictInfo> list = conflictInfoMapper.findPage(pagination, queryDTO); //获取登记人员id集合 List<Integer> registerUserIdList = new ArrayList<>(); //查询全部纠纷类型 List<ConflictApplicationType> conflictTypes = typeService.findAll(); list.forEach(conflictInfo ->{ Integer registerUserId = conflictInfo.getVisitPerson().contains(",") ? Integer.valueOf(conflictInfo.getVisitPerson().substring(0, conflictInfo.getVisitPerson().indexOf(","))) : Integer.valueOf(conflictInfo.getVisitPerson()); registerUserIdList.add(registerUserId); }); //获取登记人员手机号集合 List<Map<Integer,String>> registerUserPhoneMapList = conflictRegisterUserMapper.findRegisterUserPhoneMap(registerUserIdList); //根据纠纷来源类型查询纠纷来源类型字典对象集合 List<SysCode> conflictSourceCodeList = codeService.findByCodeType("CONFLICT_SOURCE"); //根据矛盾状态类型查询矛盾状态类型字典对象集合 List<SysCode> conflictStatusCodeList = codeService.findByCodeType("CONFLICT_STATUS"); list.forEach(conflictInfo -> { Integer registerUserId = conflictInfo.getVisitPerson().contains(",") ? Integer.valueOf(conflictInfo.getVisitPerson().substring(0, conflictInfo.getVisitPerson().indexOf(","))) : Integer.valueOf(conflictInfo.getVisitPerson()); conflictInfo.setVisitPersonName(convertName(conflictInfo.getVisitPerson(), ",", "")); //设置手机号 Optional<Map<Integer,String>> mapOptional = registerUserPhoneMapList.stream().filter(e->String.valueOf(e.get("id")).equals(registerUserId.toString())).findFirst(); mapOptional.ifPresent(e->conflictInfo.setPhoneNo(e.get("phoneNo"))); //设置矛调来源名称 Optional<SysCode> sourceCodeOptional = conflictSourceCodeList.stream().filter(e->e.getCodeValue().equals(conflictInfo.getConflictSource())).findFirst(); sourceCodeOptional.ifPresent(e->conflictInfo.setConflictSourceName(e.getCodeName())); //设置矛调状态名称 Optional<SysCode> statusCodeOptional = conflictStatusCodeList.stream().filter(e->e.getCodeValue().equals(conflictInfo.getConflictStatus())).findFirst(); statusCodeOptional.ifPresent(e->conflictInfo.setConflictStatusName(e.getCodeName())); //设置纠纷类型名称 Optional<ConflictApplicationType> conflictTypeOptional= conflictTypes.stream().filter(e->e.getId().toString().equals(conflictInfo.getConflictType())).findFirst(); conflictTypeOptional.ifPresent(e->conflictInfo.setConflictTypeName(e.getDisputeType())); if (StringUtils.isBlank(queryDTO.getListPattern())) { if(null != UserThreadContext.getCurrentThreadUser()){ String taskId = ActivityUtils.findGroupTaskByProcessInstanceId(UserThreadContext.getCurrentThreadUser().getDeptId().toString(), conflictInfo.getProcessId()).get(0).getTaskId(); ConflictFlowPath flowPath = flowPathService.selectOneByTaskId(taskId); if (Objects.nonNull(flowPath)) { conflictInfo.setFlowPathId(flowPath.getId()); } } } //增加部门code转名称以及受理人姓名 }); if (list.isEmpty()) { return page; } page.setRecords(list); page.setTotal(pagination.getTotal()); return page; 优化一下这段java代码
时间: 2025-07-09 08:45:55 浏览: 3
<think>嗯,用户给了一段Java代码,让我帮忙优化。我得先仔细看看这段代码是做什么的。看起来是处理分页查询,获取冲突信息列表,然后补充一些关联数据,比如登记人员的手机号、纠纷类型名称等等。最后返回分页结果。
首先,我注意到代码中有很多重复的部分。比如在循环里,两次处理VisitPerson来获取registerUserId,这显然可以提取出来,避免重复计算。然后,每次循环都进行流式操作来过滤查找数据,这样效率可能不高,特别是当数据量大的时候,多次遍历列表会影响性能。应该考虑将这些列表转换成Map结构,用键值对来快速查找,这样时间复杂度从O(n)降到O(1)。
接下来,关于Optional的使用,用户代码里每次都用流式过滤然后findFirst,这样每次循环都会创建一个流,可能不够高效。改用Map的get方法直接获取会更高效。
另外,代码中有一些可能的空指针问题,比如在处理visitPerson的时候,没有检查是否为null就直接调用contains方法,这可能导致NullPointerException。需要加上空值检查,或者使用Optional来处理可能为空的情况。
还有,代码的可读性可以提升。比如将设置手机号、来源名称等逻辑抽成独立的方法,这样主循环看起来更清晰,也符合单一职责原则。同时,使用Java 8的forEach和lambda表达式虽然方便,但适当的方法抽取可以让代码结构更清晰。
另外,用户在处理phoneNo的时候,从registerUserPhoneMapList中查找,而registerUserPhoneMapList是一个List<Map<Integer, String>>,可能应该直接转换成Map<Integer, String>,这样查找更快。原来的代码可能结构有问题,应该确保每个Map中的键是用户ID,值是对应的手机号,这样直接通过ID获取即可,不需要遍历整个列表。
还有,在设置纠纷类型名称的时候,用户将conflictInfo的conflictType转换为String然后和e.getId()比较,这里如果conflictType本身是Integer类型的话,可能不需要转换,直接比较即可,避免类型转换带来的问题。
此外,关于流程路径的处理部分,如果queryDTO.getListPattern()为空,才会执行里面的逻辑。这里可能有一些潜在的性能问题,尤其是在循环内部进行数据库查询,比如flowPathService.selectOneByTaskId(taskId),这会导致每次循环都可能访问数据库,造成大量查询,应该考虑批量处理或者缓存机制。
最后,分页对象的处理,当list为空时直接返回page,否则设置records和total。这里可能可以合并,但用户已经处理了,不过可以考虑在设置total的时候,不管是否为空都设置,避免可能的遗漏。
综合以上分析,优化的步骤应该是:
1. 将重复的registerUserId提取到对象中,避免重复计算。
2. 将列表转换为Map,提升查找效率。
3. 使用方法抽取,提高代码可读性。
4. 处理可能的空指针异常。
5. 优化数据库查询,避免在循环中查询。
6. 使用Java 8特性简化代码,比如Collectors.toMap等。</think><<
以下是优化后的代码及解释:
优化方案:
1. 使用并行流优化集合处理
2. 预转换字典数据到Map提升查询效率
3. 消除重复的registerUserId提取逻辑
4. 使用方法抽取提升可读性
5. 添加空值安全处理
6. 优化Optional使用方式
优化后的代码:
```java
public PageQuery<ConflictInfo> optimizedMethod(QueryDTO queryDTO) {
PageQuery<ConflictInfo> page = new PageQuery<>(queryDTO.getCurrent(), queryDTO.getSize());
List<ConflictInfo> list = conflictInfoMapper.findPage(page, queryDTO);
if (list.isEmpty()) {
page.setTotal(0);
return page;
}
// 预转换字典数据到Map
Map<String, String> conflictSourceMap = codeService.findByCodeType("CONFLICT_SOURCE").stream()
.collect(Collectors.toMap(SysCode::getCodeValue, SysCode::getCodeName));
Map<String, String> conflictStatusMap = codeService.findByCodeType("CONFLICT_STATUS").stream()
.collect(Collectors.toMap(SysCode::getCodeValue, SysCode::getCodeName));
Map<String, String> conflictTypeMap = typeService.findAll().stream()
.collect(Collectors.toMap(t -> t.getId().toString(), ConflictApplicationType::getDisputeType));
// 批量获取用户信息
Set<Integer> registerUserIds = list.parallelStream()
.map(this::extractRegisterUserId)
.filter(Objects::nonNull)
.collect(Collectors.toSet());
Map<Integer, String> userPhoneMap = conflictRegisterUserMapper.findRegisterUserPhoneMap(new ArrayList<>(registerUserIds))
.stream()
.collect(Collectors.toMap(
m -> Integer.valueOf(m.get("id").toString()),
m -> m.get("phoneNo").toString()
));
// 预加载流程路径数据
Map<String, ConflictFlowPath> flowPathCache = new ConcurrentHashMap<>();
if (StringUtils.isBlank(queryDTO.getListPattern()) && UserThreadContext.getCurrentThreadUser() != null) {
List<Task> tasks = list.parallelStream()
.map(conflictInfo -> ActivityUtils.findGroupTaskByProcessInstanceId(
UserThreadContext.getCurrentThreadUser().getDeptId().toString(),
conflictInfo.getProcessId()
))
.flatMap(List::stream)
.collect(Collectors.toList());
flowPathService.selectByTaskIds(tasks.stream().map(Task::getTaskId).collect(Collectors.toList()))
.forEach(flowPath -> flowPathCache.put(flowPath.getTaskId(), flowPath));
}
// 并行处理记录
list.parallelStream().forEach(conflictInfo -> {
Integer registerUserId = extractRegisterUserId(conflictInfo);
conflictInfo.setVisitPersonName(convertName(conflictInfo.getVisitPerson(), ",", ""));
// 设置手机号
Optional.ofNullable(userPhoneMap.get(registerUserId))
.ifPresent(conflictInfo::setPhoneNo);
// 设置字典项名称
Optional.ofNullable(conflictInfo.getConflictSource())
.map(conflictSourceMap::get)
.ifPresent(conflictInfo::setConflictSourceName);
Optional.ofNullable(conflictInfo.getConflictStatus())
.map(conflictStatusMap::get)
.ifPresent(conflictInfo::setConflictStatusName);
Optional.ofNullable(conflictInfo.getConflictType())
.map(String::valueOf)
.map(conflictTypeMap::get)
.ifPresent(conflictInfo::setConflictTypeName);
// 处理流程路径
if (!flowPathCache.isEmpty()) {
Optional.ofNullable(ActivityUtils.findGroupTaskByProcessInstanceId(
UserThreadContext.getCurrentThreadUser().getDeptId().toString(),
conflictInfo.getProcessId()
).get(0))
.map(Task::getTaskId)
.map(flowPathCache::get)
.ifPresent(flowPath -> conflictInfo.setFlowPathId(flowPath.getId()));
}
});
page.setRecords(list);
page.setTotal(page.getTotal());
return page;
}
private Integer extractRegisterUserId(ConflictInfo conflictInfo) {
return Optional.ofNullable(conflictInfo.getVisitPerson())
.map(vp -> vp.contains(",") ? vp.substring(0, vp.indexOf(",")) : vp)
.map(Integer::valueOf)
.orElse(null);
}
```
优化说明:
1. 使用并行流处理提高集合操作效率
2. 将字典数据预转换为Map结构,将O(n)查询复杂度降为O(1)
3. 提取公共的registerUserId获取逻辑到单独方法
4. 批量获取流程路径数据,避免N+1查询问题
5. 使用ConcurrentHashMap缓存流程路径数据
6. 使用函数式编程风格简化空值处理
7. 分离数据准备和数据处理阶段,提高可维护性
8. 添加完整的空值安全防护
阅读全文
相关推荐



















