Próbuję uporządkować List
pracowników imieniem ówczesnego wieku przy użyciu Java8 Comparator
, Stworzyłem poniżej Comparator
ale daje mi błąd kompilatoraporównywania i thenComparing daje błąd kompilacji
Type mismatch: cannot convert from Comparator<Object> to <unknown>
Comparator<String> c = Comparator.comparing(s -> s.split("\\s+")[0])
.thenComparingInt(s -> Integer.parseInt(s.split("\\s+")[1])); //compile error
ale działa, jeśli jednoznacznie określę typ
Comparator<String> c = Comparator.<String, String> comparing(s -> s.split("\\s+")[0])
.thenComparingInt(s -> Integer.parseInt(s.split("\\s+")[1])); //works
lub przez utworzenie dwóch Compartor
S i łańcucha
Comparator<String> name = Comparator.comparing(s -> s.split("\\s+")[0]);
Comparator<String> age = Comparator.comparingInt(s -> Integer.parseInt(s.split("\\s+")[1]));
Comparator<String> cc = name.thenComparing(age); //works
mam określony typ Comparator<String>
na lewej stronie, ale dlaczego auto typu wnioskowanie nie jest znalezienie odpowiedniego rodzaju i spodziewa się określić jednoznacznie.
Czy ktoś może to wyjaśnić?
Oto kod
String[] arr = { "alan 25", "mario 30", "alan 19", "mario 25" };
Comparator<String> c = Comparator.<String, String> comparing(s -> s.split("\\s+")[0])
.thenComparingInt(s -> Integer.parseInt(s.split("\\s+")[1]));
List<String> sorted = Arrays.stream(arr).sorted(c).collect(Collectors.toList());
System.out.println(sorted);
wyjście
[alan 19, alan 25, mario 25, mario 30]
Nie jestem ekspertem od generycznego typu wnioskowania, ale zgaduję, to jest po prostu „zbyt dużo automatycznego wnioskowania”. Prawdopodobnie nie jest w stanie określić typu metody "comparing()", ponieważ nie ma ona żadnego typu do "zakotwiczenia", w przeciwieństwie do metody łańcuchowej, w której jawnie podajesz typowi wynik porównania () '. Niezależnie od tego, myślę, że byłoby bardziej czytelne napisanie własnego "Komparatora" i wywołanie tylko raz "podziału". Nie ma nagrody za ściskanie kodu w najmniejszej możliwej linii. – ajb
Typowanie celu nie działa poprzez powiązane wywołania metod, zobacz [tutaj] (http://stackoverflow.com/a/28834656/2711488) i [tutaj] (http://stackoverflow.com/a/26883991/2711488) i [tutaj] (http://stackoverflow.com/a/31383947/2711488). Możesz jednak po prostu użyć 'Comparator.comparing (s -> s.replaceFirst (" \\ s + "," "))' zamiast swojego komparatora dwuetapowego, a wynik będzie taki sam ... – Holger
'Comparator.comparing ((String s) -> s.split ("\\ s +") [0]). ThenComparingInt (s -> Integer.parseInt (s.split ("\\ s +") [1])) 'działa, ale dlaczego ten' String' jest wymagany, może wywnioskować z 'Komparator', czy jest to ograniczenie w wnioskowaniu typu? BTW przy użyciu 'java version" 1.8.0_60 "' –
Saravana