我想知道在Java EE应用程序中使用静态方法的含义。
例如:有一个类处理日期转换、字符串重新排序等。
这个类中的所有方法都是静态的
Servlet使用这些方法。
这是否意味着静态方法需要是线程安全的(因为如果许多用户同时使用应用程序并访问静态方法,可能会出现一些问题)?
编辑我想在web应用程序的上下文中了解这一点-两个用户是否会同时使用静态方法并互相干扰(静态方法的)结果?
并行访问方法是可以的,只要没有共享的类变量;例如,如果该方法声明了它自己的东西,那么你就很好:
public static void thing() {
String x = "";
// do stuff with x
}
以上内容很好。
String x = "";
public static void thing() {
// do stuff with x
}
这个不是。
这是否意味着静态方法需要是线程安全的(在如果许多用户同时使用该应用程序,并且同时访问静态方法问题)?
只有当存在共享状态时。如果为每次调用在堆上分配新对象,那么这不是问题。
但我从不喜欢做这种事情,因为引入共享状态意味着你有线程安全问题。我更喜欢创建转换器/助手类的实例(对象创建通常在性能方面可以忽略不计)。这立即意味着你是线程安全的(前提是你没有共享状态),每个实例都可以(例如)在构建时进行定制,以便在需要时提供不同的行为。
当然,如果您不保护静态方法,并且它们更改了a状态,就会出现问题。
考虑这个样本
public class GlobalCount {
private int count = 0;
public static void increment() {
count++; // that is : count = count + 1 (which means some thread may use the old value of count when assigning)
}
}
如果有多个线程调用increment
,则可能会丢失一些增量(也就是说,count
可能小于调用增量方法的次数。
所以你必须将你的方法设置为同步:
public static synchronized void increment() {
count++;
}
如果您认为您没有共享状态,请小心:许多标准类(例如SimpleDateFormat,正如您所说的日期格式)都不是线程安全的,如果同时从多个线程调用实例,则可能会失败。
因此,一旦有一个静态实例从多个线程访问,就要非常小心。