Java Generics WildCard - Как я могу использовать универсальный с Lambda здесь? - PullRequest
0 голосов
/ 18 апреля 2019

Я пытаюсь создать универсальный метод.Мой dtos:

public class Master {
    private String string;
    private Date date;

    public String getString() {
        return this.string;
    }

    public Date getDate() {
        return this.date;
    }

    public void setString(String string) {
        this.string = string;
    }

    public void setDate(Date date) {
        this.date = date;
    }
}

Класс My Child, расширяющий класс Master:

public class Child extends Master {

    private Date newDate;

    public Date getNewDate() {
        return this.newDate;
    }

    public void setNewDate(Date newDate) {
        this.newDate = newDate;
    }
}

Теперь я хочу создать общий метод для получения -

public static <T extends Master> Map<String, Map<Date, List<T extends Master>>> getRecalculateMasterMappedByInstrumentIdAndDate(List<T extends Master> masters) {
        return masters.stream().collect(Collectors.groupingBy(Child::getString, Collectors.groupingBy(x -> org.apache.commons.lang3.time.DateUtils.truncate(x.getDate(), Calendar.DAY_OF_MONTH))));
    }

Выше приведено сообщение об ошибке во время компиляции.Как я могу написать общий метод для того же самого?

Ответы [ 3 ]

1 голос
/ 18 апреля 2019

Удалить границу после объявления:

  • Тип возврата: Map<String, Map<Date, List<T>>>
  • Тип параметра: List<T> masters.

Вы можете использовать границы только с подстановочными знаками (?) или в объявлении переменных типа.

0 голосов
/ 19 апреля 2019

Я смог решить с помощью людей здесь. Спасибо вам, ребята. Мое решение:

public static <T extends Master> Map<String, Map<Date, List<T>>> getMastersMappedByInstrumentIdAndDateForRecalculation(List<T> masters) {
        return masters.stream().collect(Collectors.groupingBy(Master::getString, Collectors.groupingBy(x -> org.apache.commons.lang3.time.DateUtils.truncate(x.getDate(), Calendar.DAY_OF_MONTH))));
    }
0 голосов
/ 18 апреля 2019

Вы должны понимать разницу между объявлением переменной типа и использованием переменной типа. Когда ты пишешь

public static <T extends Master> Map<String, Map<Date, List<T>>>
    getRecalculateMasterMappedByInstrumentIdAndDate(List<T> masters) {
    …
}

<T extends Master> объявляет переменную типа T, включая ограничение, согласно которому T должен быть подтипом Master. Другие вхождения T в возвращаемом типе Map<String, Map<Date, List<T>>> и типе параметра List<T> являются с использованием переменной типа T и повторяться не нужно (и на самом деле не разрешено повторить) границы T.

Обратите внимание, что вы также должны использовать Master::getString в реализации метода, поскольку вы не можете предполагать, что T - это Child. Это может быть Child, но вызывающий может также использовать Master или любой его подкласс для T. К счастью, getString было определено в Master в любом случае, поэтому вам не нужно предполагать Child здесь.

...