每次我必须迭代一个集合时,我最终都会检查null,就在for-each循环的迭代开始之前。像这样:
if( list1 != null ){
for(Object obj : list1){
}
}
是否有更短的方式,以便我们可以避免编写“if”块? 注意:我使用的是Java 5,并且会在一段时间内坚持使用它。
答案 0 :(得分:77)
如果可能,您应该设计代码,使首先不是null
的集合。
null
收藏品是不好的做法(因此);你应该使用空集合。 (例如,Collections.emptyList()
)
或者,您可以创建一个实现Iterable
的包装类并获取集合,并处理null
集合。
然后你可以写foreach(T obj : new Nullable<T>(list1))
答案 1 :(得分:39)
public <T extends Iterable> T nullGuard(T item) {
if (item == null) {
return Collections.EmptyList;
} else {
return item;
}
}
允许你写
for (Object obj : nullGuard(list)) {
...
}
当然,这实际上只是将复杂性转移到其他地方。
答案 2 :(得分:32)
我想正确的答案是:没有办法让它缩短。有一些技巧,如评论中的那些,但我不认为自己使用它们。我认为写一个“if”块比使用这些技术更好。并且是..在任何人再次提到之前:)“理想情况下”代码应该被设计为使得列表永远不应该是 null
答案 3 :(得分:16)
已经是2017年,您现在可以使用Apache Commons Collections4
用法:
for(Object obj : CollectionUtils.emptyIfNull(list1)){
// Do your stuff
}
答案 4 :(得分:15)
在Java 8中,使用java.util.Optional
和ifPresent
方法可以获得另一种解决方案。
Optional.ofNullable(list1).ifPresent(l -> l.forEach(item -> {/* do stuff */}));
所以,不是针对确切问题的解决方案,而是一个oneliner,可能更优雅。
答案 5 :(得分:11)
Null check in an enhanced for loop
public static <T> Iterable<T> emptyIfNull(Iterable<T> iterable) {
return iterable == null ? Collections.<T>emptyList() : iterable;
}
然后使用:
for (Object object : emptyIfNull(someList)) { ... }
答案 6 :(得分:9)
Apache Commons
for (String code: ListUtils.emptyIfNull(codes)) {
}
Google Guava
for (String code: Optional.of(codes).get()) {
}
答案 7 :(得分:7)
您希望它缩短多少?它只是一个额外的2行,它清晰简洁的逻辑。
我认为您需要决定的更重要的事情是null
是否为有效值。如果它们无效,您应该编写代码以防止它发生。那你就不需要这种检查了。如果您在执行foreach
循环时遇到异常,则表示代码中的其他位置存在错误。
答案 8 :(得分:5)
1)如果list1是一个类的成员,则在构造函数中创建列表,使其存在,并且非空,但为空。
2)for(Object obj:list1!= null?list1:new ArrayList())
答案 9 :(得分:1)
另一种Java 8+方法是创建一个使用null
值时不会崩溃的forEach方法:
public static <T> void forEach(Iterable<T> set, Consumer<T> action) {
if (set != null) {
set.forEach(action);
}
}
自己定义的foreach
的用法与本机Java 8接近:
ArrayList<T> list = null;
//java 8+ (will throw a NullPointerException)
list.forEach(item -> doSomething(...) );
//own implementation
forEach(list, item -> doSomething(...) );