I have a requirement where I have to use a hashMap where values can change dynamically and keys can get only inserted not deleted or updated. However Keys will be read many times and values may be updated many times.
For latency issues, I haven't made entire HashMap as ConcurrentHashMap in which case while writing keys I will have issues. I am fine with compromising slight data accuracy with keys. So I decided to keep my own dirty copy of keys. A code snippet like below.
package com.test.collections;
import java.util.HashMap;
import java.util.Map;
import java.util.Set;
import java.util.TreeSet;
import java.util.concurrent.ConcurrentHashMap;
public class CheckKeySet {
private static Map<String, ConcurrentHashMap<String, String>> testMap = new HashMap<String, ConcurrentHashMap<String, String>>();
public static void main(String[] args) {
CheckKeySet trial = new CheckKeySet();
try {
trial.doIt();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
private void doIt() throws InterruptedException {
Thread accessThread1 = new AccessKeySet("Access1");
Thread writeThread = new WriteValueSet();
Thread accessThread2 = new AccessKeySet("Access2");
Thread accessThread3 = new AccessKeySet("Access3");
writeThread.start();
Thread.sleep(1000);
accessThread1.start();
Thread.sleep(2000);
accessThread2.start();
Thread.sleep(4000);
accessThread3.start();
}
private Set<String> getKeySet() {
return new TreeSet<String>(testMap.keySet());
}
class AccessKeySet extends Thread {
public AccessKeySet(String string) {
super(string);
}
@Override
public void run() {
Set<String> keySet = getKeySet();
System.out.println("###############Trying to print########## " + getName() + " keySet size " + keySet.size());
for (String s : keySet) {
System.out.println(s);
try {
Thread.sleep(100);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
class WriteValueSet extends Thread {
@Override
public void run() {
int i = 1;
for (i = 1; i < 10000; i++) {
testMap.put("Check-" + i, new ConcurrentHashMap<String, String>());
System.out.println("Inserted " + i);
try {
Thread.sleep(100);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
}
My question, I am creating new Set Object in above implementation with the HashMap.keySet() as base value. HashMap.keySet() will live forever in my code. Will this impact the GC of dirty set objects that I am creating in getKeySet() ? I want this new set object to be cced whenever its holding object becomes eligible for gc. It should not be stopped from getting gced because hashMap.keySet is alive