早上好, 我目前正在开发一个公开Web服务接口的Java Web应用程序。为了将全局对象保留在内存中,我将以下类用作Singleton:
public class SingletonMap {
private static final SingletonMap instance = new SingletonMap();
private static HashMap couponMap = null;
private static long creationTime;
private SingletonMap() {
creationTime = System.currentTimeMillis();
couponMap = new HashMap();
}
public static synchronized SingletonMap getInstance() {
return instance;
}
public static long getCreationTime() {
return creationTime;
}
}
我正在使用上面的类,以便为Web服务的所有线程提供相同的HashMap实例。维护SingletonMap对象的Web服务类如下:
@WebService()
public class ETL_WS {
private String TOMCAT_TEMP_DIR;
private final int BUFFER_SIZE = 10000000;
private static SingletonMap couponMap;
private static SingletonProductMap productCategoryMap;
private String dbTable = "user_preferences";
public ETL_WS() {
Context context = null;
try {
context = (Context) new InitialContext().lookup("java:comp/env");
this.TOMCAT_TEMP_DIR = (String) context.lookup("FILE_UPLOAD_TEMP_DIR");
}catch(NamingException e) {
System.err.println(e.getMessage());
}
public long getCouponMapCreationTime() {
return couponMap.getCreationTime();
}
}
我有方法getCouponMapCreationTime()的原因是检查Web服务的所有线程是否正在访问同一个对象。上述方法是否正确?性能开销怎么样?你认为我需要Singleton属性,还是我可以只为所有线程使用静态HashMap?如果我使用静态HashMap,如果没有线程处于活动状态,它是否会被垃圾收集?
感谢您的时间。
答案 0 :(得分:7)
JAX-WS Web服务本身就是一个Singleton。这意味着将使用单个Web服务实例(如Servlet)处理所有请求。
因此,该类的任何成员都将在所有请求之间“共享”。在您的情况下,您不需要使您的成员(即couponMap)成为静态属性。
结论:别担心,您的所有主题(请求)都将访问相同的“couponMap”。因为您不再需要getCouponMapCreationTime
,我认为您可以消除SingletonMap
抽象并直接在Web服务类中使用Map。
但我有一些非常重要的补充。如果几个线程(请求)将访问您的地图,您必须使其线程安全!有很多方法可以做到这一点,但我会提出一个想法:使用ConcurrentHashMap
代替HashMap
。这将使您的所有get(), put(), remove()
操作都是线程安全的!如果您需要更大的范围,则可以使用synchronized块,但请避免使用同步方法,因为scoop太大并且始终在this
对象上进行同步。
答案 1 :(得分:3)
JAX-WS有自己的模式用于创建单例,您不需要使用静态字段。您可以在每个服务中使用@Inject
注释。请参阅此博文:http://weblogs.java.net/blog/jitu/archive/2010/02/19/jax-ws-cdi-java-ee-6-0(但请勿使用@SessionScoped
,请使用@Singleton
)
其他一些观点:
HashMap
不是线程安全的,您需要ConcurrentHashMap
。
此catch(NamingException e) { System.err.println(e.getMessage());
无益。将其改为RuntimeException
。你无法从中恢复。
在此阶段不要担心性能开销。有一些工作后测量它。