Yashaswi Bhardwaj
Yashaswi Bhardwaj

Reputation: 85

HashMap function keyset() in java

HashMap<Character,Character> h=new HashMap<>();
for(int i=0; i<str.length(); i++){
    h.put(str.charAt(i),str.charAt(i));
}
Set<Character> keys=h.keySet();

Character [] arr=new Character[keys.size()];

keys.toArray(arr);
String ans="";
for(int i=0; i<arr.length; i++) {
    ans+=arr[i];
}

In this question I have to remove duplicates from the string entered.It works fine for normal characters but when input is like: o&6nQ0DT$3 i.e. containing special characters then it does not get printed in order.

input: o&6nQ0DT$3
expected output: o&6nQ0DT$3 
my output: 0Q3DT$&6no

I am getting the value returned by keyset() method in a set "keys" (because return type is set internally of keyset()) after that I created an array of length keys and put the string into it for returning. But its coming in different order.

Upvotes: 2

Views: 1109

Answers (5)

Bruno Silva
Bruno Silva

Reputation: 63

can it be done without HashMap?

    String str = "Teste";
    String finalStr = ""; 

    for (Character charInString: str.toCharArray()) {
        if(!finalStr.contains(charInString.toString()))
        {
            finalStr += charInString;
        }

    }
    System.out.println(finalStr);

Improving, what about it? A Workaround with TreeSet.

    String str = "teste";
    HashMap<Integer, Character> map = new HashMap<>();
    for (int i = 0; i < str.length(); i++) {
        if (!map.containsValue(str.charAt(i))) {
            map.put(i, str.charAt(i));
        }
    }
    SortedSet<Integer> keys = new TreeSet<Integer>(map.keySet());
    keys.forEach(k -> System.out.println(k + " value " + map.get(k).toString()));

Upvotes: 1

vijayraj34
vijayraj34

Reputation: 2415

LinkedHashMap & LinkedHashSet maintains the insertion order.

String s = "o&6nQ0DT$3";
Map<Character,Character> hm = new LinkedHashMap<>();    
for(Character c:s.toCharArray())
    hm.put(c, c);
System.out.println(hm);

Output :

{o=o, &=&, 6=6, n=n, Q=Q, 0=0, D=D, T=T, $=$, 3=3}

But LinkedHashSet internally uses hashmap to store the values, so the performance will be slightly better in LinkedHashMap.

Upvotes: 1

I don't see how are you fully using a hashmap, perhaps you would like to replace with a ArrayList, like this:

ArrayList<Character> h = new ArrayList<>();
for(int i=0;i<str.length();i++)
{
   if(!h.contains(str.charAt(i)))
      h.add(str.charAt(i));
   }
...

An arraylist will keep the same order of insertion too.

Upvotes: 0

Mureinik
Mureinik

Reputation: 311228

A HashMap (or HashSet, for that matter) has no intrinsic order. The fact that this worked for some inputs is just a lucky stroke. You could use a LinkedHashMap, as @javaguy suggests, or it may be easier to implement this entire exercise using streams:

String input =  "o&6nQ0DT$3";
String output = input.chars()
                     .distinct()
                     .mapToObj(c -> String.valueOf((char) c))
                     .collect(Collectors.joining());

Upvotes: 3

Vasu
Vasu

Reputation: 22422

HashMap does not guarantee/retain the insertion order of the elements, so use LinkedHashMap to preserve the order of the characters you are inserting:

Map<Character,Character> h = new LinkedHashMap<>();//use LinkedHashMap

Upvotes: 1

Related Questions