How to get two different keys inside a foreach keySet()? - java

I want to print the keys of my HashMap "allDishes".
This HashMap contains an Dish as the value.
The Dish class has a HashMap field named "Ingredients".
I want to print the key of the "allDishes" and the keys of its HashMap "Ingredients".
With the foreach keySet(),
the key for Ingredients is "null",
because there is no value in "Ingredient" like there is in "allDishes".
Is it possible at all to print keys of different HashMaps?
Map<String, Dish> allDishes = (Map<String, Dish>) application.getAttribute("allDishesHashMap");
for (String key : allDishes.keySet()) {
Map <String, String> Ingredient = allDishes.get(key).getIngredients();
out.println("<li><b>" + key + "</b> with: </li>" + Ingredient.get(key));
}

You are doing it wrong.
Currently,
you are iterating through the keys of the allDishes HashMap.
What you want to do is iterate through the keys of the allDishes HashMap and
for each key in the allDishes HashMap,
iterate through the keys of Ingredient HashMap contained within the current dish in the allDishes HashMap.
To do this,
first iterate through the allDishes entrySet,
then iterate through the ingredients keySet for each entry.
Here is some code:
final Map<String, Dish> dishMap = (Map<String, Dish>)application.getAttribute("allDishesHashMap");
for (final Map.Entry dishEntry: dishMap.entrySet())
{
final Map <String, String> ingredientMap = dishEntry.getIngredients();
out.println("<li><strong>" + dishEntry.getKey() + "</strong> Ingredients: <ul>");
for (final String ingredientName : ingredientMap.keySet())
{
out.println("<li>" + ingredientName + "</li>")
}
out.println("</ul></li>");
}

You can print them with nested loops and a null check.
Map<String, Dish> allDishes = (Map<String, Dish>)
application.getAttribute("allDishesHashMap");
for (String dishKey : allDishes.keySet()) {
Map <String, String> ingredients = allDishes.get(dishKey).getIngredients();
System.out.println("Dish Key: " + dishKey);
// check if null here, if necessary
if (ingredients == null) {
continue; // continue, or print something else. whatever you need
}
for (String ingredient : ingredients.keySet()) {
System.out.println("Ingredient Key: " + ingredient);
}
}
You can also print a "keyset" directly like the following if you don't need any special formatting on the keysets.
Map<String, Dish> allDishes = (Map<String, Dish>)
application.getAttribute("allDishesHashMap");
for (String key : allDishes.keySet()) {
Map <String, String> ingredients = allDishes.get(key).getIngredients();
System.out.println("Dish Key: " + key);
// check if null here, if necessary
if (ingredients == null) {
continue; // continue, or print something else. whatever you need
}
System.out.println("Ingredients KeySet: " + ingredients.keySet());
}

Related

How do I build up in a map with one Key with many Values in Java 7

I want to build up a map based on 2 arrays where 1 key has many objects inside it.
Key: "Letter A" Value: "Albatross"
Value: "Alligator"
Key: "Letter B" Value: "Badger"
Value: "Bandicoot"
The structure must show the key 1 time, without repetitions
Hope the code is self explanatory.
Java 7:
public Map<String, List<String>> group(String[] input) {
Map<String, List<String>> result = new HashMap<>();
for (String str : input) {
String key = "Letter " + str.charAt(0);
if (result.containsKey(key)) {
result.get(key).add(str);//if Key already exists, just add this word to existing list.
} else {
List<String> list = new ArrayList<>();
list.add(str);
result.put(key, list); //Otherwise, create a new list and add the new word into the list
}
}
return result;
}
Java 8:
public static Map<String, List<String>> group(String[] input) {
return Arrays.stream(input)
.collect(Collectors.groupingBy(k -> "Letter " + k.charAt(0)));
//Provide the key for how you want to group. In your case it is first character of string.
}
You can use Guava's Mutlimap implementation, however that may not be Java 7 compatible. https://guava.dev/releases/23.0/api/docs/com/google/common/collect/Multimap.html
You can get the same effect by using a List for the values in your map like so:
Map<String, List<String>> map = new HashMap<>();
Then, let's say for each entry you want to add to the map you have the key in key and value in val, add it like so:
List<String> list = map.get(key);
if (list == null) {
list = new ArrayList<>();
map.put(key, list);
}
list.add(val);

How do I iterate over a LinkedHashMap of LinkedHashMaps?

My map looks like this :
LinkedHashMap <LinkedHashMap <String,String>,LinkedHashMap <String,String>> leftRightWords
Where the first map contains left words of a proper noun and second map contains right words of a proper noun. E.g. in :
"Following the Rhode Island solution provider Atrion's decision to
sell"
map1 will have entries like:
Rhode Island, Following the
Atrion, solution provider
map2 will have entries like:
Rhode Island, solution provider
Atrion, decision to sell
In both maps the keys are the same but the values differ based on left and right words. How do i iterate over this map to extract the left words and right words to analyze them?
You can use a nested forEach loop to extract the data you desire, like so:
for(LinkedHapMap<String, String> lhm: leftRightWords.keySet()){
for(String k:lhm.keySet()){
String left = lhm.get(k);
String right = leftRightWords.get(lhm).get(k);
//do something with these Strings
}
}
You can do it this way:
Iterator<LinkedHashMap<String, String>> resultKeys = leftRightWords
.keySet().iterator();
while (resultKeys.hasNext()) {
LinkedHashMap<String, String> tempKey = resultKeys.next();
LinkedHashMap<String, String> tempVal = leftRightWords.get(tempKey);
System.out.println("Key:");
for (Map.Entry<String, String> entry : tempKey.entrySet()) {
System.out.println(entry.getKey() + " "
+ entry.getValue());
}
System.out.println();
System.out.println("Value:");
for (Map.Entry<String, String> entry : tempVal.entrySet()) {
System.out.println(entry.getKey() + " "
+ entry.getValue());
System.out.println();
}
}

Get the key and value of Map that is used Inside another Map (JAVA)

I am using a map inside another map, The key of the outer map is Integer and the value is another Map. I get the values as expected but I don't know how to get the key and value of teh inner map.
Here is the code
Map<Integer, Map<Integer, Integer>> cellsMap = new HashMap<Integer, Map<Integer, Integer>>();
Map<Integer , Integer> bandForCell = cellsMap.get(band_number);
if (bandForCell == null)
bandForCell = new HashMap<Integer, Integer>();
bandForCell.put(erfcn, cell_found);
cellsMap.put(band_number, bandForCell);
csv.writeCells((Map<Integer, Map<Integer, Integer>>) cellsMap);
public void writeCells (Map<Integer, Map<Integer, Integer>> cellsMap ) throws IOException
{
for (Map.Entry<Integer, Map<Integer, Integer>> entry : cellsMap.entrySet()) {
System.out.println("Key: " + entry.getKey() + ". Value: " + entry.getValue() + "\n");
}
}
Out put of my Map
Key: 20 Value: {6331=0, 6330=1, 6329=1, 6328=0, 6335=1, 6437=0, 6436=1}
The value in the above output is another map.
How can I get the key and value of the inner map from the value of the outer map?
Like Keys of inner map = 6331, 6330, 6329 ....
and values of inner map = 0 , 1 , 1 , 0 ...
Thanks
This worked for me , Hope it will help someone else in future
for (Map.Entry<Integer, Map<Integer, Integer>> outer : cellsMap.entrySet()) {
System.out.println("Key: " + outer.getKey() + "\n");
for (Map.Entry<Integer, Integer> inner : entry.getValue().entrySet()) {
System.out.println("Key = " + inner.getKey() + ", Value = " + inner.getValue());
}
}
In order to get a reference to an inner map, you would just use cellsMap.get(key). I'm not sure exactly what you want to do, but, for example, if you wanted to get the value where the first key was i and the second key was j, you could get it using cellsMap.get(i).get(j)
Or, if you wanted to print out all the keys and values of the inner map at index i, you could use
for (Map.Entry> entry : cellsMap.get(i).entrySet()) {
System.out.println("Key: " + entry.getKey() + ". Value: " + entry.getValue() + "\n");
}

Get Key value from iterator

I have a HashMap, which contains another HashMap. I want to iterate over the first HashMap and use the Key values from that. Then, as I iterate over the first HashMap I want to start an inner loop iterating over the second HashMap, getting all the values.
The problem I have so far is that I can't figure out how to get the keys from the Iterator.
HashMap<String, HashMap<Integer, String>> subitems = myHashMap.get("mainitem1");
Collection c = subitems.values();
Iterator itr = c.iterator();
while(itr.hasNext())
{
// Get key somehow? itr.getKey() ???
// contains the sub items
HashMap productitem = (HashMap)itr.next();
}
The data that i get from subitems is this:
{Item1{0=sub1, 1=sub2}, Item2{0=sub3, 1=sub4}}
Then, in the while loop productitem contains the 'sub items'. But i can't find out where i can get the key value 'Item1' and 'Item2' from.
How can i get those?
You can't get the key from values().iterator().
You need to use entrySet().iterator(). That will return Map.Entry<K,V> objects on which you can call getKey() and getValue().
for (Map.Entry<Integer,Key> entry : subitems.keySet()) {
Integer key = entry.getKey();
String value = entry.getValue();
// do stuff
}
I'd also like to add that having deeply nested maps of lists of maps is usually a sign that you really want to write custom classes to hold your data. Especially when the maps have pre-defined keys to be used and interpretation of the values in the lists depends on the position within the list! I call this code smell "object denial".
You can't go from value to key in a map. (There may be several keys mapping to the same value!)
You can iterate over the map entries though using subitems.entrySet().iterator(), or you can iterate over the keys, and in each iteration retrieve the associated value through subitems.get(key).
You could do something like this (using iterators):
Set<Entry<String, HashMap<Integer, String>>> c = subitems.entrySet();
Iterator<Entry<String, HashMap<Integer, String>>> iterator = c.iterator();
while(iterator.hasNext())
{
Entry<String, HashMap<Integer, String>> entry = iterator.next();
System.out.println("key:" + entry.getKey());
HashMap<Integer, String> innerMap = entry.getValue();
if (innerMap == null) {
continue;
}
Iterator<Entry<Integer, String>> innerIterator = innerMap.entrySet().iterator();
while (innerIterator.hasNext()) {
Entry<Integer, String> innerEntry = innerIterator.next();
System.out.println("key:" + innerEntry.getKey() + " value: " + innerEntry.getValue());
}
}
or like this using foreach structure:
for (Entry<String, HashMap<Integer,String>> entry : subitems.entrySet())
{
System.out.println("key:" + entry.getKey());
HashMap<Integer, String> innerMap = entry.getValue();
if (innerMap == null) {
continue;
}
for (Entry<Integer, String> innerEntry : innerMap.entrySet())
System.out.println("key:" + innerEntry.getKey() + " value: " + innerEntry.getValue());
}
}
java Collections provide facility of EntrySet. This is a list of objects which contain individual keys and values as its properties. You can take a iterator out of this list.
You can get keys as follows.
Iterator i= subitems.entrySet().iterator();
while(i.hasNext()){
String key= i.next().getkey();
}
You can iterate over entries using entrySet().iterator() on the first HashMap or get the keys and iterate over them: Instead of subitems.values().iterator() use subitems.keys().iterator() and use the next key to get the inner hashmap.

Java Iteration over a keySet

I have the following Java code:
public void myMethod (final Map pFeatureGroupsFromPackage) {
final Set<String> keys = pFeatureGroupsFromPackage.keySet();
for (final String key : keys) {
tmpList = (List<FeatureKey>) pFeatureGroupsFromPackage.get(key);
// do whatever
}
}
I am getting a warning from "findBugs" telling the following:
Method myMethod makes inefficient use of keySet iterator instead of entrySet iterator.
The warning is done at the tmpListassignment.
I do not understand why this is inefficient. In fact the keyslist is computed only once.
Any comment? Thanks.
Instead of iterating over the keySet and calling get to get the corresponding value for each key, iterate over the entrySet:
final Set<Map.Entry<String, List<FeatureKey>>> entries = pFeatureGroupsFromPackage.entrySet();
for (Map.Entry<String, List<FeatureKey>> entry : entries) {
String key = entry.getKey();
List<FeatureKey> tmpList = entry.getValue();
// do whatever
}
That way you don't have to do a lookup in the map for every key; you directly get the key and value in one go.
Also, declare your Map with type parameters:
public void myMethod (final Map<String, List<FeatureKey>> pFeatureGroupsFromPackage) {
// ...
}
you're getting all the keys and then you search for every key in the collection
a Map.EntrySet iteration would be much faster, a small example:
But you also should use generics...
Set entries = map.entrySet();
Iterator entryIter = entries.iterator();
System.out.println("The map contains the following associations:");
while (entryIter.hasNext()) {
Map.Entry entry = (Map.Entry)entryIter.next();
Object key = entry.getKey(); // Get the key from the entry.
Object value = entry.getValue(); // Get the value.
System.out.println( " (" + key + "," + value + ")" );
}
This could help you:
Map map = new HashMap();
Iterator entries = map.entrySet().iterator();
while (entries.hasNext()) {
Map.Entry entry = (Map.Entry) entries.next();
Integer key = (Integer)entry.getKey();
Integer value = (Integer)entry.getValue();
System.out.println("Key = " + key + ", Value = " + value);
}
Sample code:
for (Map.Entry < Integer, List < FeatureKey >>> i: map.entrySet()) {
System.out.println(i.getValue() + " " + i.getKey()));
}
It could be that you are querying the map twice:
first for the keys,
and second for the values
Using entryset iterator will iterate over the map once.
Accessing the HashMap via keySet iterator is even faster than using the keySet iterator on the TreeMap.
Hey Luixv,
The reason using keysey iterator is less effective than entryset iteratot is that with the first option you still have to use the Map.get(key) lookeup which is avoided with the second option.

Categories

Resources