当线程特别阻塞时,避免全局修改静态对象
Avoid global modification of static object when a thread is in particulare block
我有两个class,第一个class(ClassServletA.java)是HttpServlet,把ipaddress和访问时间存储在HashMap中,我想把HashMap备份到DB中每天,所以我正在安排任务并将静态 HashMap 对象存储在数据库中,然后重新初始化 HashMap(存储在数据库中之后)。
是否可以全局锁定静态对象?
public class ClassServletA {
public static Map<String,String> myMap = new HashMap<String, String>();
void doGet(HttpServeltRequest request , HttpServletResponse response){
myMap.put("ipaddress", "accessTime");
}
}
第二个Class是调度器:
public class MyDailyTask implements Job {
void executeMethod(){
//Writing the map object to file or database login here
ByteArrayOutputStream bos = new ByteArrayOutputStream();
ObjectOutputStream out = new ObjectOutputStream(bos);
out.writeObject(ClassServletA.myMap);
out.flush();
out.close();
// Reinitialize the hashmap
ClassServletA.myMap=new HashMap<String,String> ();
}
}
是否可以在调度程序(MyDailyTask.java)执行executeMethod()时在调度时间段内全局锁定或避免修改ClassServletA.myMapMap对象。
如果您只想确保 myMap
在执行 executeMethod
时未被修改,但又不想阻止其他线程访问它,您可以使用 AtomicReference
public class ClassServletA {
public static final AtomicReference<Map<String,String>> myMap = new AtomicReference(new HashMap<>());
void doGet(HttpServeltRequest request , HttpServletResponse response){
myMap.get().put("ipaddress", "accessTime");
}
}
public class MyDailyTask implements Job {
void executeMethod(){
//Writing the map object to file or database login here
ByteArrayOutputStream bos = new ByteArrayOutputStream();
ObjectOutputStream out = new ObjectOutputStream(bos);
out.writeObject(ClassServletA.myMap.getAndSet(new HashMap<>()));
out.flush();
out.close();
}
}
如果您想阻止对 myMap
的任何访问,请考虑使用 ReadWriteLock. See other SO questions about it: Java Concurrency: ReadWriteLock on Variable
无论如何,HashMap
都不是线程安全的,并发访问需要适当的同步。参见 Java Multithread Access Static Variable
我有两个class,第一个class(ClassServletA.java)是HttpServlet,把ipaddress和访问时间存储在HashMap中,我想把HashMap备份到DB中每天,所以我正在安排任务并将静态 HashMap 对象存储在数据库中,然后重新初始化 HashMap(存储在数据库中之后)。
是否可以全局锁定静态对象?
public class ClassServletA {
public static Map<String,String> myMap = new HashMap<String, String>();
void doGet(HttpServeltRequest request , HttpServletResponse response){
myMap.put("ipaddress", "accessTime");
}
}
第二个Class是调度器:
public class MyDailyTask implements Job {
void executeMethod(){
//Writing the map object to file or database login here
ByteArrayOutputStream bos = new ByteArrayOutputStream();
ObjectOutputStream out = new ObjectOutputStream(bos);
out.writeObject(ClassServletA.myMap);
out.flush();
out.close();
// Reinitialize the hashmap
ClassServletA.myMap=new HashMap<String,String> ();
}
}
是否可以在调度程序(MyDailyTask.java)执行executeMethod()时在调度时间段内全局锁定或避免修改ClassServletA.myMapMap对象。
如果您只想确保 myMap
在执行 executeMethod
时未被修改,但又不想阻止其他线程访问它,您可以使用 AtomicReference
public class ClassServletA {
public static final AtomicReference<Map<String,String>> myMap = new AtomicReference(new HashMap<>());
void doGet(HttpServeltRequest request , HttpServletResponse response){
myMap.get().put("ipaddress", "accessTime");
}
}
public class MyDailyTask implements Job {
void executeMethod(){
//Writing the map object to file or database login here
ByteArrayOutputStream bos = new ByteArrayOutputStream();
ObjectOutputStream out = new ObjectOutputStream(bos);
out.writeObject(ClassServletA.myMap.getAndSet(new HashMap<>()));
out.flush();
out.close();
}
}
如果您想阻止对 myMap
的任何访问,请考虑使用 ReadWriteLock. See other SO questions about it: Java Concurrency: ReadWriteLock on Variable
无论如何,HashMap
都不是线程安全的,并发访问需要适当的同步。参见 Java Multithread Access Static Variable