Błędy w metodach, które powinny zwracać

0

Cześć

Prosiłbym o wskazówki do rozwiązania zadania z metodami.
Mam stworzyc klase EmployeeService w ktorej kazda z metod pobiera liste employow jako argument

  1. metoda, która zwraca pracownika co najwiecej zarabia w podanym jako 2gi argument miescie - lub rzuca wyjatek jesli nie ma zadnego pracownika w danym miescie
  2. metoda, która zwraca miasto (String) w ktorym jest najwiecej pracownikow.

ad 1 W tej metodzie chciałem rzucić customowy wyjątek Optionalem orElseThrow, ale dostaję informację że nie da radę zrobić tego Mapując
ad 2 W tej metodzie również pojawia się błąd.
Proszę rzucić okiem gdzie popełniam błędy

Stworzyłem klasę Employee, klasę Runner z listą pracowników, klasę customowego wyjątku i klasę EmolyeeService gdzie mieszczą się metody

import java.util.ArrayList;
import java.util.Comparator;
import java.util.List;
import java.util.Optional;
import java.util.function.BinaryOperator;
import java.util.stream.Collectors;

public class EmployeeService {
    

    public Employee biggestSalaryEmployeeInTheCity(List<Employee> employeeList) throws NoEmployeeInCityException {
        return Optional.ofNullable(employeeList)
                .orElseGet(ArrayList::new)
                .stream()
                .collect(Collectors.toMap(e -> e.getCity(), e -> e, BinaryOperator.maxBy(Comparator.comparingDouble(e -> e.getSalary()))))
                .orElseThrow(() -> new NoEmployeeInCityException("No employee found"));
    }

    public String cityMostEmployees(List<Employee> employeeList) {
        return employeeList.stream()
                .max(Comparator.comparingDouble(Employee::getCity))
                .orElse(null);
    }


public class Runner {

    public static void main(String[] args) throws NoEmployeeException {


        List<Employee> employees = new ArrayList<>();
        employees.add(new Employee("Adam", "Nowak", "12345678999", 10_000.0D, "Programmer", "Warsaw"));
        employees.add(new Employee("Robert", "Puczyk", "09876543212", 12_000.0D, "Programmer", "Warsaw"));
        employees.add(new Employee("Anna", "Kwiatkowska", "65748345327", 13_000.0D, "Manager", "Poznan"));
        employees.add(new Employee("Franciszek", "Lasek", "23456569995", 9_000.0D, "Tester", "Poznan"));
        employees.add(new Employee("Roman", "Kowalski", "23226569995", 12_000.0D, "Programmer", "Poznan"));


1

Tutaj trzeba dobrze znać API Streamów i myśleć trochę SQL-em. Pomocne jest też przypisywanie sobie poszczególnych kroków przetwarzania na zmienną, żeby kontrolować jakiego typu masz aktualnie Stream.

 public Employee biggestSalaryEmployeeInTheCity(List<Employee> employeeList) throws NoEmployeeInCityException {
        return Optional.ofNullable(employeeList)
                .orElseGet(ArrayList::new)
                .stream()
                .collect(Collectors.toMap(e -> e.getCity(), e -> e, BinaryOperator.maxBy(Comparator.comparingDouble(e -> e.getSalary()))))
                .orElseThrow(() -> new NoEmployeeInCityException("No employee found"));
    }
  1. Nie widzę tutaj drugiego parametru, który miał być miastem
  2. Kiedy odpali Ci się ten orElseThrow?
  3. Stream ma taką fajną metodę max()
public String cityMostEmployees(List<Employee> employeeList) {
        return employeeList.stream()
                .max(Comparator.comparingDouble(Employee::getCity))
                .orElse(null);
    }
  1. Czy getCity() zwraca double? Użyłeś comparingDouble
  2. Podpowiedź: musisz pogrupować po mieście, zmapować mapę na listę par (city, count) i wziąć maksymalny element po drugiej współrzędnej (podobnie jak w biggestSalaryEmployeeInTheCity)
0

Co do metody pierwszej to najpierw filtruje wg miasta, a potem porownuje wynagrodzenie

public Employee biggestSalaryEmployeeInCity(List<Employee> employeeList, String city) throws NoEmployeeException {
        return Optional.ofNullable(employeeList)
                .orElseGet(ArrayList::new)
                .stream().filter(t -> t.getCity().equals(city))
                .max(Comparator.comparingDouble(Employee::getSalary))
                .orElseThrow(() -> new NoEmployeeException("No employee found"));

    }

Metoda druga pierwsze grupowanie według miasta i liczby, a na tej podstawie uzyskiwanie klucza wartości maksymalnych

public String getMostEmployeesCity(List<Employee> employeeList) {
        return employeeList.stream()
                .collect(Collectors.groupingBy(Employee::getCity,Collectors.counting()))
                .entrySet().stream().max(Map.Entry.comparingByValue()).get().getKey();
    }

Jeśli dobrze zrozumiałem, proszę rzucić okiem

2

Elegancko, bardzo duży progres. Spróbuj jeszcze odpalić druga metodę na pustej liście

2

Moim zdaniem wygląda ok, ale jedno pytanie: po co zmieniasz optional of exception na koniec? Czemu nie zwrócić optionala? :)

1 użytkowników online, w tym zalogowanych: 0, gości: 1