Search code examples
javacomparablecompareto

How do you compare classes for order?


I am having issues finding an efficient way to sort classes by order. My following code completes the order in which i need to sort, but I believe there is another way (one I dont know).

What is an efficient way to sort classes?

public int compare(Object one, Object two)    
{  
          //S = Salaried, W = Weekly, D = Daily

          //SS == 0 -> SW == -1 -> SD == -1
          //WS == 1 -> WW == 0 -> WD == -1 
          //DS == 1 -> DW == 1 -> DD == 0

          Employee a = (Employee)one;
          Employee b = (Employee)two;

          SalariedEmployee s = new SalariedEmployee(0.0); 
          WeeklyEmployee w = new WeeklyEmployee (0.0);
          DailyEmployee d = new DailyEmployee();


          if(one.getClass() == s.getClass() && two.getClass() == s.getClass())
              return Double.compare(b.grossPay(), a.grossPay());

          if(one.getClass() == s.getClass() && two.getClass() == w.getClass())
              return -1;

          if(one.getClass() == s.getClass() && two.getClass() == d.getClass())
              return -1;

          if(one.getClass() == w.getClass() && two.getClass() == s.getClass())
              return 1;

          if(one.getClass() == w.getClass() && two.getClass() == w.getClass())
              return Double.compare(b.grossPay(), a.grossPay());

          if(one.getClass() == w.getClass() && two.getClass() == d.getClass())
              return -1;

          if(one.getClass() == d.getClass() && two.getClass() == s.getClass())
              return 1;

          if(one.getClass() == d.getClass() && two.getClass() == w.getClass())
              return 1;

          if(one.getClass() == d.getClass() && two.getClass() == d.getClass())
              return Double.compare(b.grossPay(), a.grossPay());

          return 0;

      }

Solution

  • I am having issues finding an efficient way to sort classes by order

    Depends what you mean by "efficient". Putting all the code in a single method will be the most efficient (if done properly) from a CPU perspective, but it is not very efficient from a flexibility point of view.

    For an approach that will not be a fast but will be far more flexible check out the Group Comparator and Bean Comparator.

    The GroupComparator allows you to combine multiple Comparators into one sort. The BeanComparator is a generic comparator that allows you to sort on any field within a given class. So to use the GroupComparator the basic code would be:

    EmployeeComparator employee = new EmployeeComparator();
    BeanComparator grossPay = new BeanComparator(Employee.class, "grossPay");
    GroupComparator gc = new GroupComparator(employee, grossPay);
    Collections.sort(list, gc);
    

    So you would need to write a Comparator that sorts Employees by salaried, weekly and daily. The basic code for the EmployeeComparator might be something like:

    if (one.getClass()equals(two.getClass())
        return 0;
    
    if (one instanceOf SalariedEmployee)
        return 1;
    
    if (two instanceOf SalariedEmployee)
       return -1;
    
    if (one instanceOf WeeklyEmployee)
        return 1;
    else
        return -1;
    

    A little more work to set up, but once you have an EmployeeComparator you can then sort of multiple different properties using the Bean and Group Comparators.