What i wanna do is to remove an object from a table of object ONLY IF the object i wanna delete have the id i put in params.
Let's get into the code :
public static animals[] supprimerAnimals(int identifiant, animals[] liste){
animals[] newOne = new animals[0];
for(int i = 0; i < liste.length; i++){
}
return newOne;
}
This method will receive a id and a table in params.
In the table, we have objects... let's tell them animals. Here is a list of objects we could have :
liste[0] = animals(1, "cat", 6)
liste[1] = animals(2, "dog", 4)
here would be the constructor :
animals(int id, String type, int age);
So we have all we would need to get the solution.
So now let's get into an example...
If i do this :
animals[] zoo = supprimerAnimals(2, liste);
I need that zoo contains this :
zoo[0] = animals(1, "cat", 6);
Can you guys put me on the right way please ?
I'm getting lock on the fact that i have to create a new table and i don't even now if the id will exist on the old table... So i can't fix the size of the new table...
Thank you guys
animals[]
means that there is a java Object called animals, and the items in that array have this DataType "animals"
bellow i created an Object named Animal and here is an example with 2 ways of doing that
public class Animal{
private int id;
private String name;
private int age;
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
}
now some where you can implement the deleteMethods something like:
public static Animal[] removeAnimal(Animal[] animals, int id) {
List<Animal> list = Arrays.asList(animals);
for(Animal item : animals)
if( item.getId() == id )
list.remove(item);
return list.toArray(animals);
}
OR
public static Animal[] removeAnimal2(Animal[] animals, int id) {
Animal[] arr = new Animal[animals.length-1];
int i = 0;
for(Animal item : animals){
if( item.getId() != id ){
try{
arr[i]=item;
}catch(Exception ex){
ex.printStackTrace();
}
}
}
return arr;
}
See if this suits your need.
public static animals[] supprimerAnimals(int identifiant, animals[] liste) {
int supprimer = -1;
for (int i = 0; i < liste.length; i++) {
if (liste[i].getId() == identifiant) {
supprimer = i;
break;
}
}
if (supprimer < 0) {
return liste;
}
animals[] nouveauListe = new animals[liste.length - 1];
for (int i = 0; i < supprimer; i++) {
nouveauListe[i] = liste[i];
}
for (int i = supprimer + 1; i < liste.length; i++) {
nouveauListe[i - 1] = liste[i];
}
return nouveauListe;
}
Note
Java class names by convention are PascalCase and are singular, not plural
Just Check out this. I have used list instead of Arrays.
package com.Hangman;
import java.util.ArrayList;
import java.util.List;
public class Test5 {
public static void main(String[] args) {
List zoo= new ArrayList();
Animal animal= new Animal(1,"cat",01);
zoo.add(animal);
animal= new Animal(6,"dog",02);
zoo.add(animal);
animal= new Animal(3,"mouse",03);
zoo.add(animal);
animal= new Animal(8,"rabbit",04);
zoo.add(animal);
animal= new Animal(5,"lion",05);
zoo.add(animal);
System.out.println("List of Animals in zoo");
System.out.println(zoo);
System.out.println("Animal to be removed from zoo is having id 3");
removeFromZoo(zoo, 3);
System.out.println("Animals in zoo after removal");
System.out.println(zoo);
}
static void removeFromZoo(List zoo,int id){
Animal animal= new Animal(id,null, 0);
zoo.remove(animal);
}
}
class Animal{
int id;
String type;
int age;
public Animal(int id, String type, int age) {
super();
this.id = id;
this.type = type;
this.age = age;
}
#Override
public String toString() {
return ""+this.type;
}
#Override
public boolean equals(Object animal) {
if(animal instanceof Animal){
return this.id==((Animal) animal).id;
}else
return false;
}
}
Related
Im just start learning java renow .i created a class student which contain variable ID and name and another class studentlist that is an arraylist of student.
I want to create seach function that allow to pass variale's name of stunt class (ID or name) and the variable value. how can i do it ?
class Student{
String ID;
String name;
public Student(){
}
public Student(String ID,String name){
this.ID = ID;
this.name = name;
}
public String getStudent() {
String info = this.ID +"\t\t\t"+ this.name;
return info;
}
}
class StudentList{
private ArrayList <Student> list = new ArrayList<>();
private int counter = 0;
static Scanner sc = new Scanner(System.in);
public StudentList(){
}
public StudentList(Student stu){
Student student = new Student(stu.ID,stu.name);
this.list.add(student);
this.counter++;
}
public int seach(String type(name or ID) , String value ){
int i;
int found = 0;
for(i = 0; i < list.size();i++){
if(value.equals(list.get(i).type){
found++;
System.out.println(value.equals(list.get(i).type);
}
}
return found;
}
}
Create getter for ID and name in Class Student.
Than you can ask in seach
public int seach(String type , String value ){
int i;
int found = 0;
for(i = 0; i < list.size();i++){
Student student = list.get(i);
if(value.equals(student.getID()) || value.equals(student.getName())){
found++;
System.out.println(value.equals(list.get(i).type);
}
}
return found;
}
First I recommend to set the attributes of your Student class to private. Then you could add setters and getters.
public class Student {
private String ID;
private String name;
public Student() {}
public Student(String ID, String name) {
this.ID = ID;
this.name = name;
}
public String getID() { return ID; }
public String getName() { return name;
public void setID(String ID) { this.ID = ID; }
public void setName(String name) { this.name = name; }
}
In your class StudentList I would split and extend the functionalities of the search instead of passing the value type as an additional argument.
public class StudentList {
...
public int searchByName(String name) {
for(int i=0; i < list.size(); i++) {
if(list.get(i).getName().equals(name)) return i;
}
return -1;
}
public int searchByID(String ID) {
for(int i=0; i < list.size(); i++) {
if(list.get(i).getID().equals(ID)) return i;
}
return -1;
}
public int searchStudent(Student stud) { return list.indexOf(stud); }
}
If you really need a function that bundles all of that you could add another function that decides by a flag which function should be called with the passed argument. You could also add a check for arguments here while having more flexibility and separation of responsibilities.
public int search(int flag, arg Object) {
if(flag == 0) return searchStudent((Student) arg);
else if(flag == 1) return searchByID((String) arg);
else return searchByName((String) arg);
}
Additional side note: if you want to indicate the current number of students in the list with your counter variable, I highly recommend to remove this variable and always call the size() method of your list when needed. Every Java collection (i.e. ArrayList) provides it and it will always return the correct value after removing or adding students. Implementing your own counter for this task will result in a more error prone source code.
I had an interview today and I have given two java classes and asked to search dog details by registration number. I know that Java.util.ArrayList.contains(Object) but do not know how to implement when there are more than one fields.
The second question was: what is the most efficient search techniques you can use in this example? I thought about Collections.binarySearch but not sure that it is the most efficient in this example. If so, how can I implement it?
DogSort.java
public class DogSort {
public static void main(String[] args) {
ArrayList<Dog> listDog = new ArrayList<Dog>();
Scanner sc = new Scanner(System.in);
listDog.add(new Dog("Max", "German Shepherd", "33"));
listDog.add(new Dog("Gracie","Rottweiler","11"));
Collections.sort(listDog, Dog.COMPARE_BY_NAME);
System.out.println(listDog);
}
}
Dog.java
class Dog {
private String name;
private String breed;
private String registrationNumber;
public Dog(String name, String breed, String registrationNumber) {
this.name = name;
this.breed = breed;
this.registrationNumber = registrationNumber;
}
public static Comparator<Dog> COMPARE_BY_NAME = new Comparator<Dog>() {
public int compare(Dog one, Dog other) {
return one.name.compareTo(other.name);
}
};
//getter and setter methods for all private variable
}
I agree with #Pritam Banerjee's answer. The most efficient search technique is to use HashMap in this scenario. I would recommend to use HashSet but the HashSet#contains method returns boolean, so just use map. Here is the code snippet.
Just for Information When using hash based collection/map dont forget to implement hashCode and equals method properly.
public class DogSearch {
public static void main(String[] args) {
Map<String, Dog> dogs = new HashMap<String, Dog>();
Dog max = new Dog("Max", "German Shepherd", "1001");
Dog gracie = new Dog("Gracie", "Rottweiler", "1002");
Dog luca = new Dog("Luca", "Labrador", "1003");
Dog tiger = new Dog("Tiger", "Beagle", "1004");
Dog meemo = new Dog("Meemo", "Bulldog", "1005");
Dog lacie = new Dog("Lacie", "German Shorthaired Pointer", "1006");
dogs.put(max.getRegistrationNumber(), max);
dogs.put(gracie.getRegistrationNumber(), gracie);
dogs.put(luca.getRegistrationNumber(), luca);
dogs.put(tiger.getRegistrationNumber(), tiger);
dogs.put(meemo.getRegistrationNumber(), meemo);
dogs.put(lacie.getRegistrationNumber(), lacie);
Dog result = dogs.get("1002");
if (result == null) {
System.out.println("Dog not found");
} else {
System.out.println(result);
}
}
}
class Dog {
private String name;
private String breed;
private String registrationNumber;
public Dog(String name, String breed, String registrationNumber) {
this.name = name;
this.breed = breed;
this.registrationNumber = registrationNumber;
}
public static Comparator<Dog> COMPARE_BY_NAME = new Comparator<Dog>() {
public int compare(Dog one, Dog other) {
return one.name.compareTo(other.name);
}
};
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getBreed() {
return breed;
}
public void setBreed(String breed) {
this.breed = breed;
}
public String getRegistrationNumber() {
return registrationNumber;
}
public void setRegistrationNumber(String registrationNumber) {
this.registrationNumber = registrationNumber;
}
#Override
public int hashCode() {
final int prime = 31;
int result = 1;
result = prime * result + ((breed == null) ? 0 : breed.hashCode());
result = prime * result + ((name == null) ? 0 : name.hashCode());
result = prime * result + ((registrationNumber == null) ? 0 : registrationNumber.hashCode());
return result;
}
#Override
public boolean equals(Object obj) {
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
Dog other = (Dog) obj;
if (breed == null) {
if (other.breed != null)
return false;
} else if (!breed.equals(other.breed))
return false;
if (name == null) {
if (other.name != null)
return false;
} else if (!name.equals(other.name))
return false;
if (registrationNumber == null) {
if (other.registrationNumber != null)
return false;
} else if (!registrationNumber.equals(other.registrationNumber))
return false;
return true;
}
#Override
public String toString() {
return "Dog [name=" + name + ", breed=" + breed + ", registrationNumber=" + registrationNumber + "]";
}
}
Time Complexity
Insertion : O(1)
Search : O(1)
Add it to a HashMap with Registration as Key and Dog object as the value and then search the Map.
O(1) insertion and O(1) searching.
Binary Search O(log n).
For the first question ie to search details by registration number here is the code
import java.util.Comparator;
import java.util.TreeMap;
public class DogSort {
public static void main(String[] args) {
TreeMap<Integer, Dog> listDogs = new TreeMap<>();
listDogs.put(33, new Dog("Max", "German Shepherd", "33"));
listDogs.put(11, new Dog("Gracie", "Rottweiler", "11"));
System.out.println(listDogs);
System.out.println(listDogs.containsKey(11));
System.out.println(listDogs.get(11));
}
}
class Dog {
private String name;
private String breed;
private String registrationNumber;
public Dog(String name, String breed, String registrationNumber) {
this.name = name;
this.breed = breed;
this.registrationNumber = registrationNumber;
}
public static Comparator<Dog> COMPARE_BY_NAME = new Comparator<Dog>() {
public int compare(Dog one, Dog other) {
return one.name.compareTo(other.name);
}
};
#Override
public String toString() {
return "Dog [name=" + name + ", breed=" + breed + ", registrationNumber=" + registrationNumber + "]";
}
}
It is very difficult to get the details of dog by registration number using arraylist, but with map it is quite easy.
And you can override the hashcode and equals method like this but the arraylist compare method works differently.
What you can do is you can write a method which can search details by registration number. The method will have to iterate the list and find the Dog object,and if the list is sorted then you need to implement your own binary search to get the Dog object according to the registration number.
import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
public class DogSort {
public static void main(String[] args) {
ArrayList<Dog> listDog = new ArrayList<Dog>();
listDog.add(new Dog("Max", "German Shepherd", "33"));
listDog.add(new Dog("Gracie", "Rottweiler", "11"));
Collections.sort(listDog, Dog.COMPARE_BY_NAME);
System.out.println(listDog);
System.out.println(listDog.contains(new Dog("Max", "Rottweiler", "33")));
}
}
class Dog {
private String name;
private String breed;
private String registrationNumber;
public Dog(String name, String breed, String registrationNumber) {
this.name = name;
this.breed = breed;
this.registrationNumber = registrationNumber;
}
public static Comparator<Dog> COMPARE_BY_NAME = new Comparator<Dog>() {
public int compare(Dog one, Dog other) {
return one.name.compareTo(other.name);
}
};
#Override
public String toString() {
return "Dog [name=" + name + "]";
}
#Override
public int hashCode() {
final int prime = 31;
int result = 1;
result = prime * result + ((registrationNumber == null) ? 0 : registrationNumber.hashCode());
return result;
}
#Override
public boolean equals(Object obj) {
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
Dog other = (Dog) obj;
if (registrationNumber == null) {
if (other.registrationNumber != null)
return false;
} else if (!registrationNumber.equals(other.registrationNumber))
return false;
return true;
}
}
We have a ArrayList. It contains duplicate employee objects with only difference in their age, but name and id will be same. So while removing the duplicates, we have to keep the employee with maximum age and remove all other duplicates. This is one of the questions asked by an interviewer in one of the interviews.
I tried solving this. It is giving me correct result, but I am not sure with my approach as I am changing the state of the object in equals method. Is there any other approach to solve this problem?
Code Snippet below: -
package practice;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
class Employee {
private int id;
private String name;
private int age;
Employee(int id, String name, int age) {
this.id = id;
this.name = name;
this.age = age;
}
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
#Override
public int hashCode() {
return (31*(name.hashCode()) + 31);
}
#Override
public boolean equals(Object obj) {
if ((obj instanceof Employee)) {
if (((Employee)obj).getId() == this.id && (((Employee)obj).getName().equalsIgnoreCase(this.name))) {
if(this.age > ((Employee)obj).getAge()) {
((Employee)obj).setAge(this.age);
}
return true;
} else
return false;
} else
return false;
}
}
public class ListDuplicateRemoval {
public static List<Employee> removeDuplicates(List<Employee> employees) {
Set<Employee> set = new HashSet<>();
for (int i = 0; i < employees.size(); i++) {
set.add(employees.get(i));
}
/*for (int i = 0; i < set.size(); i++) {
System.out.println(set.iterator().next().getAge());
}*/
employees.removeAll(employees);
employees.addAll(set);
return employees;
}
public static void main(String[] args) {
Employee e1 = new Employee(1, "Mike", 20);
Employee e2 = new Employee(1, "Mike", 21);
List <Employee> list = new ArrayList<>();
list.add(e1);
list.add(e2);
removeDuplicates(list);
System.out.println(list.size());
System.out.println(list.get(0).getAge());
}
}
No this solution is really awful. equals should never, ever, modify the state of the objects it's comparing.
Create a class containing the information that identifies employees uniquely, and which properly override equal() and hashCode(). Then use a Map containing these identication info as key, and the employee with the largest age as value. Then get the values and make it a list:
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.function.Function;
import java.util.stream.Collectors;
class Employee {
private int id;
private String name;
private int age;
Employee(int id, String name, int age) {
this.id = id;
this.name = name;
this.age = age;
}
int getId() {
return id;
}
String getName() {
return name;
}
int getAge() {
return age;
}
#Override
public String toString() {
return "Employee{" +
"id=" + id +
", name='" + name + '\'' +
", age=" + age +
'}';
}
}
class DuplicateRemoval {
public static void main(String[] args) {
List<Employee> employeeList = Arrays.asList(
new Employee(1, "Joe", 23),
new Employee(2, "Joe", 23),
new Employee(1, "Joe", 21),
new Employee(1, "Jane", 22),
new Employee(1, "Jane", 20)
);
Map<EmployeeKey, Employee> map = employeeList.stream().collect(
Collectors.toMap(e -> new EmployeeKey(e.getId(), e.getName()),
Function.identity(),
(e1, e2) -> e1.getAge() > e2.getAge() ? e1 : e2)
);
List<Employee> result = new ArrayList<>(map.values());
System.out.println("result = " + result);
}
private static class EmployeeKey {
private int id;
private String name;
EmployeeKey(int id, String name) {
this.id = id;
this.name = name;
}
#Override
public boolean equals(Object o) {
if (this == o) {
return true;
}
if (o == null || getClass() != o.getClass()) {
return false;
}
EmployeeKey that = (EmployeeKey) o;
return id == that.id &&
Objects.equals(name, that.name);
}
#Override
public int hashCode() {
return Objects.hash(id, name);
}
}
}
Implement a Comparator<Employee>
Have the compare method take into account age.
Have the equals method ignore age.
use equals to identify duplicates.
use compare to determine which duplicate to keep.
I have a Query I have developed a pojo ..
public class Customer {
int Age;
public Customer(int age, String surname, String forename) {
super();
Age = age;
Surname = surname;
Forename = forename;
}
String Surname,Forename;
public int getAge() {
// TODO Auto-generated method stub
return Age;
}
public String getSurname() {
// TODO Auto-generated method stub
return Surname;
}
public String getForename() {
// TODO Auto-generated method stub
return Surname;
}
public void display()
{
// System.out.println(Forename+"\t"+Surname+"\t"+Age);
System.out.println(Age+"\t"+Forename+"\t"+Surname);
}
}
and here is my collection class ..
class testCustomerComparator
{
public static void main(String... a)
{
Customer customerFirst = new Customer(46,"Alabama", "Christonson");
Customer customerSecond = new Customer(21, "Anna", "Sobek");
Customer customerThird = new Customer(27, "Rafael", "Sobek");
List<Customer> list = new ArrayList<Customer>();
list.add(customerThird);
list.add(customerSecond);
list.add(customerFirst);
}
}
please advise me How to make comprator for this class , I want to make comparator so that a list of customers get sorted by age and second by surname. After that you want to sort by forename. please advise I have nesting condition inside comparator
lOGIC MUST BE SOMETHING LIKE...
public class CustomerComparator implements Comparator<Customer> {
#Override
public int compare(Customer c1, Customer c2) {
if (c1.getAge() == c2.getAge()) {
if (c1.getSurname().compareTo(c2.getSurname()) == 0) {
return c1.getForename().compareTo(c2.getForename()) {
} else {
return c1.getSurname().compareTo(c2.getSurname());
}
} else if (c1.getAge() > b2.getAge()) {
return -1;
} else {
return 1;
}
}
but it is not working please advise
Seems much like homework. I can give you some hints in where to look at.
You have two choices:
make the POJO class extend Comparable<Customer>
define a custom external comparator as a Comparator<Customer>.
Assuming the second choice, in which you have two explicit customers, you'll have to define a method similar to this one:
#Override
public int compare(Customer c1, Customer c2)
{
// this method should return 0 if c1.equals(c2),
// should instead return 1 if c1 should come first than c2 and -1 otherwise
}
public class CustomerComparator implements Comparator<Customer> {
public int compare(Customer c1, Customer c2) {
.... here you have c1 and c2. compare returns -1 if c1 should go before c2,
0 if they are found to be equal, and 1 if c2 should go before c1.
You add the logic to compare c1 and c2 fields as you stated and return the result.
}
}
Then you use Collections.sort to sort that list using this comparator.
You can help of the below code.
import java.util.*;
class Customer {
private int age;
private String name;
private String forename;
public Customer(int age, String surname, String forename) {
super();
this.age = age;
this.name = surname;
this.forename = forename;
}
public void setAge(int age) {
this.age = age;
}
public int getAge() {
return this.age;
}
public void setName(String name) {
this.name = name;
}
public String getName() {
return this.name;
}
public void setForename(String forename) {
this.forename = forename;
}
public String getForename() {
return forename;
}
}
class AgeComparator implements Comparator {
public int compare(Object emp1, Object emp2) {
int emp1Age = ((Customer) emp1).getAge();
int emp2Age = ((Customer) emp2).getAge();
if (emp1Age > emp2Age)
return 1;
else if (emp1Age < emp2Age)
return -1;
else
return 0;
}
}
/*
* The below given comparator compares employees on the basis of their name.
*/
class NameComparator implements Comparator {
public int compare(Object emp1, Object emp2) {
// parameter are of type Object, so we have to downcast it to Employee
// objects
int emp1Age = ((Customer) emp1).getAge();
int emp2Age = ((Customer) emp2).getAge();
if (emp1Age > emp2Age) {
return 1;
} else if (emp1Age < emp2Age) {
String emp1Name = ((Customer) emp1).getName();
String emp2Name = ((Customer) emp2).getName();
// uses compareTo method of String class to compare names of the
// employee
return emp1Name.compareTo(emp2Name);
} else {
return 0;
}
}
}
class CustomerComparator implements Comparator {
public int compare(Object emp1, Object emp2) {
// parameter are of type Object, so we have to downcast it to Employee
// objects
String emp1Name = ((Customer) emp1).getName();
String emp2Name = ((Customer) emp2).getName();
// uses compareTo method of String class to compare names of the
// employee
return emp1Name.compareTo(emp2Name);
}
}
public class JavaComparatorExample {
public static void main(String args[]) {
// Employee array which will hold employees
Customer employee[] = new Customer[3];
// set different attributes of the individual employee.
employee[0] = new Customer(46, "Alabama", "Christonson");
employee[1] = new Customer(21, "Anna", "Sobek");
employee[2] = new Customer(27, "Rafael", "Sobek");
System.out.println("Order of employee before sorting is");
// print array as is.
for (int i = 0; i < employee.length; i++) {
System.out.println("Employee " + (i + 1) + " name :: "
+ employee[i].getName() + ", Age :: "
+ employee[i].getAge());
}
Arrays.sort(employee, new AgeComparator());
System.out
.println("\n\nOrder of employee after sorting by employee age is");
for (int i = 0; i < employee.length; i++) {
System.out.println("Employee " + (i + 1) + " name :: "
+ employee[i].getName() + ", Age :: "
+ employee[i].getAge());
}
// Sorting array on the basis of employee Name by passing NameComparator
Arrays.sort(employee, new NameComparator());
System.out
.println("\n\nOrder of employee after sorting by employee name is");
for (int i = 0; i < employee.length; i++) {
System.out.println("Employee " + (i + 1) + " name :: "
+ employee[i].getName() + ", Age :: "
+ employee[i].getAge());
}
}
}
Hope this will help you.
EDIT
Look at the CustomerComparator class.
#Override
public int compare(Customer c1, Customer c2) {
int r = Integer.valueOf(c1.getAge()).compareTo(c2.getAge());
if (r != 0) return r;
r = c1.getSurname().compareTo(c2.getSurname());
if (r != 0) return r;
return c1.getForename().compareTo(c2.getForename());
}
If I have the following class:
public class Employee {
private int empId;
private String name;
private int age;
public Employee(int empId, String name, int age) {
// set values on attributes
}
// getters & setters
}
How can I use comparator that compares by name, then age, then id?
You need to implement it so that it orders by preferred elements. That is, you need to compare by name, then if that comparison is equal, compare by age, etc. An example is listed below:
public class EmployeeComparator implements Comparator<Employee> {
#Override
public int compare(Employee e1, Employee e2) {
int nameDiff = e1.getName().compareTo(e2.getName());
if(nameDiff != 0) {
return nameDiff;
}
int ageDiff = e1.getAge() - e2.getAge();
if(ageDiff != 0) {
return ageDiff;
}
int idDiff = e1.getEmpId() - e2.getEmpId();
return idDiff;
}
}
Update
Came across this a moment ago: How to compare objects by multiple fields One of the answers linked to ComparatorChain which will invoke multiple comparators in sequence until a non-zero result is received from a comparator or all comparators are invoked. This should probably be your preferred solution.
Perhaps this (untested) implementation of Comparator#compare() will do the trick.
int compare(Employee e, Employee f)
{
int val = e.name.compareTo(f.name);
if(val == 0)
{
val = e.age - f.age;
if(val == 0)
{
val = e.empId - f.empId;
}
}
return val;
}
You can also implement the Comparable Interface in your class.
for example, something like this:
public class Employee implements Comparable<Employee>{
private int empId;
private String name;
private int age;
public Employee(int empId, String name, int age) {
// set values on attributes
}
// getters & setters
public int compareTo(Employee o) {
int ret = this.name.compareTo(o.name);
if(ret == 0)
ret = this.age - o.age;
if(ret == 0)
ret = this.empId - o.empId;
return ret;
}
}
so you don't have to implement a extra class to compare your Employees.
Implement it
public class Employee {
private int empId;
private String name;
private int age;
/**
* #param empId
* #param name
* #param age
*/
public Employee(int empId, String name, int age) {
super();
this.empId = empId;
this.name = name;
this.age = age;
}
/**
*
*/
public Employee() {
super();
// TODO Auto-generated constructor stub
}
public int getEmpId() {
return empId;
}
public void setEmpId(int empId) {
this.empId = empId;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
//Compare by name, age and then id
public static Comparator<Employee> COMPARE_EMPLOYEE = new Comparator<Employee>() {
public int compare(Employee one, Employee other) {
//Compare Name
if (one.getName().compareToIgnoreCase(other.getName()) == 0) {
//Compare age
if((one.getAge() - other.getAge()) == 0) {
// Now check with id is useless
// So directly return result of compare by id
return one.getEmpId() - other.getEmpId();
} else { //If age Not equal
return one.getAge() - other.getAge();
}
} else { //If name not equal
return one.getName().compareToIgnoreCase(other.getName());
}
}
};
}
Use :
List<Employee> contacts = new ArrayList<Employee>();
//Fill it.
//Sort by address.
Collections.sort(contacts, Employee.COMPARE_EMPLOYEE);
Read Sorting an ArrayList of Contacts , this must help you and you will get more ideas and different different types of use of Comparator.
guava ComparisonChain:
List<Employee> list = new ArrayList<Employee>();
//...
Collections.sort(list, new Comparator<Employee>(){
#Override
public int compare(Employee e1, Employee e2) {
return ComparisonChain.start()
.compare(e1.empId, e2.empId)
.compare(e1.name, e2.name)
.compare(e1.age, e2.age).result();
}});
Use this:
public class Test
{
public static void main(String[] args)
{
Employee emp1 = new Employee(2, "Tom", 20);
Employee emp2 = new Employee(1, "Tom", 20);
Employee emp3 = new Employee(3, "Hank", 21);
List<Employee> list = new ArrayList<>();
list.add(emp1);
list.add(emp2);
list.add(emp3);
Collections.sort(list, new Employee().new MyComparator());
System.out.println(list);
}
}
class Employee
{
private int empId;
private String name;
private int age;
public Employee()
{}
public Employee(int empId, String name, int age)
{
this.empId = empId;
this.name = name;
this.age = age;
}
class MyComparator implements Comparator<Employee>
{
#Override
public int compare(Employee e1, Employee e2)
{
if(e1.name.compareTo(e2.name) == 0)
{
if(((Integer)e1.age).compareTo(e2.age) == 0)
{
return ((Integer)e1.empId).compareTo(e2.empId);
}
else
{
return ((Integer)e1.age).compareTo(e2.age);
}
}
return e1.name.compareTo(e2.name);
}
}
#Override
public String toString()
{
return "Employee [empId=" + empId + ", name=" + name + ", age=" + age + "]";
}
}
The Comparator interface defines two methods: compare() and equals().
The compare() method, compares two elements for order:
int compare(Object obj1, Object obj2)
obj1 and obj2 are the objects to be compared. This method returns zero if the objects are equal. It returns a positive value if obj1 is greater than obj2. Otherwise, a negative value is returned.
By overriding compare(), you can alter the way that objects are ordered. For example, to sort in a reverse order, you can create a comparator that reverses the outcome of a comparison.
The equals() method, tests whether an object equals the invoking comparator: boolean equals(Object obj)
obj is the object to be tested for equality. The method returns true if obj and the invoking object are both Comparator objects and use the same ordering. Otherwise, it returns false.
Example:
import java.util.*;
class Dog implements Comparator<Dog>, Comparable<Dog> {
private String name;
private int age;
Dog() {
}
Dog(String n, int a) {
name = n;
age = a;
}
public String getDogName() {
return name;
}
public int getDogAge() {
return age;
}
// Overriding the compareTo method
public int compareTo(Dog d) {
return (this.name).compareTo(d.name);
}
// Overriding the compare method to sort the age
public int compare(Dog d, Dog d1) {
return d.age - d1.age;
}
}
public class Example {
public static void main(String args[]) {
// Takes a list o Dog objects
List<Dog> list = new ArrayList<Dog>();
list.add(new Dog("Shaggy", 3));
list.add(new Dog("Lacy", 2));
list.add(new Dog("Roger", 10));
list.add(new Dog("Tommy", 4));
list.add(new Dog("Tammy", 1));
Collections.sort(list); // Sorts the array list
for(Dog a: list) // printing the sorted list of names
System.out.print(a.getDogName() + ", ");
// Sorts the array list using comparator
Collections.sort(list, new Dog());
System.out.println(" ");
for(Dog a: list) // printing the sorted list of ages
System.out.print(a.getDogName() +" : "+ a.getDogAge() + ", ");
}
}
Check it out for more Java Comparator examples.