Mukund Jalan
Mukund Jalan

Reputation: 1339

Ordering for key value pairs

I have the following two classes:

class KeyClass {
    private prop1;
    private prop2;

    hashcode() {
    //implemented properly
    }

    equals() {
    //implemented properly
    }
}

class ValueClass {
    private prop1;
    private prop2;

    hashcode() {
    //implemented properly
    }

    equals() {
    //implemented properly
    }
}

I am trying to find out the max pair from a map where objects of these classes are key and value pairs respectively. I also have an com.google.common.collect.Ordering<ValueClass> which uses multiple comparators. I can easily find out the max of values using this ordering, but what I am interested into is the key of the max value.

I can write a certain implementation wherein I can keep track of my key w.r.t the value in a loop and use the ordering to compare values (similar to the conventional way of finding a max value) but I want to know if we already have such case handled by Guava or any other library?

Upvotes: 5

Views: 272

Answers (3)

Manos Nikolaidis
Manos Nikolaidis

Reputation: 22234

You say guava or any other library and that's straightforward with Java 8 streams. If your Ordering<ValueClass> instance is called ordering:

Entry<KeyClass, ValueClass> maxEntry = map.entrySet().stream()
        .max(Comparator.comparing(Entry::getValue, ordering))
        .orElse(null);

Add .map(Entry::getKey) before orElse to get just the key.

The above is possible since guava's Ordering implements java.util.Comparator so you can pass it as argument to comparing.

Upvotes: 5

Hasnain Ali Bohra
Hasnain Ali Bohra

Reputation: 2180

yes. using the Bidi Map :- Bidi Map

Download jar

How to use.

Example:-

BidiMap bidiMap = new DualHashBidiMap( );
bidiMap.put( "il", "Illinois" );
bidiMap.put( "az", "Arizona" );
bidiMap.put( "va", "Virginia" );
// Retrieve the key with a value via the inverse map
String vaAbbreviation = bidiMap.inverseBidiMap( ).get( "Virginia" );

// Retrieve the value from the key
String illinoisName = bidiMap.get( "il" );

Using the same approach you just need to implement the hascode() and equals() contract of a Map. Solution :-

  1. we know that HashCode is used to Store in Bucket. Assume hashcode as row number in 2-D matrix and each Row has the linked List of entry[key,value].

  2. implement the hashcode() such that for each entry[key,value] you will get different `bucket no(row no).

  3. Implement equals() method to check the equality in each bucket's entry[key,value].

  4. Complexity :- if you assign each entry[key, value] to the different bucket then SEARCHING and ADDING complexity will be o(1).

  5. please refer the below documents for better understanding of solution:-doc1 doc2

Upvotes: 1

Jacob G.
Jacob G.

Reputation: 29690

I recommend you do the following:

Change your com.google.common.collect.Ordering<ValueClass> to com.google.common.collect.Ordering<Map.Entry<KeyClass, ValueClass>> and modify the multiple Comparator<ValueClass> that are used to use Map.Entry#getValue instead.

Thus, the maximum ValueClass will be equivalent to the maximum Map.Entry<KeyClass, ValueClass>.

I can easily find out the max of values using this ordering, but what I am interested into is the key of the max value.

Now, you can simply use Map.Entry#getKey to grab the key of the maximum value/entry.

Upvotes: 1

Related Questions