I am having issues using the Java 8 Comparator class to sort a list of items.
My current working comparator is below:
comparator = Comparator.comparing(Person::getName, Comparator.nullsFirst(Comparator.naturalOrder()));
This works: it orders the list by name with the null values first. However, I am now attempting to ignore case of the names.
I know that I can write a new getter that returns the name all lowercase, but I do not want to go with this approach as I have to do this for multiple attributes.
Looking online, it looks like I should be using String.CASE_INSENSITIVE_ORDER
, but the only examples I see do not include the null ordering specification.
I can do something like this:
comparator = Comparator.comparing(Person::getName, String.CASE_INSENSITIVE_ORDER);
However, whenever I try to include the Comparator.nullsFirst
I end up getting type errors, and am confused on how to continue.
I've tried doing a chain similar to
thenComparing(Comparator.nullsFirst(Comparator.naturalOrder))
but that also doesn't work.
Could someone lend me some advice on how I can chain these together to sort by name (not case sensitive) and then order the nulls. I seem to be confusing myself with the types.
Comparators are used to compare two objects. In this challenge, you'll create a comparator and use it to sort an array. The Player class is provided in the editor below. It has two fields: : a string. : an integer. Given an array of Player objects, write a comparator that sorts them in order of decreasing score.
Like the nullsFirst method, when both the arguments are null, they are considered as equal. If both are non-null, it uses the specified comparator to determine the order. If the specified comparator is null, then it considers all non-null values to be equal.
There are many possible places where we would use a Comparator. We might use it for sorting a list or an array, pass a Comparator to a TreeSet or a TreeMap, or sort a stream of objects using a Comparator. When there are one or more null elements in the collection, we would get a NullPointerException.
Using Comparator.reversed When invoked on an existing Comparator, the instance method Comparator.reversed returns a new Comparator that reverses the sort order of the original. Let's use the Comparator that sorts the employees by name and reverse it so that employees are sorted in descending order of the name:
There are two types of null
s you can have in your list. You can have null
Person
references, and you can have Person
s with null
names.
In the first case, you have to apply nullsFirst
to the base comparator you want to use:
comparator = Comparator.nullsFirst(
Comparator.comparing(Person::getName, String.CASE_INSENSITIVE_ORDER));
If you have the possibility of null
names, you need to make sure that your key never returns a null
, or that you apply nullsFirst
to String.CASE_INSENSITIVE_ORDER
. The second option is of course much easier:
comparator = Comparator.comparing(
Person::getName, Comparator.nullsFirst(String.CASE_INSENSITIVE_ORDER));
If you have both options (null
references and null
names), you will have to combine both versions and apply nullsFirst
twice:
comparator = Comparator.nullsFirst(
Comparator.comparing(
Person::getName,
Comparator.nullsFirst(String.CASE_INSENSITIVE_ORDER)
)
);
If you are chaining multiple comparisons like this, the outer nullsFirst
, which ensures that null
Person
s get sorted properly, can be applied to the entire chain:
comparator = Comparator.nullsFirst(
Comparator.comparing(
Person::getName,
Comparator.nullsFirst(String.CASE_INSENSITIVE_ORDER)
).thenComparing(...)
);
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With