当我们想要为集合中每个元素都获得某一属性,或者为所有元素添加某一属性的时候往往会通过遍历的方法。如果遍历中的每个元素的某一属性都是获得目标属性的条件时,那么会每次遍历都会调用数据库,这种方法虽然容易书写但是并不理想。如果有一种只需要调用一次数据库就可以得到这两个属性的映射关系,在通过map.get()方法获取目标属性那就太舒服惹~
以下方法便是上面需求的代码操作。部分代码为展现。
当前操作场景为:获取分页列表中的数据集合,集合中含有唯一的code,但没有相应的name。获取name需要查询另一个表。
返回含有code、name的集合。
一、获取分页的数据集合
Page<ApiCallTotalEntity> pageEntity = apiCallTotalMapper.queryByApiCode(apiCode, page);
List<ApiCallTotalEntity> apiCallTotalEntities = pageEntity.getRecords();
if (CollUtil.isEmpty(apiCallTotalEntities)){
return new DataList<>();
}
二、通过stream流得到数据集合的 code Set集合,再调用dao层的方法得到code与name的映射关系。
Set<String> appCodeSet = apiCallTotalEntities.stream().map(ApiCallTotalEntity::getAppCode)
.collect(Collectors.toSet());
Map<String, String> appCodeAndNameMap = appBaseService.queryAppCodeAndNameByAppCodes(appCodeSet);
三、核心代码
@Override
public Map<String, String> queryAppCodeAndNameByAppCodes(Set<String> appCodeSet) {
LambdaQueryWrapper<AppEntity> qw = new LambdaQueryWrapper<>();
qw.in(AppEntity::getAppCode,appCodeSet);
List<AppEntity> list = this.list(qw);
if(CollUtil.isEmpty(list)){
return Maps.newHashMap();
}
return list.stream().collect(Collectors.toMap(AppEntity::getAppCode, AppEntity::getAppName));
}
四、通过map 即可实现 一次查询数据库,便可完成获取唯一属性
List<ApiCallTotalDTO> collect = apiCallTotalEntities.stream().map(s -> {
ApiCallTotalDTO apiCallTotalDTO = new ApiCallTotalDTO();
apiCallTotalDTO.setAppCode(s.getAppCode());
apiCallTotalDTO.setAppName(appCodeAndNameMap.get(s.getAppCode()));
// 一些其他操作
//。。。。。。。
}
return apiCallTotalDTO;
}).collect(Collectors.toList());
返回的部分JSON为:
"data": [
{
"appCode": "yzt_slt",
"appName": "水利厅"
},
{
"appCode": "yzt_zwfwsj",
"appName": "政务服务数据"
}
]
总结
场景:
表1里面有 code和想得到的数据
表2里面有 code 和 name
现在想把 想得到的数据 和 name封装起来
一般方法:(封装数据时多次查询数据库)
1、用code查询表1,得到实体类列表,得到想得到的数据
2、遍历列表,通过code查询表2,得到相应name
3、封装在一起
优化方法:(封装数据时一次查询数据库)
1、用code查询表1,得到实体类列表,得到想得到的数据
2、得到实体类列表中的所有code(封装为codeSet)
3、用codeSet查询表2,得到所有code和相对应的name,封装成map
4、遍历列表,通过map得到code对应的name
5、封装在一起
如果本篇文章对你有所帮助,还请一键三连【开心】