我想知道有没有办法用Stream
的API来重写这样与流API排除结果的记录的更好的办法
public static void main(String[] args) {
final List<String> dataCollection = Collections.emptyList();
final Set<String> someValues = new HashSet<>();
final Iterator<String> iterator = dataCollection.iterator();
while (iterator.hasNext()) {
final String dataItem = iterator.next();
// imagine some calculations
String calculatedData = dataItem;
if (!someValues.contains(calculatedData)) {
logger.error("Skipped data {} because of ...#1", dataItem);
iterator.remove();
continue;
}
for (char element : dataItem.toCharArray()) {
// imagine some other calculations
if (element > 100) {
logger.error("Skipped data {} because of ...#2", dataItem);
iterator.remove();
break;
}
}
}
}
代码,以便排除过滤元素被记录后。 peek()在这种情况下不起作用,因为它要么在过滤器之前执行每个元素的操作,要么在剩余项之后执行操作。
到目前为止,我设法使用lambda中的日志记录来设计它,但它看起来冗长,笨拙,并且像副作用一样。我们可以用一些方法来包装它,但它只会隐藏该代码
public static void main(String[] args) {
final List<String> dataCollection = Collections.emptyList();
final Set<String> someValues = new HashSet<>();
final Iterator<String> iterator = dataCollection.iterator();
dataCollection.stream()
.filter(byCondition1(someValues))
.filter(byCondition2())
.collect(Collectors.toList());
}
private static Predicate<String> byCondition1(Set<String> someValues) {
return dataItem -> {
final boolean remain = someValues.contains(dataItem);
if (!remain) {
logger.error("Skipped data {} because of ...#1", dataItem);
}
return remain;
};
}
private static Predicate<String> byCondition2() {
return dataItem -> {
for (char element : dataItem.toCharArray()) {
// imagine some other calculations
if (element > 100) {
logger.error("Skipped data {} because of element {}...#2", dataItem, element);
return false;
}
}
return true;
};
}
我希望有更好的方法。
*可能* Predicate的扩展可能是?像'LoggingPredicate extends Predicate ...'和静态方法'Static LoggingPredicate(Logger log)'一样,它会创建它并覆盖'test'方法。只是一个想法... – Eugene
是的,但是......这是包装此代码的另一种方式。当然,它具有更好的可重用性,比我的 – WeGa
我不认为有任何其他的方式来做到这一点,因为流API没有任何东西,除了'peek' – Eugene