我正在使用java-8
修改对象users.stream().filter(u -> u.count > 0).forEach(u -> u.setProperty("value"))
但是,我想知道是否有任何对象被修改...即,我想要一个布尔返回值,而这是无效的。
有什么办法吗?
答案 0 :(得分:6)
如果我找到你,你想知道在执行操作时是否有任何匹配。你可以简单地使用两个语句。
boolean anyMatch = users.stream().anyMatch(u -> u.count > 0);
if(anyMatch) users.stream().filter(u -> u.count > 0).forEach(u -> u.setProperty("value"));
由于anyMatch
在第一个匹配元素处停止,因此只有在第一个匹配之前存在非匹配元素的长前缀时才会有冗余工作。
如果这是一个问题,你可以使用
Spliterator<User> sp = users.stream().filter(u -> u.count > 0).spliterator();
boolean anyMatch = sp.tryAdvance(u -> u.setProperty("value"));
sp.forEachRemaining(u -> u.setProperty("value"));
代替。
答案 1 :(得分:3)
由于这是一项消耗操作,因此它只能用于实际上不返回任何东西的方法;也就是说,使用forEach
可确保终端操作无法获得返回值。
如果要验证属性是否按照您希望的方式设置,则必须再次检查元素。
users.stream().filter(u -> u.count > 0)
.allMatch(u -> u.getProperty().equals("value"));
虽然这比偏执狂更能说明偏执狂;除非setProperty
有其他副作用,但 ,否则设置者应该始终设置值。我在单元测试中将上述内容写入验证目的,但不在生产代码中。
答案 2 :(得分:2)
致电peek()
:
AtomicBoolean modified = new AtomicBoolean();
users.stream()
.filter(u -> u.count > 0)
.peek(u -> modified.set(true))
.forEach(u -> u.setProperty("value"))
如果有任何元素通过过滤器,modified.get()
将返回true
。
需要使用AtomicBoolean
(或类似的东西),因为lambdas中使用的引用必须有效最终。