[英]Handling null in java streams with optional
如果我們有如下所示的senario,那么處理null的最佳方法是什么
//mocking for demonstraton
studentsByCourseRoster.setUsers(null);
studentsByCourseRoster.getUsers().stream().forEach(user -> {
final UserDTOv2 userDTO = new UserDTOv2();
userDTO.populateUserDataFromUserDTO(user, groupedUsers);
users.add(userDTO);
});
如果要保留單個語句結構,可以使用Optional.ofNullable
並將null
替換為空列表:
Optional.ofNullable(studentsByCourseRoster.getUsers())
.orElse(Collections.emptyList())
.forEach(user -> {
final UserDTOv2 userDTO = new UserDTOv2();
userDTO.populateUserDataFromUserDTO(user, groupedUsers);
users.add(userDTO);
});
稍微修改一下Mureinik的答案我會改用:
List<UserDTOv2> users = Optional.ofNullable(studentsByCourseRoster.getUsers())
.orElse(Collections.emptyList())
.stream()
.map(user -> {
UserDTOv2 userDTO = new UserDTOv2();
userDTO.populateUserDataFromUserDTO(user, groupedUsers);
return userDTO;
}).collect(Collectors.toList());
Stream.ofNullable
List<UserDTOv2> users = Stream.ofNullable(studentsByCourseRoster.getUsers())
.map(user -> {
UserDTOv2 userDTO = new UserDTOv2();
userDTO.populateUserDataFromUserDTO(user, groupedUsers);
return userDTO;
}).collect(Collectors.toList());
如果我們有如下所示的senario,那么處理null的最佳方法是什么
在您當前的設計下,最簡單的解決方案是使用if
語句。
這並不是說它是“處理”這個問題的最好方法,而是處理這個問題的最好方法是永遠不要讓列表首先處於空狀態,如評論中所提到的那樣。
有一個空列表作為默認值, if
你的代碼庫周圍檢查取決於使用getUsers()
次數,這將為你節省相當多的錢,最重要的是你不必擔心NullPointerExeception
,因為它們永遠不應該發生。
另一方面,無論何時你似乎在某個集合上看到你的自我調用stream()
然后立即調用forEach
你應該意識到它是錯的; 1)從某種意義上說,你可以輕松地直接在列表上調用forEach
,即studentsByCourseRoster.getUsers().forEach(...)
2)流和副作用只是不能很好地協同工作。
您還可以通過filter(Objects :: nonNull)過濾空對象:
studentsByCourseRoster.getUsers().stream().filter(Objects::nonNull).forEach(user -> {
final UserDTOv2 userDTO = new UserDTOv2();
userDTO.populateUserDataFromUserDTO(user, groupedUsers);
users.add(userDTO);
});
除了糾正@ Murenik的答案之外,還有一種方法可以選擇這個。 無需創建空列表,我們只能通過以下方式傳遞執行非null的情況:
Optional.ofNullable(nullableUsers)
.ifPresent(users -> users.forEach(user -> {
// work with user
}));
Nullable可選也適用於嵌套的空引用,例如我們有一些結構:
class User {
@Getter
Address address;
}
class Address {
@Getter
String street;
}
然后而不是寫作
if (user.getAddress() != null && user.getAddress().getStreet() != null) {
// work with street
}
我們可以使用Optional:
Optional.ofNullable(user)
.map(User::getAddress)
.map(Address::getStreet)
.ifPresent(street -> {
// work with street
});
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.