Compare two objects by two criteria

I have a user of a class that contains a logical field, I want to sort the list of users, I want users who have a logical field to be true to be at the top of the list, and I want to sort them by their names. Here is my class:

public class User{ int id; String name; boolean myBooleanField; public User(int id, String name, boolean myBooleanField){ this.id = id; this.name = name; this.myBooleanField = myBooleanField; } @Override public boolean equals(Object obj) { return this.id == ((User) obj).id; } } 

Here is an example to clear what I want: let's say I have this collection of users:

 ArrayList<User> users = new ArrayList<User>(); users.add(new User(1,"user1",false)); users.add(new User(2,"user2",true)); users.add(new User(3,"user3",true)); users.add(new User(4,"user4",false)); Collections.sort(users, new Comparator<User>() { @Override public int compare(User u1, User u2) { //Here i'm lookin for what should i add to compare the two users depending to the boolean field return u1.name.compareTo(u2.name); } }); for(User u : users){ System.out.println(u.name); } 

I want to sort users to get this result:

 user2 user3 user1 user4 
+6
source share
5 answers

First you can use the Boolean.compare(boolean x, boolean y) method Boolean.compare(boolean x, boolean y) . And since true elements are sorted at the beginning of the array, you should use compare(u2.myBooleanField, u1.myBooleanField) :

 @Override public int compare(User u1, User u2) { final int booleanCompare = Boolean.compare(u2.myBooleanField, u1.myBooleanField); if (booleanCompare != 0) { return booleanCompare; } return u1.name.compareTo(u2.name); } 
+2
source

Is something like that possible?

 Collections.sort(users, new Comparator<User>() { public int compare(User u1, User u2) { String val1 = (u1.myBooleanField ? "0" : "1") + u1.name; String val2 = (u2.myBooleanField ? "0" : "1") + u2.name; return val1.compareTo(val2); } }); 
+2
source
 if (u1.myBooleanField) { if (u2.myBooleanField) return u1.name.compareTo(u2.name); return -1; } else if (u2.myBooleanField) { return 1; } else { return u1.name.compareTo(u2.name); } 
+2
source
 if(!u1.myBooleanField && u2.myBooleanField){ return 1; } else if (!u1.myBooleanField && u2.myBooleanField){ return -1; } else { //Whatever comparator you would like to sort on after sorting based on true and false } 

See what the Java compareTo () method returns. In the above example, we first sort based on true and false, and then if myBooleanField is equal for both users, you can sort based on a different property.

+1
source

You can use Collectors.groupingBy to separate the best users from the rest.

 Map<Boolean, List<User>> list = users.stream() .collect( Collectors.groupingBy( Info::getMyBooleanField); 

Choose the best users and sort them by name

 List<User> topUsers = list.get(true); topUsers.sort((u1, u2) -> u1.getName().compareTo(u2.getName())); 

Select the remaining users and sort them by name:

 List<User> restUsers = list.get(false); restUsers.sort((u1, u2) -> u1.getName().compareTo(u2.getName())); 

And here is the final list

 topUsers.addAll(restUsers ); users=(ArrayList<User>)topUsers; 
+1
source

Source: https://habr.com/ru/post/986534/


All Articles