Преобразование / сравнение различных числовых типов внутри потоков - PullRequest
0 голосов
/ 09 января 2019

У меня проблема с Stream API ... снова. Функциональность, которую я пытаюсь реализовать, не самая сложная, но у меня возникают трудности с фильтрацией, поскольку существуют несовместимые типы, и я не знаю, как сделать сравнение правильно. Идея состоит в том, чтобы получить информацию об отделах, с которыми связаны данные разделы.

department.getSectionId() возвращает Long, в то время как Section::getId является Integer (который я не могу изменить)

private List<DepartmentInfo> retrieveLinkedDepartments(final Collection<Section> sections) {
        return this.departmentDao
                .findAll()
                .stream()
                .filter(department -> department.getSectionId() != null)
                .filter(department -> department.getSectionId().equals(sections.stream().map(Section::getId)))                                           
                .map(this.departmentInfoMapper::map)
                .collect(Collectors.toList());
}

Конечно, результат основного предиката всегда ложен. Я знаю, что код ужасен, и я не правильно определяю условия, но надеюсь, вы поняли идею. Возможно, есть возможность как-то объединить эти коллекции или сравнить с умом.

Заранее спасибо!

Ответы [ 3 ]

0 голосов
/ 09 января 2019

В этой строке department.getSectionId().equals(sections.stream().map(Section::getId) вы сравниваете Long с Stream<Integer>, который всегда будет давать ложь.

вместо этого сопоставьте идентификаторы Section с Set<Long> и затем используйте contains в операции filter:

Set<Long> ids = sections.stream() // Stream<Section>
                        .map(Section::getId) //Stream<Integer>
                        .filter(Objects::nonNull) // remove potential null elements
                        .map(Integer::longValue) // Stream<Long>
                        .collect(Collectors.toSet()); //Set<Long>

return this.departmentDao
           .findAll()
           .stream()
           .filter(department -> department.getSectionId() != null)
           .filter(department -> ids.contains(department.getSectionId()))
           .map(this.departmentInfoMapper::map)
           .collect(Collectors.toList());
0 голосов
/ 09 января 2019

На данный момент вы сравниваете Long и Steam<Integer>, которые всегда возвращают false.

Вы можете немного перевернуть логику и использовать mapToLong для преобразования целых чисел в Long:

private List<DepartmentInfo> retrieveLinkedDepartments(final Collection<Section> sections) {
    return this.departmentDao
               .findAll()
               .stream()
               .filter(department -> department.getSectionId() != null)
               .filter(department -> sections.stream()
                                 .mapToLong(Section::getId)                                     
                                 .anyMatch(department.getSectionId()::equals))                                           
               .map(this.departmentInfoMapper::map)
               .collect(Collectors.toList());
}

Это преобразует Section::getId в Stream<Long>, а затем фильтрует через Stream, чтобы увидеть, равен ли какой-либо из department.getSectionId Id.

0 голосов
/ 09 января 2019

Возможно, вы ищете что-то вроде:

private List<DepartmentInfo> retrieveLinkedDepartments(final Collection<Section> sections) {
    Set<Long> sectionIds = sections.stream()
            .map(Section::getId)
            .map(Long::valueOf)
            .collect(Collectors.toSet()); // collect all the possible sectionIds
    return this.departmentDao
            .findAll()
            .stream()
            .filter(department -> department.getSectionId() != null)'
            // validate if the sectionIds include this department's section id or not
            .filter(department -> sectionIds.contains(department.getSectionId()))
            .map(this.departmentInfoMapper::map)
            .collect(Collectors.toList());
}

Offcourse, результат основного предиката всегда ложен

Это потому, что вы сравнивали Long, сгенерированный с использованием department.getSectionId(), с Stream<Integer>, сгенерированным с использованием sections.stream().map(Section::getId), сравнение этих двух типов всегда будет неравным и, следовательно, результирующим false.

Редактировать : Как отметил Хольгер в комментариях, код для подготовки Set может быть улучшен как:

Set<Long> sectionIds = sections.stream()
            .mapToLong(Section::getId)
            .boxed()
            .collect(Collectors.toSet());
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...