使用 lambdas 而不是显式 类
Usage of lambdas instead of explicit classes
我有程序使用显式 类 对值进行排序:
class CompLastNames implements Comparator<String> {
public int compare(String aStr, String bStr) {
int i, j;
i = aStr.lastIndexOf(' ');
j = bStr.lastIndexOf(' ');
return aStr.substring(i).compareToIgnoreCase(bStr.substring(j));
}
}
class CompThenByFirstName implements Comparator<String> {
public int compare(String aStr, String bStr) {
int i, j;
return aStr.compareToIgnoreCase(bStr);
}
}
public class TreeMapDemo2A {
public static void main(String[] args) {
CompLastNames compLN = new CompLastNames();
Comparator<String> compLastThenFirst =
compLN.thenComparing(new CompThenByFirstName());
TreeMap<String, Double> tm =
new TreeMap<String, Double>(compLastThenFirst);
...
得到结果:
Jane Baker: 1378.0
John Doe: 3434.34
Ralph Smith: -19.08
Tom Smith: 123.22
Tod Hull: 99.22
The new account balance of John Doe: 4434.34
然后,我尝试添加 lambda 而不是显式 类,例如:
Comparator<String> compLastThenFirst =
((aStr, bStr) -> aStr.compareToIgnoreCase(bStr));
TreeMap<String, Double> tm =
new TreeMap<String, Double>((aStr, bStr) -> aStr.substring(aStr.lastIndexOf(' ')).compareToIgnoreCase(bStr.substring(bStr.lastIndexOf(' '))));
结果是:
Jane Baker: 1378.0
John Doe: 3434.34
Tom Smith: -19.08
Tod Hull: 99.22
The new account balance of John Doe: 4434.34
但我没有得到完整列表 (没有拉尔夫·史密斯:-19.08)。
有谁知道如何正确书写?谢谢。
更新:
1)
Comparator<String> compLastThenFirst =
((Comparator<String>) (a, b) -> a.substring(a.lastIndexOf(' ')).compareToIgnoreCase(b.substring(b.lastIndexOf(' '))))
.thenComparing((a, b) -> a.compareToIgnoreCase(b));
TreeMap<String, Double> tm =
new TreeMap<String, Double>(compLastThenFirst);
...
2)
Comparator<String> compLN = (aStr, bStr) ->
aStr.substring(aStr.lastIndexOf(' '))
.compareToIgnoreCase(bStr.substring(bStr.lastIndexOf(' ')));
Comparator<String> compLastThenFirst =
compLN.thenComparing((aStr, bStr) -> aStr.compareToIgnoreCase(bStr));
TreeMap<String, Double> tm =
new TreeMap<String, Double>(compLastThenFirst);
...
正如@Sweeper 在评论中提到的,您忘记了对 Comparator#thenComparing
的调用。与 lambda 表达式对应的代码为:
Comparator<String> compLastThenFirst =
((Comparator<String>) (a, b) -> a.substring(a.lastIndexOf(' ')).compareToIgnoreCase(b.substring(b.lastIndexOf(' '))))
.thenComparing((a, b) -> a.compareToIgnoreCase(b));
您需要重新实现 thenComparing(Comparator)
所做的事情:
(aStr, bStr) -> {
int compareResult =
aStr.substring(aStr.lastIndexOf(' '))
.compareToIgnoreCase(
bStr.substring(bStr.lastIndexOf(' '))
)
if (compareResult != 0)
compareResult = aStr.compareToIgnoreCase(bStr);
return compareResult;
}
(还有see the OpenJDK source code。)
或者您可以通过分配给临时变量来使用 thenComparing
(如第一个示例):
Comparator<String> compLN = (aStr, bStr) ->
aStr.substring(aStr.lastIndexOf(' '))
.compareToIgnoreCase(bStr.substring(bStr.lastIndexOf(' ')));
Comparator<String> compLastThenFirst =
compLN.thenComparing((aStr, bStr) -> aStr.compareToIgnoreCase(bStr));
然而,最简单的写一个比较器的方法可能是这样的,使用comparing(Function,Comparator)
:
Comparator.comparing(str -> str.substring(str.lastIndexOf(' ')),
String.CASE_INSENSITIVE_ORDER)
.thenComparing(String.CASE_INSENSITIVE_ORDER)
(另请参阅 String.CASE_INSENSITIVE_ORDER
文档。)
我有程序使用显式 类 对值进行排序:
class CompLastNames implements Comparator<String> {
public int compare(String aStr, String bStr) {
int i, j;
i = aStr.lastIndexOf(' ');
j = bStr.lastIndexOf(' ');
return aStr.substring(i).compareToIgnoreCase(bStr.substring(j));
}
}
class CompThenByFirstName implements Comparator<String> {
public int compare(String aStr, String bStr) {
int i, j;
return aStr.compareToIgnoreCase(bStr);
}
}
public class TreeMapDemo2A {
public static void main(String[] args) {
CompLastNames compLN = new CompLastNames();
Comparator<String> compLastThenFirst =
compLN.thenComparing(new CompThenByFirstName());
TreeMap<String, Double> tm =
new TreeMap<String, Double>(compLastThenFirst);
...
得到结果:
Jane Baker: 1378.0
John Doe: 3434.34
Ralph Smith: -19.08
Tom Smith: 123.22
Tod Hull: 99.22
The new account balance of John Doe: 4434.34
然后,我尝试添加 lambda 而不是显式 类,例如:
Comparator<String> compLastThenFirst =
((aStr, bStr) -> aStr.compareToIgnoreCase(bStr));
TreeMap<String, Double> tm =
new TreeMap<String, Double>((aStr, bStr) -> aStr.substring(aStr.lastIndexOf(' ')).compareToIgnoreCase(bStr.substring(bStr.lastIndexOf(' '))));
结果是:
Jane Baker: 1378.0
John Doe: 3434.34
Tom Smith: -19.08
Tod Hull: 99.22
The new account balance of John Doe: 4434.34
但我没有得到完整列表 (没有拉尔夫·史密斯:-19.08)。 有谁知道如何正确书写?谢谢。
更新:
1)
Comparator<String> compLastThenFirst =
((Comparator<String>) (a, b) -> a.substring(a.lastIndexOf(' ')).compareToIgnoreCase(b.substring(b.lastIndexOf(' '))))
.thenComparing((a, b) -> a.compareToIgnoreCase(b));
TreeMap<String, Double> tm =
new TreeMap<String, Double>(compLastThenFirst);
...
2)
Comparator<String> compLN = (aStr, bStr) ->
aStr.substring(aStr.lastIndexOf(' '))
.compareToIgnoreCase(bStr.substring(bStr.lastIndexOf(' ')));
Comparator<String> compLastThenFirst =
compLN.thenComparing((aStr, bStr) -> aStr.compareToIgnoreCase(bStr));
TreeMap<String, Double> tm =
new TreeMap<String, Double>(compLastThenFirst);
...
正如@Sweeper 在评论中提到的,您忘记了对 Comparator#thenComparing
的调用。与 lambda 表达式对应的代码为:
Comparator<String> compLastThenFirst =
((Comparator<String>) (a, b) -> a.substring(a.lastIndexOf(' ')).compareToIgnoreCase(b.substring(b.lastIndexOf(' '))))
.thenComparing((a, b) -> a.compareToIgnoreCase(b));
您需要重新实现 thenComparing(Comparator)
所做的事情:
(aStr, bStr) -> {
int compareResult =
aStr.substring(aStr.lastIndexOf(' '))
.compareToIgnoreCase(
bStr.substring(bStr.lastIndexOf(' '))
)
if (compareResult != 0)
compareResult = aStr.compareToIgnoreCase(bStr);
return compareResult;
}
(还有see the OpenJDK source code。)
或者您可以通过分配给临时变量来使用 thenComparing
(如第一个示例):
Comparator<String> compLN = (aStr, bStr) ->
aStr.substring(aStr.lastIndexOf(' '))
.compareToIgnoreCase(bStr.substring(bStr.lastIndexOf(' ')));
Comparator<String> compLastThenFirst =
compLN.thenComparing((aStr, bStr) -> aStr.compareToIgnoreCase(bStr));
然而,最简单的写一个比较器的方法可能是这样的,使用comparing(Function,Comparator)
:
Comparator.comparing(str -> str.substring(str.lastIndexOf(' ')),
String.CASE_INSENSITIVE_ORDER)
.thenComparing(String.CASE_INSENSITIVE_ORDER)
(另请参阅 String.CASE_INSENSITIVE_ORDER
文档。)