Looping to enter values into Java Hashmap - java

i am trying to insert values into a hashmap. I have it in a loop as the values are being retrieved from a list of strings. The code is as follows:
HashMap<String, String> resultHashMap = new HashMap<String, String>();
//add the top document id back to the resultHashMap
resultHashMap.put("entryObject", dsStepParam.getValue());
for(String res : results)
{
log.info(res);
resultHashMap.put("dataObject", res);
}
The hashMap (after this loop should contain the following:
{"entryObject":"500386787",
"dataObject":"500386883;500901929",
"dataObject":"500386906;500901969",
"dataObject":"500386787;500901666",
"dataObject":"500386784;500901654",
"dataObject":"500386762;500901599"}
however the actual contents are:
{"entryObject":"500386787",
"dataObject":"500386762;500901599"}
As you can see it only stores the entryObject and the last dataObject.
How can I make it store all the values in the hashMap?

It only stores the last entry because duplicate keys are not allowed in a hashmap. To store all elements you could do something like this
int count = 0;
for(String res : results)
{
log.info(res);
resultHashMap.put("dataObject-"+count, res);
count++;
}
Thus you'd get something like this
{"entryObject":"500386787",
"dataObject-1":"500386883;500901929",
"dataObject-2":"500386906;500901969",
"dataObject-3":"500386787;500901666",
"dataObject-4":"500386784;500901654",
"dataObject-5":"500386762;500901599"}

If you want it to store all values in the hashMap you need to allow duplicates in the map. For this to happen, you'd need to use Google's version of Multimap, which can be found here

The keys in hashMap are unique so you are seeing the last entry for the duplicate keys inserts. If you want to store multiple items associated to one key then you can make use MultiMap i.e a map that holds a collection of values against each key. Couple of good multimap implementations are available:
Apache MultiMap
Guava MultiMap

Related

Go through multiple hashmaps of different sizes to extract values with common keys

So I essentially want to go through all the elements in the arraylist and match it with the keys of each hashmap and for the values of the common keys I want to make a new arraylist.
Essentially if keygrades is on value 1, I want to check every hashmap with the key 1 and then extract all the values associated with that key and make a brand new arraylist with those values.
ArrayList <String> keygrades = new ArrayList<>();
HashMap <String,String> gradeA = new HashMap<>();
HashMap <String,String> gradeB = new HashMap<>();
HashMap <String,String> gradeC = new HashMap<>();
HashMap <String,String> gradeD = new HashMap<>();
This is what is in the hashmap:
keygrades = [1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20]
gradeA = {11=134, 1=100, 3=110, 4=120, 15=142, 5=130}
gradeB = {2=102, 3=103, 6=108, 8=109}
gradeC = {3=104, 5=105, 6=111}
gradeD = {3=122, 4=123}
For example for key 1 I want a new arraylist which would be (100,"","","") ""= empty string. For key 2 I want a new arraylist which would be ("",102,"","").It would continue going through hashmaps in order and inputting into new arraylist each time.
I recommend writing a method with this struture:
Create an ArrayList<ArrayList>, which will hold the outcoming
ArrayLists containing the different values for common keys.
Iterate over Arraylist containing the keys.
Create an ArrayList that will get the 4 values.
Check all 4 Hashmaps with the current key using HashMap.get(key).
If the outcome is null, you should add "" to your ArrayList, otherwise you
enter the value to the ArrayList inside the loop.
After it iterated through the ArrayList containing the keys. You should have an
ArrayList<ArrayList> holding exactly as much ArrayList containing the values for similar keys, as you ArrayList of keys size.
You can achieve this by transforming your maps into a stream of maps and extracting the values for a particular key.
List<String> values = Stream.of(gradeA,
gradeB,
gradeC,
gradeD)
.map(map -> map.getOrDefault("1", ""))
.collect(Collectors.toList());
To reuse this, you'll have to create a function that handles the combining of the maps and a function that extracts values from that stream of maps.
The example should get you on your way.

Create multiple Lists from one (Group List's Objects by a specific field)

Given that I have the array of :
List<CustEnt> bulkList= CustRepo.fetchData();
//System.out.println(bulkList) -->
gives me :
CustEct(name:"kasis",age:24,surname:"kumar"),CustEct(name:"samika",age:50,surname:"sharma"),CustEct(name:"manoj",age:84surname:"kumar")
OR
bulkList.get(1) --> CustEct(name:"kasis",age:24,surname:"kumar")
I want to create a new array which is grouped by the 3rd parameter of surname object.
So that my array becomes
ArrayFinal = [CustEct(name:"kasis",age:24,surname:"kumar"),CustEct(name:"samika",age:50,surname:"sharma")],CustEct(name:"manoj",age:84surname:"kumar")
So that when we do .get(1) we would get object of kasis and samika.
Need the help in respective to java 8.
I heard that we can use the Map ,but can anyone give the small code sample or any other implementation guide.
A Map tracks key-value pairs.
Your key is the surname string.
Your value is a list of the CustEnt objects carrying that surname.
Map<String, List<CustEnt>>
Modern syntax with streams and lambdas makes for brief code to place your objects in a map.
Something like:
Map<String, List<CustEnt>> map = originalList.stream.collect(Collectors.groupingBy(CustEnt::getSurename));
Map<String, List<CustEntity>> NamesList
= bulkList.stream()
.collect(Collectors.groupingBy(CustEntity::getSurames));
for (Map.Entry<String, List<CustEntity>> entry: NamesList.entrySet()) {
ExcelGenerationService exp = new ExcelGenerationService( entry.getValue());
//service call
exp.export(entry.getKey());
}

java- hashmap one key and multiple values alternative to storing the value part in a List

Usually when you have multiple values for the same key in hash map the answers I have found would use a List or ArrayList to store the value part. For example:
Map<Object,ArrayList<Object>> multiMap = new HashMap<Object,ArrayList<Object>>();
I was wondering it was possible to keep the normal definition of hashmap and append any new values to the old value (comma separated). Something like this:
Map<String, String> memOf = new HashMap<String, String>();
Map<String, String> subOrg = new HashMap<String, String>();
Map<String, String> email = new HashMap<String, String>();
String line="";
String source="";
String sub="";
String obj="";
String hashKey="";
String hashVal="";
for (Text value : values){ //start iterate over values
line=value.toString();
String[] parts=line.trim().split(",");
source=parts[0].trim();
sub=parts[1].trim();
obj=parts[2].trim();
hashKey=sub;
if (source.equals("memberOf")){
hashVal=memOf.get(hashKey);
if (hashVal!=null){
hashVal=hashVal+","+obj;
memOf.put(hashKey, hashVal);
}
}
}
The previous code is to populate the hashmaps and next to read individual values use split(",")and store them in a String array. something like:
for (String key1 : memOf.keySet()) {
x=key1;
String[] y=memOf.get(x).toString().split(",");
int numberOfItems = y.length;
for (int i=0; i<numberOfItems; i++){
System.out.println(y[i]);
}
}
I was wondering it was possible to keep the normal definition of hashmap and append any new values to the old value (comma separated).
You already did it. In an inefficient manner, but you did it.
As pointed out by Andy Turner in the comments, you may look for implementations like Guava's MultiMap which allows to map a single key to multiple values.
Aside from that, the official Map documentation does not report such capabilities of adding one value to another, only replacing it. In the case of Integers, you can increment them pretty easily, but for the rest you'll have to either do it yourself or find a more efficient way (e.g. an ArrayList).

How do I store this data in Java?

I want a dictionary of values. The keys are all strings. Each key corresponds with some sort of list of strings. How do I make a list of strings for each key and update that accordingly? I'll explain:
I have a loop that is reading lines of a word list. The words are then converted into a string code and set as keys in the dictionary. Here is an example of the string code/word relationship.
123, [the]
456, [dog]
328, [bug]
...
However, my program keeps looping through the word list and eventually will run into a word with the same code as "the", but maybe a different word, lets say "cat". So I want the list to look like:
123, [the, cat]
456, [dog]
...
How do I get it to make an arraylist for every key that I can then add to on the fly when needed? My end goal is to be able to print out the list of words in that list for a called code (.get())
You can make a HashMap. In your case
HashMap<Integer, ArrayList<String>> works fine.
Like it has already been said, a MultiMap seems to be what you need. Guava that was already suggested and it's a good option. There is also and implementation from commons-collections you can use.
From commons-collections documentation:
MultiValuedMap<K, String> map = new MultiValuedHashMap<K, String>();
map.put(key, "A");
map.put(key, "B");
map.put(key, "C");
Collection<String> coll = map.get(key); // returns ["A", "B", "C"]
You can always implement your own MultiMap if you don't want to use an external library. Use a HashMap<String,List<String>> to store your values and wrap it with your own put, get and whatever other methods you see fit.
It sounds like you want a Multimap from the Guava library.
You can also go the route of using a Map<Integer, List<String>>, but then you will need to manually handle the case where the list is null (probably just allocate a new list in that case).
You can use a HashMap that links each id to a list of strings:
Map<String, List<String>> dictionary = new HashMap<String,List<String>>();
Now let's say you read two Strings: id and word . To add them to your dictionary, you can first verify if your id has already been read (using the containsKey() method)- in which case you just append the word to the list corresponding to that id - or, if this is not the case, you create a new list with this word:
//If the list already exists...
if(dictionary.containsKey(id)) {
List<String> appended = dictionary.get(id);
appended.add(word); //We add a new word to our current list
dictionary.remove(id); //We update the map by first removing the old list
dictionary.put(id, appended); //and then appending the new one
} else {
//Otherwise we create a new list for that id
List<String> newList = new ArrayList<String>();
newList.add(word);
dictionary.put(id, newList);
}
Then whenever you want to retrieve your list of strings for a certain id you can simply use dictionary.get(id);
You can find more information on HashMaps on the Java documentation
I assumed you didn't want repeats in your list so I used Set instead.
Map<String,Set<String>> mapToSet = new HashMap<>();
List<String []>keyvals = Arrays.asList(new String[][]{{"123","the"},{"123","cat"}});
for(String kv[] : keyvals) {
Set<String> s = mapToSet.get(kv[0]);
if(null == s) {
s = new HashSet<String>();
}
s.add(kv[1]);
mapToSet.put(kv[0], s);
}

HashMap overrides the nextvalue Java

Lets say I have hashmap store and it contains for example-(11,name1) (11,name2) and i call HashMap.get(11), it only shows name2 which means it overrides the first input for 11. How can i store both name1 and name2 with ID 11 using hashmap?I know i can use both HashMap and HashSet but i dont want to create every HashSet for HashMap. I just want to use hashSet only. how should I do this? I hope you can help me with it. Thank you.
public void insert(int ID, String key){
int hashKey = Hash(key);
System.out.println("Hash Key" + hashKey);
int node = Find(ID,hashKey);
storeR.put(node, key);
}
You can use:
HashMap<Integer, List<String>>
In HashMap you must put a value with every key. So of course, if you put the same key twice, the value will be override.
The solution is to hold a collection of values for every key.
in your code instead of:
storeR.put(node, key);
you should write:
List<String> nodeValues = storeR.get(node);
if (nodeValues == null) {
nodeValues = new ArrayList<String>();
storeR.put(node, nodeValues );
}
nodeValues.add(key);
And you should also change storeR type to be HashMap<Integer, List<String>>
MultiMap is also a similar solution.
You can probably use MultiMap from Apache Commons Collections.
You will have to either have a HashMap where the value of each key is another collection (list or set) or concatenate the string values together (e.g. comma separated).
Alternatively you may be able to find a data collection that supports multiple values per key.
To store multiple values for a single key, use a HashMap that contains a list as a value. HashMap's implementation overrides values for existing keys.
HashMap<Integer,List<String>>
Also, you could use MultiMap from Apache Commons or, if you're just using Integer I can suggest you use an array directly:
List<String>[] yourList = new List<String>[initCapacity];
So you can access that list like this:
yourList[0].add("A New Value");
As a final note, you can use any collection you deem appropiate, even a HashSet if performance is important for you and you won't store duplicated values for a same index.

Categories

Resources