Добрый. Очень нужна помощь, в программировании совсем новичок и возник затор с задачкой. Задача: вывести год, в который жило максимальное количество людей. Дата рождения и дата смерти произвольные значения.
Вот что имею пока:
public class Main {
static List<Human> list = new ArrayList();
int year;
Human human;
public static void main(String[] args) {
int birthDay;
int LifeLeight;
Human human = null;
for (int i = 0; i < 200; i++) {
human = new Human();
int min = 1880;
int max = 1990;
int LifeLeightMin = 35;
int LifeLeightMax = 150;
boolean isLife = true;
birthDay = (int) (Math.random() * (max - min) + min);
human.setBirthDay(birthDay);
LifeLeight = (int) (Math.random() * (LifeLeightMax - LifeLeightMin)
+ LifeLeightMin);
human.setDeathDay(human.getBirthDay() + LifeLeight);
System.out.println(human);
countMaxLives();
}
}
И дальше не могу сообразить, как правильно сделать список всех лет жизни у каждого человека и засунуть все это в Map, что бы потом посчитать максимальное значение по Value.
Help...please
Дурацкий вариант "в лоб"
//В качестве ключа год, в качестве значения - количество живущих в нем
Map<Integer, Integer> years = new HashMap();
for(int i = min; i <= max; i++){
years.put(i, 0);
}
for (int i = 0; i < 200; i++) {
birthDay = (int) (Math.random() * (max - min) + min);
human.setBirthDay(birthDay);
LifeLenght = (int) (Math.random() * (LifeLeightMax - LifeLeightMin)
+ LifeLenghtMin);
human.setDeathDay(human.getBirthDay() + LifeLeight);
//Добавляем по единичке к каждому году, в котором живет данный индивидум
for(int j = birthDay; j <= LifeLenght + birthDay; j++){
years.put(j, years.get(j) + 1);
}
}
//Ищем ключ(год) с максимальным значением. Тут я схалтурю и скопипащу решение для Java 8
Integer year = Collections.max(map.entrySet(), Map.Entry.comparingByValue()).getKey();
countMaxLives(); нужно вызвать после заполнения списка людей - замените этот вызов на list.add(human);
После наполнения списка, можно развернуть его в список лет, в которые каждый человек жил, и затем определить наиболее часто встречаемый год.
Если достаточно получить хотя бы один из годов, когда количество живущих было максимальным, то можно сделать так:
private static int countMaxLives() {
return Collections.max(list.parallelStream()
.map(h -> IntStream.range(h.birthDay, h.deathDay))
.flatMapToInt(Function.identity()).boxed() //здесь имеем стрим с годами жизни
.collect(Collectors.groupingBy(Function.identity(), Collectors.counting())).entrySet(), Map.Entry.comparingByValue())
.getKey();
}
Если необходимо получить все максимальные года, то необходимо переписать и возвращать список лет с максимальным количеством людей:
private static List<Integer> countMaxLives(){
return Collections.max(list.parallelStream()
.map(h -> IntStream.range(h.birthDay, h.deathDay))
.flatMapToInt(Function.identity()).boxed() //здесь имеем стрим с годами жизни
.collect(Collectors.groupingBy(Function.identity(), Collectors.counting())) //здесь map <год -> количество людей>
.entrySet().parallelStream()
.collect(Collectors.groupingBy(Map.Entry::getValue, Collectors.mapping(Map.Entry::getKey, Collectors.toList()))) // здесь map <количество людей -> года>
.entrySet(),
Map.Entry.comparingByKey())
.getValue();
}
Продвижение своими сайтами как стратегия роста и независимости