我有一个用于统计计算的Util类。在多个线程之间计算指数移动平均。此外,这个线程传递不同的值,有时是双倍的,另一些是长的。我希望建立泛型,并确保在将同步应用于方法签名时。
public class StatUtils {
public static class WMA {
// MMA
}
public static class EMA {
/** The alpha. */
private static double staticAlpha = 0.9;
/** The old value. */
private static double staticOldValue = 1.0;
/**
* Compute.
*
* @param pValue the value
* @return the double
*/
public static synchronized double compute(double pValue) {
if (staticOldValue == 0.0) {
staticOldValue = pValue;
return pValue;
}
double lValue = staticOldValue + staticAlpha * (pValue - staticOldValue);
staticOldValue = lValue;
return lValue;
}
}
}计算方法线程安全吗?如果是的话,这有可能使这个静态类成为通用类吗?
发布于 2016-07-05 09:52:12
只要同步,您的方法是线程安全的,但不能使泛型成为静态类。类实例化时解析泛型类型,但这种情况永远不会发生在静态类中。
您可以定义一个泛型方法,例如:
public static synchronized <T extends Number> compute(T pValue)但是,在您的情况下,您可以简单地使用double,因为长的值可以被抛到双倍,没有问题。
发布于 2016-07-05 10:14:46
是的,你现在的方法是线程安全的。但是,它可能不像整个compute方法会被单个线程阻塞那样有效。
我不确定EMA算法,但是如果您认为线程使用了几乎最新的staticOldValue值,那么您可以对其进行如下改进:
public static class EMA {
/** The alpha. */
private static double staticAlpha = 0.9;
/** The old value. */
private static double staticOldValue = 1.0;
private static Object monitor = new Object();
/**
* Compute.
*
* @param pValue the value
* @return the double
*/
public static double compute(double pValue) {
synchronized (monitor) {
if (staticOldValue == 0.0) {
staticOldValue = pValue;
return pValue;
}
}
double lValue = staticOldValue + staticAlpha * (pValue - staticOldValue);
synchronized (monitor) {
staticOldValue = lValue;
}
return lValue;
}
}https://stackoverflow.com/questions/38198894
复制相似问题