6

在重构一些代码时,我偶然发现了这种奇怪现象。在不影响整个类的情况下控制初始化器的 strictfp 属性似乎是不可能的。例子:

public class MyClass {

    public final static float[] TABLE;
    strictfp static { // this obviously doesn't compile
         TABLE = new float[...];
         // initialize table
    }

    public static float[] myMethod(float[] args) {
         // do something with table and args
         // note this methods should *not* be strictfp
    }

}

JLS 的第 8.1.1.3 节中,我收集到如果将使用 strictfp 修饰符声明类,则初始化程序将是 strictfp。但它也说它使所有方法都隐式地严格执行:

strictfp 修饰符的作用是使类声明中的所有浮点或双精度表达式(包括变量初始化器、实例初始化器、静态初始化器和构造器中)显式地为 FP-strict(第 15.4 节)。

这意味着类中声明的所有方法,以及类中声明的所有嵌套类型,都是隐式的 strictfp。

那么,静态初始化器不接受修饰符,当应用于整个类时,一切都变成了strictfp?既然没有strictfp关键字的对立面,这不可能实现吧?

那么,我是否搞砸了使用静态方法来保持初始化块的主体以实现对严格控制的精确控制?

4

1 回答 1

1

使用以下要求:

  • 初始化代码被调用一次,
  • MyClass.myMethod方法是非严格的浮点数,
  • 类 API 没有“乱七八糟”的方法,
  • 并且初始化代码严格的浮点数

...这就足够了:

class MyClass {
  //1) initialized/called once
  public final static float[] TABLE = MyClassInitializer.buildSomething();

  public static float[] myMethod(float[] args) {
    //2) non-strict
  }
}

//3) doesn't "pollute" the MyClass API
class MyClassInitializer {
  strictfp [static] float[] buildSomething() { //4) strictfp here or on the class
    //TODO: return something
  }
}

如果您将类的静态成员视为单独的单例对象中的对象,那么上面的示例看起来很自然。我认为这与单一职责原则非常吻合。

于 2012-08-29T17:47:06.713 回答