Generyki Metoda statyczna

0

Wypisanie maksymalnej i minimalnej wartości dla obiektów typu String i Integer z listy.

public class MinMax<T extends Comparable<T>> {

    private T max;
    private T min;

    public MinMax(T max, T min) {
        this.max = max;
        this.min = min;
    }

    public T getMax() {
        return max;
    }

    public T getMin() {
        return min;
    }

    @Override
    public String toString() {
        return "MinMax{" +
                "max=" + max +
                ", min=" + min +
                '}';
    }
}

public class MinMaxService {
    public static void main(String[] args) {
        List<Double> doubleList = List.of(2.2, 545.88888, 1.2, -2222.2, 59.36);
        List<Integer> integerList = List.of(18888, 2, 3, 4, 5, 6, -2, -129, -2, 5, 222, 124);
        List<String> stringList = List.of("Jaaaaa", "Ta", "Jac", "Szym", "Olaaa", "U");

        System.out.println(getMinAndMax(doubleList));
        System.out.println(getMinAndMax(integerList));
        System.out.println(getMinAndMax(stringList));
    }
    public static <T extends Comparable> MinMax<?> getMinAndMax(List<T> arr){
        if (arr == null || arr.size()==0){
            return null;
        }
        T min = arr.get(0);
        T max = arr.get(0);
        for (T t : arr) {
            if (t.compareTo(min) < 0) {
                min = t;
            }
            if (t.compareTo(max) > 0) {
                max = t;
            }
        }
        return new MinMax<>(max,min);
    }
}

Mógłby mi ktoś wytłumaczyć jak stworzyć prawidłowo metodę statyczną getMinAndMax ? (Tak żebym zrozumiał) Dla Integerów wypisuje dobrze min i max. Dla Stringa na odwrót...

4

Dorzuć, jakie wartości wypisuje ci metoda dla String i jakie wartości chciałbyś otrzymać.

Ogólnie to jest tak, że Integer i String mają wbudowany w siebie mechanizm porównywania (dlatego możesz użyć t.compareTo(min) lub t.compareTo(max)). Podejrzewam, że porównywanie tekstu działa zgodnie z dokumentacją, natomiast nie działa tak jakbyś chciał.

EDIT: Java z domysłu porządkuje Stringi leksykograficznie: https://chortle.ccsu.edu/java5/Notes/chap92/ch92_2.html

0

screen.png
Czyli min max String robi tylko alfabetycznie ? Nie na długość znaków ?
Czy jest opcja w ogóle aby porównywać w tej metodzie String na długość znaków nie leksykograficznie ?
A i jeszcze jakby można o dokładne wytłumaczenie tej metody.
public - wiadomo publicnza
static - statyczna
<T extends Comparable> - parametr generyczny T ograniczenie dołu interfejs Comparable (aby była metoda compareTo())
MinMax<T> - ???
getMinAndMax - nazwa metody statycznej
List<T> - parametr generyczny który przyjmuje metoda

2

Wszystko się da ;)

Po pierwsze - to musisz olać Comparable (obiekty mające "wbudowaną" porównywarkę) na rzecz Comparator (obiekt, który wie jak porównywać inne obiekty).

Czyli:

  1. Zamiast metody:
public static <T extends Comparable> MinMax<?> getMinAndMax(List<T> arr) {
  // kod
}

Powinno być:

public static <T> MinMax<T> getMinAndMax(List<T> arr, Comparator<T> comparator) {
  // kod
}

Tu masz więcej o różnicy: https://www.javatpoint.com/difference-between-comparable-and-comparator

Wtedy t.compareTo(min) < 0 zamieni ci się na comparator.compare(t, min) i będziesz mógł z zewnątrz przekazać, jak chcesz sortować obiekty.
Np.

public class StringLengthComparator implements Comparator<String> {
    public int compare(String o, String o2) {
       if (o.length() > o2.length()) {
          return 1;
       } else if (o.length() == o2.length()) {
          return 0;
       } else {
          return -1;
       }
    }
}

I potem użyć tego w ten sposób:

List<String> stringList = List.of("Jaaaaa", "Ta", "Jac", "Szym", "Olaaa", "U");
System.out.println(getMinAndMax(stringList), new StringLengthComparator());

Co więcej, jest sporo "ułatwiaczy" do pisania Comparatorów, więc możesz wykorzystać lambdy, zamiast tworzyć klasy samemu:

List<String> stringList = List.of("Jaaaaa", "Ta", "Jac", "Szym", "Olaaa", "U");
Comparator<String> lengthComparator = Comparator.comparing(String::length);
System.out.println(getMinAndMax(stringList), lengthComparator);

Natomiast jeśli nie ogarniasz jeszcze lambd to po prostu zostań przy pisaniu własnych klas.

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