Hariom
Hariom

Reputation: 69

Java ArrayList Sort on the basis of dynamic objects fields?

I am getting a issue i have below code

public void columnsList(List<TableRecord> records){

    for(TableRecord record : records){
        Table table = record.getTable();
        //Do sort here on stampDate
        Field[] fields = table.fields();
        for(Field field : fields){
            field.getName();
            record.getValue(field);

        }
    }

}

and records object contain Object of different class type

List<TableRecord> records = new List<TableRecord>();
records.add(new AddressRecord());
records.add(new CityRecord());
records.add(new UserRecord());

Now how i need to sort them by stampDate variable which is in each class how can we do it when we have different classes in list

Upvotes: 0

Views: 2075

Answers (4)

agad
agad

Reputation: 2189

If you can't change the classes write your comparator( Comparator<Object>), that will try to find the field stampDate and compare them. Than use it for sorting the list. Comparator implementation:

import java.util.Comparator;
import java.util.Date;


public class StampDateComparator implements Comparator<Object> {

@Override
public int compare(Object o1, Object o2) {

    try {
        Date d1 = (Date) o1.getClass().getDeclaredField("stampDate").get(o1);
        Date d2 = (Date) o2.getClass().getDeclaredField("stampDate").get(o2);
        return compare(d1, d2);
    } catch (SecurityException e) {
        throw new RuntimeException(e);
    } catch (NoSuchFieldException e) {
        throw new RuntimeException("Missing variable stampDate");
    }catch (ClassCastException e) {
        throw new RuntimeException("stampDate is not a Date");
    } catch (IllegalArgumentException e) {
        //shoud not happen
        throw new RuntimeException(e);
    } catch (IllegalAccessException e) {
        throw new RuntimeException(e);
    }
}

}

Upvotes: 1

aUserHimself
aUserHimself

Reputation: 1597

If your code above is correct, that means AddressRecord, CityRecord and UserRecord all extend TableRecord:

class AddressRecord extends TableRecord {
    // other fields and methods here
}
class CityRecord extends TableRecord {
    // other fields and methods here
}
class UserRecord extends TableRecord {
    // other fields and methods here
}

You only have to write a Comparator for this class. It should look something like this:

class TableRecord {
    private Date timeStamp;

    public Date getTimeStamp() {
        return timeStamp;
    }
// other fields and methods here
}

class RecordStampDateComparator implements Comparator<TableRecord>{

    public int compare(TableRecord tr1, TableRecord tr2) {
        Date tr1Date = tr1.getTimeStamp();
        Date tr2Date = tr2.getTimeStamp();   
        return tr1Date.compareTo(tr2Date);
    }
}

Upvotes: 2

Viktor Ozerov
Viktor Ozerov

Reputation: 326

Just write abstract class Record with protected field stampDate, that implements Comparable and override compareTo method.

public abstract class Record implements Comparable<Record> {
    protected Date stampDate;

    @Override
    public int compareTo(Record anotherRecord){
        return this.stampDate.compareTo(anotherRecord.stampDate);
    }
}

Then extend this class with your record classes:

public class AddressRecord extends Record{
...
}

public class CityRecord extends Record{
...
}

public class UserRecord extends Record{
...
}

Upvotes: 1

Masudul
Masudul

Reputation: 21981

Use following Comparator class on List.

class TableRecordCompare implements Comparator<TableRecord>{
     if(TableRecord instanceof AddressRecord){
       // return compareTo for sample data of address.
     }
     else if(TableRecord instanceof CityRecord){
     // return compareTo for sample data of CityRecord.
      }
     else{
     // return compareTo for sample data of UserRecord.
    }

}

Upvotes: 0

Related Questions