Reputation: 1774
My goal is to apply 2 sorts on a list of objects made of string and boolean.
I have accounts and active/inactive states, so I want to show active first (sort boolean values) and then to sort rest of elements in alphabetical order.
For instance:
[John,inactive], [Craig,active], [Mike,inactive], [Dennis,innactive]
I want to have:
[Craig,active], [Dennis,innactive], [John,inactive], [Mike,inactive]
What I plan to do is to use Comparable<> but I wonder if there is another way to do that.
I don't want to use Guava or any additional libraries. This should be used for Android API 21 as well, so list.sort() cannot be used.
Thanks in advance!
Upvotes: 1
Views: 600
Reputation: 2863
Simply create a new Comparator
like this:
public class AccountComparator implements Comparator<Account> {
@Override
public int compare(Account o1, Account o2) {
if (o1.isActive() && !o2.isActive()) {
return -1;
}
if (!o1.isActive() && o2.isActive()) {
return 1;
}
return o1.getName().compareTo(o2.getName());
}
}
Minimal tested example:
public static void main(String[] args) {
Account account2 = new Account("B", true);
Account account4 = new Account("D", false);
Account account3 = new Account("C", true);
Account account1 = new Account("A", false);
List<Account> list = new ArrayList<>();
list.add(account1);
list.add(account2);
list.add(account3);
list.add(account4);
Collections.sort(list, new AccountComparator());
list.forEach(System.out::println);
}
with the expected output of
Account{name='B', active=true}
Account{name='C', active=true}
Account{name='A', active=false}
Account{name='D', active=false}
Or with a lambda expression: (Thanks to @Wow for using Comparator.comparing
)
Collections.sort(list, Comparator.comparing(Account::isActive).reversed()
.thenComparing(Account::getName));
Upvotes: 2
Reputation: 54214
There's no magic/easy way to do it without Java 8 or some third-party library. You'll have to implement Comparable
and do the heavy lifting yourself:
public class Person implements Comparable<Person> {
private final boolean isActive;
private final String name;
@Override
public int compareTo(Person other) {
if (isActive && !other.isActive) {
return -1;
} else if (!isActive && other.isActive) {
return 1;
} else {
return name.compareTo(other.name);
}
}
}
Upvotes: 2