0

I created a generic collection class called Pair

public class Pair<L,R> {
private L l;
private R r;

public Pair(L l, R r){
    this.l = l;
    this.r = r;
}
public L getL(){
    return l;
}
public R getR(){
    return r;
}
public void setL(L l){
    this.l = l;
}
public void setR(R r){
    this.r = r;
}
}

I want to then create a Vector named records of type

Pair<String, int>

so that I can later iterate through the vector and compare the int values at different indexes of the vector. I did this through the following code:

private Vector<Pair<String, Long>> records = new Vector();

And then want to compare the int values at different indexes in a sorting function

public void sort(){
    int n = records.size();
    int p = 0;
    int i, j;

    for(p = 0; p < n-1; p++){
        j = p;
        for(i = p+1; i<n; i++){
            if(records.get(i) < records.get(j))
                j = i;
        }   
    }
}

I'm getting an error in the If statement, saying that the operator is undefined for argument types. If anyone has any idea how to resolve this, please let me know. Thanks in advance

Johnny
  • 105
  • 1
  • 13
  • 2
    Given the type of records, what will `records.get(i)` give you? – Rohit Jain Mar 08 '15 at 08:52
  • Using `<` operator, you can compare only primitives. Here you should implement `Comparable` interface to compare your objects by some natural order and use `if (records.get(i).compareTo(records.get(j)) < 0)` to compare them. – Alex Salauyou Mar 08 '15 at 08:58
  • Just asking, why not use `Map` (`HashMap`) and `Map.Entry` http://stackoverflow.com/questions/8689725/map-entry-how-to-use-it ? – EpicPandaForce Mar 08 '15 at 09:36

1 Answers1

0

Though there are no overloaded operators in Java, you cannot compare objects using >. You should implement Comparable interface and use its compareTo() method:

public class Pair<L, R> implements Comparable<Pair<L, R>> {
    private L l;
    private R r;

    // ... remaining part ...

    @Override
    public int compareTo(Pair p) {
         // e.g. comparison by length of `toString` representation
         return (toString().length() - p.toString().length());
    }

}

Now, compare your objects using Pair#compareTo:

for(p = 0; p < n-1; p++){
    j = p;
    for(i = p+1; i<n; i++) {
        // compare your object by natural order
        if(records.get(i).compareTo(records.get(j)) < 0)
            j = i;
    }   
}

To compare your Pair objects by some meaningful value you should implement more sophisticated logic of compareTo() method--since on design time you cannot know which types are L and R, for compiler they are objects of no specific type.

To solve this issue, you can explicitly define these types comparable:

class Pair<L extends Comparable<L>, R extends Comparable<R>> implements Comparable<Pair<L, R>> {
    //...
} 

and implement Pair#compareTo() using L#compareTo() or/and R#compareTo() methods.

Both String and Long implement Comparable so they can be used as types for such class.

Another way is to implement your Pair class holding no-generic-typed int(long) value as a property, like Pair<T> with constructor Pair(T t, int length).

Alex Salauyou
  • 14,185
  • 5
  • 45
  • 67