0

I want to "print" a Hashmap<String, Integer> (let's say Alpha) in a Hashmap<String, Hashmap<String, Integer>> (Beta) and I say "print" because I don't want the "printed" Alpha to change when I re-use Alpha.

For example:

class scratch_2 {
    public static void main(String[] args) {
        HashMap<String, Integer> Alpha = new HashMap<>();
        HashMap<String, HashMap<String, Integer>> Beta = new HashMap<>();
        Beta.put("A1", Alpha);
        Beta.put("B2", Alpha);
        Alpha.put("A", 1);
        Alpha.put("B", 2);

        System.out.println(Beta); --->print1

        Alpha.clear();

        System.out.println(Beta); ---->print2
    }
}

Result of print1: {A1={A=1, B=2}, B2={A=1, B=2}}
Result of print2: {A1={}, B2={}}

How to set the Beta.put() so that when Alpha is cleared, Beta remains the same?

SemAntys
  • 316
  • 2
  • 15
  • What do you mean by 'cleared'? To remove Alpha values you are changing Beta's values so likely you'll need to go through each Beta and insert the null for the Alpha that no longer exists. – April_Nara Aug 31 '18 at 20:12
  • Java uses pointers for instances of classes so Beta doesnt contain copy of Alpha, it contains Alpha, reference to Alpha, if you want to copy Alpha inside Beta, you have to clone Alpha, try using .clone() method. – agilob Aug 31 '18 at 20:12
  • 1
    *"I don't want the "printed" Alpha to change when I re-use Alpha"* Then don't *reuse* Alpha. Create another instance. – Andreas Aug 31 '18 at 20:15
  • @agilob I should create a new HashMap which is the clone of Alpha, and then put it in Beta? – SemAntys Aug 31 '18 at 20:15
  • Variant of [Why does my ArrayList contain N copies of the last item added to the list?](https://stackoverflow.com/q/19843506/5221149) – Andreas Aug 31 '18 at 20:16
  • @Andreas But I need Alpha to be a Hashmap accessible through the entire activity – SemAntys Aug 31 '18 at 20:17
  • 1
    If you only have one instance, then any changes *will* be seen by all other references to that one and only instance. At what point in time do you want the instance referenced by `"A1"`, and the instance referenced by `"B2"`, to no longer "see" changes to the instance referenced by `Alpha`? --- When they are inserted into `Beta`? Then they will both be empty, because `Alpha` doesn't have any content until later. --- Right before you call `clear()`? Then replace `Alpha.clear()` with `Alpha = new HashMap<>();` – Andreas Aug 31 '18 at 20:21
  • @Andreas If I understood you, at the moment I declare Alpha as a new HashMap, all the previous "uses" of Alpha become independent of it? – SemAntys Aug 31 '18 at 20:29
  • That is correct, except `Alpha = new HashMap<>();` is not a *declaration*, it's an *assignment*. `HashMap Alpha` is a declaration. `HashMap Alpha = new HashMap<>();` is a *declaration with initializer*, aka a combined declaration and assignment. – Andreas Aug 31 '18 at 20:30
  • @Andreas Ok! Thank you very much for your help and your time! – SemAntys Aug 31 '18 at 20:32

2 Answers2

0

Here is what you can do to reset a nested HashMap. The value is removed on line 22 and then added back as a new inner hashmap instance. Again, I loop through containingMap and the innerMap getting each map. Once I have a value to reset I call the reset function.

import java.util.*;
import java.lang.*;

public class Collections {

public HashMap<String, HashMap<String, Integer>> 
 createMap(String beta, String alpha, int m, HashMap<String, 
 Integer> innerStructure, HashMap<String, HashMap<String, 
  Integer>> containingStructure) {
    while(m>0) {
        innerStructure.put(beta, m);
        m--;
    }
    containingStructure.put(alpha, innerStructure); 
    return containingStructure;
}

public void reset(HashMap<String, HashMap<String, Integer>> 
map, int x) {
    HashMap<String, Integer> betaMap = new HashMap<String, Integer>();
    for(Map.Entry<String,HashMap<String,Integer>> entry: map.entrySet()) {
        System.out.println("Key before is:" + entry.getKey());
        if(entry.getValue() instanceof Map) {
            for(Map.Entry<String, Integer> mapEntry: entry.getValue().entrySet()) {
                if(mapEntry.getValue() == x) {
                    entry.getValue().remove(x);
                    map.put(entry.getKey(), betaMap);
                }
            }
        }
    }   
} 

public void print(HashMap<String, HashMap<String, Integer>> map) {
    for(Map.Entry<String,HashMap<String,Integer>> entry: map.entrySet()) {
        System.out.println("Key is:" + entry.getKey());
        if(entry.getValue() instanceof Map) {
            for(Map.Entry<String, Integer> mapEntry: entry.getValue().entrySet()) {
                System.out.println(mapEntry.getKey());
            }
        }
    }
}

public static void main(String[] args) {
    Collections collections = new Collections();
    HashMap<String, Integer> innerStructure = new HashMap<>();
    HashMap<String, HashMap<String, Integer>> containingStructure = new HashMap<>();
    containingStructure = collections.createMap("B1", "A1", 4, innerStructure, containingStructure);
    collections.reset(containingStructure, 2);
    collections.print(containingStructure);
}
}

It really doesn't change the Beta with put it is a matter of evaluating each entry and making sure it is a new HashMap type being used in it's place. I think this should help.

April_Nara
  • 1,024
  • 2
  • 15
  • 39
-1

As @Andreas said, I should have created a new instance of Alpha by assigning it like Alpha = new HashMap<>(); when I no longer needed it. I can then re-use it without affecting Beta.

SemAntys
  • 316
  • 2
  • 15