【发布时间】:2022-10-18 02:00:10
【问题描述】:
如果实体有10个字段,5个字段有数据,5个字段在数据库记录中没有数据,那么该实体记录的百分比为50%。
我们如何使用 Spring data jpa 或 Java 中的任何现有库进行计算
【问题讨论】:
标签: java sql spring-boot spring-data-jpa
如果实体有10个字段,5个字段有数据,5个字段在数据库记录中没有数据,那么该实体记录的百分比为50%。
我们如何使用 Spring data jpa 或 Java 中的任何现有库进行计算
【问题讨论】:
标签: java sql spring-boot spring-data-jpa
您可以尝试在实体类的瞬态字段中使用反射。
@Transient
public float getPercentDone() {
var propDesc = BeanUtilsBean2.getInstance().getPropertyUtils().getPropertyDescriptors(this);
var allProps = Arrays.stream(propDesc).filter(prop -> !"percentDone".equals(prop.getName()))
.collect(Collectors.toList());
var countNotNull = allProps.stream().filter(prop -> {
try {
return BeanUtilsBean2.getInstance().getProperty(this, prop.getName()) != null;
} catch (Exception e) {
return false;
}
}).count();
return (countNotNull * 100.0f) / allProps.size();
}
我为此使用了来自 Apache Commons 的 BeanUtils,但如果你不能使用它,你可以使用开箱即用的反射来做同样的事情(它只是更长)。
要跳过 ids 和 join 字段等字段,您可以创建一个列表。并将过滤器替换为检查跳过属性列表的过滤器。如果你把它放在@MappedSuperclass 中,实体子项只需要覆盖列表。
笔记:percentDone 和 skippedProperties 本身都必须是跳过的字段。
List<String> skippedProperties = List.of("percentDone", "skippedProperties", "id", "user");
...
@Transient
public float getPercentDone() {
var propDesc = BeanUtilsBean2.getInstance().getPropertyUtils().getPropertyDescriptors(this);
var allProps = Arrays.stream(propDesc)
.filter (prop -> !skippedProperties.contains(prop.getName())
.collect(Collectors.toList());
var countNotNull = allProps.stream().filter(prop -> {
try {
return BeanUtilsBean2.getInstance().getProperty(this, prop.getName()) != null;
} catch (Exception e) {
return false;
}
}).count();
return (countNotNull * 100.0f) / (allProps.size() - skippedProperties.size());
}
【讨论】:
allProps.stream().filter(p -> !p.getName().equals("id").prop(prop -> ...