Akash Lanjewar
Akash Lanjewar

Reputation: 39

In hashmap how to assign previous key to the next if duplicate values are exist

Ii'm trying to assigning the previous key to the next in case of duplicate are present in hashmap.

for example, duplicate entries in hashmap:

5-->51  
6-->51

I want output as below:

5-->51  
5-->51

Below is my code:

HashMap<Integer, Integer> map = new HashMap();
    map.put(1, 99);
    map.put(2, 120);
    map.put(3, 89);
    map.put(4, 71);
    map.put(5, 51);
    map.put(6, 51);
    map.put(7, 77);
    map.put(8, 44);
    map.put(9, 22);
    Set set = new HashSet<>();
    List list = new ArrayList<>();
    for (Entry<Integer, Integer> mapVal : map.entrySet()) {
        if (!set.add(mapVal.getValue())) {
            list.add(mapVal.getValue());
        } else {
            set.add(mapVal.getValue());
        }
    }
    for (Entry<Integer, Integer> mapVal : map.entrySet()) {
        if (list.contains(mapVal.getValue())) {
            System.out.println(mapVal.getKey() + "-->" + mapVal.getValue());
        }
    }

Would it be possible in hashmap case? If so, what algorithm or code should I use?

Upvotes: 2

Views: 160

Answers (3)

marknorkin
marknorkin

Reputation: 4084

As pointed out by @AliOmar62 you can not have duplicate keys in map.

What you can do is inverse key with value and collect all values to collection e.g.

    Map<Integer, List<Integer>> sameValueToDiffKeys = map.entrySet()
            .stream()
            .map(e -> new SimpleImmutableEntry<>(e.getValue(), e.getKey()))
            .collect(Collectors.toMap(SimpleImmutableEntry::getKey, e -> new ArrayList<>(Collections.singleton(e.getValue())), (first, second) -> {
                first.addAll(second);
                return first;
            }));

The output with your data will look in console like:

{51=[5, 6], 99=[1], 22=[9], 71=[4], 120=[2], 89=[3], 44=[8], 77=[7]}

Please take a look at merge function, which is the third argument to Collectors.toMap.

This function resolves all duplications for one key by merging them into one collection.

Upvotes: 0

davidxxx
davidxxx

Reputation: 131436

i want output as below:

5-->51
5-->51

You could not get such a thing with a Map as keys are unique.

As workaround to get that result in the output, you should use a Map implementation that maintains the insertion order of the elements: LinkedHashMap.
HashMap doesn't maintain it.

Then the idea is rather simple :

  • Create a list from map keys and create another list from map values.
  • Iterate values list and update elements of the keys list which the value associated contains a value already encountered.
  • output the lists

Here is a sample code :

public class Foo {

    public static void main(String[] args) {

        HashMap<Integer, Integer> map = new LinkedHashMap<>();
        map.put(1, 99);
        map.put(2, 120);
        map.put(3, 89);
        map.put(4, 71);
        map.put(5, 51); // 51 value
        map.put(6, 51); // 51 value
        map.put(7, 77);
        map.put(8, 51); // 51 value
        map.put(9, 22);

        List<Integer> keys = new ArrayList<>(map.keySet());
        List<Integer> values = new ArrayList<>(map.values());

        Set<Integer> valuesWithKeyUpdated = new HashSet<>();
        for (int i = 0; i < values.size() - 1; i++) {

            final Integer oldestKeyForCurrentValue = keys.get(i);
            final Integer currentValue = values.get(i);

            if (valuesWithKeyUpdated.contains(currentValue)) {
                continue;
            }

            for (int j = 1; j < values.size(); j++) {
                if (currentValue == values.get(j)) {
                    keys.set(j, oldestKeyForCurrentValue);
                }
            }

            valuesWithKeyUpdated.add(values.get(i));
        }


        for (int i = 0; i < keys.size(); i++) {
            System.out.println("key=" + keys.get(i) + ", value="+ values.get(i));

        }
    }
}

key=1, value=99

key=2, value=120

key=3, value=89

key=4, value=71

key=5, value=51 // value 51 with key 5 in the original map

key=5, value=51 // value 51 : display 5 instead of 6

key=7, value=77

key=5, value=51 // value 51 : display 5 instead of 8

key=9, value=22

Upvotes: 1

AliOmar62
AliOmar62

Reputation: 55

If I got your question right. It's not possible to have duplicate keys in a map whichever map it is. You want for two value same key which isn't possible.

Upvotes: 3

Related Questions