2014-10-21 20 views
7

Ho una classe enum che contiene una classe interna in Java.Le classi interne in enumerazione sono sempre statiche in Java?

Per esempio (Nel codice vero e proprio, ci sono alcuni metodi dichiarati sul enum che utilizzano internamente la classe interna):

public enum MyEnum{ 
    VALUE_1, 
    VALUE_2; 

    private static class MyInnerClass // is static here needed or can it be removed? 
    { 
    } 
} 

PMD mi dice che il modificatore 'static' non è necessario (Violazione la regola UnusedModifier). È corretto o sarebbe un bug di PMD?

Nota: This question non è un duplicato, è l'inverso di ciò che chiedo qui.

+1

Secondo JLS (http://docs.oracle.com/javase/specs/jls/se5.0/html/classes.html#8.9),"È un errore in fase di compilazione per tentare di creare un'istanza esplicita un tipo enum ". Quindi, direi che la statica è ridondante. – Tetramputechture

+1

Il JLS si riferisce a qualcosa come 'new MyEnum()', non all'istanziazione di classi interne dichiarate all'interno del tipo enum. –

risposta

6

static parola chiave non è ridondante. È possibile creare una classe nidificata statica (con la parola chiave static) o una classe interna (senza di essa). Nel primo caso la classe non sarà assegnata ad alcun particolare valore enum. Nel secondo caso, le istanze della classe interna devono avere un'istanza allegando - uno dei valori enum:

public class Test { 
    public static void main(String[] args) { 
     MyEnum.VALUE_1.createInnerObject().showName(); 
     MyEnum.VALUE_2.createInnerObject().showName(); 
    } 

    public enum MyEnum { 
     VALUE_1, VALUE_2; 

     public MyInnerClass createInnerObject() { 
      return new MyInnerClass(); 
     } 

     private class MyInnerClass { 
      public void showName() { 
       System.out.println("Inner class assigned to " + MyEnum.this + " instance"); 
      } 
     } 
    } 
} 

Nell'esempio di cui sopra non è possibile creare un'istanza del MyInnerClass direttamente dal MyEnum:

new MyEnum.MyInnerClass(); // this will fail 

per fare questo, è necessario disporre di una classe annidata static, ma poi non si può usare qualcosa come MyEnum.this.