Saturday, 11 May 2013

Comparable Vs Comparator

Comparable interface contains a method called compareTo(Obj) which takes only one argument and it compares itself with another instance or objects of the same class.

Comparator interface contains a method called compare(Obj1, Obj2) which takes two arguments and it compares the value of two objects from the same or different classes.
Number of times I read this definition but this time I wrote a small program to understand how can I implement these two interfaces. Lets take comparable first.
In this example I have sorted the list of employees according to their names.

// Employee Class - Implements Comparable
public class Employee implements Comparable<Employee>
{
 private int empId;
 private String name;
 private int age;
 public Employee(int empId, String name, int age)
 {
  this.empId = empId;
  this.name = name;
  this.age = age;
 }
compareTo method takes second object and compare it with the first object(this here). Returns 1,0,-1 based on comparison if value is greater, equals and smaller respectively and swap  the values if necessary.Doing (this - o) will sort in ascending order and reverse will sort in descending order.
  public int compareTo(Employee o)
  {
  return this.name.compareTo(o.name);
  }
  public int getAge()
  {
   return this.age;
  }
  public int getEmpId()
  {
   return this.empId;
  }
  public String getName()
  {
   return this.name;
  }
}

// Another Class Util - Contains a list of employees

public class Util
{
 public static List<Employee> getEmployees()
 {
  List<Employee> col = new ArrayList<Employee>();

  col.add(new Employee(1, "Ankit", 25));
  col.add(new Employee(2, "Vijay", 82));
  col.add(new Employee(3, "Deepak", 30));
  col.add(new Employee(4, "Ajay", 12));
  col.add(new Employee(5, "Seema", 23));
  return col;
 }
}

// Another class TestEmployeeSort

public class TestEmployeeSort
{
 public static void main(String[] args)
 {
  List coll = Util.getEmployees();
  Collections.sort(coll); // sort method
  printList(coll);
 }

 private static void printList(List<Employee> list)
 {
  System.out.println("EmpId\tName\tAge");
  for (Employee e : list)
  {
   System.out.println(e.getEmpId() + "\t" + e.getName() + "\t"
     + e.getAge());
  }
 }
}

Lets do this by using Comparator

// Class Employee and Util will remain the same but this time Employee class will not implement the comparable interface. 

// Create a class SortByName - implements Comparator Interface

public class SortByName implements Comparator<Employee>
{
 public int compare(Employee o1, Employee o2)
 {
  return o1.getName().compareTo(o2.getName());
 }
}

Now there is a slight change in TestEmployeeSort class which is highlighted below:

public static void main(String[] args)
{
 List coll = Util.getEmployees();
 Collections.sort(coll, new SortByName()); // sort method
 printList(coll);
}

private static void printList(List<Employee> list)
{
 System.out.println("EmpId\tName\tAge");
 for (Employee e : list)
 {
  System.out.println(e.getEmpId() + "\t" + e.getName() + "\t"
    + e.getAge());
 }
}
        
The output for both the programs will be same i.e.
EmpId Name       Age
4         Ajay        12
1         Ankit        25
3         Deepak        30
5         Seema        23
2         Vijay        82

Key Points to be noted:

1. Collections.sort(coll) - Here sort is a static method of class Collections.
    public static <T extends Comparable<? super T>> void sort(List<T> list)
   Sorts the specified list into ascending order, according to the natural ordering of its elements. All elements in the list must implement the Comparable interface

2. Collections.sort(coll, new SortByName()) - This is again a static method of class Collections.
     public static <T> void sort(List<T> list, Comparator<? super T> c)
     Sorts the specified list according to the order induced by the specified comparator. 

3. Here return obj1.compareTo(obj1) or return obj1.compareTo(obj) statement only take    Object, primitive is not allowed. 

1 comment: