2011-09-06 22 views
9

Posso creare un tipo di enum Java vuoto, ma quando voglio aggiungere alcuni metodi: ottengo un "errore di sintassi" (in Eclipse). Non ho trovato documentazione ufficiale su questo, quindi la mia domanda è: è semplicemente impossibile (quindi dove è chiaramente menzionato?) O è solo il compilatore che è sbagliato?È possibile creare un tipo enum Java vuoto con metodi?

+0

se pubblichi il codice che ha dato l'errore, saremo in grado di dare una risposta più elaborata. – tb189

+3

perché ti piacerebbe avere un enum vuoto? – maasg

+0

Potrebbe voler creare un set di quell'Enum in fase di runtime, ma ha ancora comportamenti di istanza. – ggb667

risposta

16

Sì, è possibile. Hai solo bisogno di aggiungere un ; per terminare la lista (vuoto) di costanti enum:

enum TestEnum { 
    ;       // doesn't compile without this. 
    public void hello() { 
     System.out.println("Hello World"); 
    } 
} 

JLS Syntax Definition for enums

(Si noti che, senza tutte le istanze, sarete solo in grado di chiamare i metodi del static enum)

correlati:.

+0

Il metodo ciao sarebbe impossibile da chiamare, vero? Non riesco a vedere il punto di tale costrutto. –

+0

Così com'è sì. Forse i suoi metodi sono "statici", non lo so. Ma sì, sono d'accordo con te. Sembra un po 'imbarazzante. – aioobe

+3

Grazie a @aioobe per la risposta e il collegamento. Voglio farlo perché penso sia un modo naturale, e molto facile/comprensibile, di implementare una classe non-instanciable (tipicamente una classe di utilità con solo metodi statici di definizione): per me è più naturale dire "un la classe non-instanciable è un enum senza elemento "(cioè permette di non usare istanze di se stessa) che dire" dovrebbe essere implementato con un costruttore privato che lancia un AssertionError "(cfr. Java efficace n. 4). Ma è solo il mio punto di vista, quindi non esitate a sfidarmi se sbaglio ... – cedric

5

sì, è:

È necessario aggiungere un punto e virgola (;) per terminare la lista vuota di enumerazioni.
Questo compila:

public enum MyEnum { 
    ; 
    public void method() { 

    } 
} 

Anche se non riesco a pensare che cosa sarebbe utile per.

+1

I metodi possono essere utili, quando le enumerazioni sono composte da campi .. quindi diciamo che hai un enumeratore COLORS che ha una rappresentazione int, una rappresentazione di stringa breve e una rappresentazione di stringa di visualizzazione .. allora questo enum può avere metodi come getInteger(), getShortString(), getDisplayString() .. quindi, per esempio, viene mostrato sulla GUI usando l'opzione getDisplayString() ... forse memorizzato nel DB usando l'opzione getShortString() ... – Scorpion

+2

Penso che ciò che Bohemian significa è che non può pensare a nulla di utile con un * vuoto * enum con i metodi. – aioobe

+1

Sì, qualsiasi metodo di istanza di questo tipo sarebbe inaccessibile. Inoltre, non riesco a pensare a molto utile da fare con un enum vuoto. – Bohemian

1

Absoulely,

/** 
* @author The Elite Gentleman 
* @since 06 September 2011 
* 
*/ 
public enum ExampleEnum { 
    WHAT_ENUM 
    ; 

    public void doOperation() { 

    } 
} 

tardi:

ExampleEnum exEnum = ExampleEnum.WHAT_ENUM; 
exEnum.doOperation(); 
6

Naturalmente è possibile! "Ia! Ia! Cthulhu Fthagn! Ph'nglui mglw'nfah Cthulhu R'lyeh wgah'nagl fhtagn !!"

idea originale: "http://www.theserverside.com/news/thread.tss?thread_id=50190"

Distruggere la realtà a proprio rischio.

import java.lang.reflect.Constructor; 
import java.lang.reflect.Field; 
import java.lang.reflect.Method; 

enum ThingsThatShouldNotBe { 
; 
public void HelloWorld() { 
    System.out.println(this.name() + " Says Hello!"); 
} 
public static void main(String[] args) throws Exception { 
    Constructor<?> con = ThingsThatShouldNotBe.class.getDeclaredConstructors()[0]; 
    Method[] methods = con.getClass().getDeclaredMethods(); 
    for (Method m : methods) { 
     if (m.getName().equals("acquireConstructorAccessor")) { 
      m.setAccessible(true); 
      m.invoke(con, new Object[0]); 
     } 
    } 
    Field[] fields = con.getClass().getDeclaredFields(); 
    Object ca = null; 
    for (Field f : fields) { 
     if (f.getName().equals("constructorAccessor")) { 
      f.setAccessible(true); 
      ca = f.get(con); 
     } 
    } 
    Method m = ca.getClass().getMethod("newInstance", 
     new Class[] { Object[].class }); 
    m.setAccessible(true); 
    ThingsThatShouldNotBe v = (ThingsThatShouldNotBe) m.invoke(ca, new Object[] { new Object[] { "Cthulhu", 
      Integer.MAX_VALUE } }); 
    System.out.println(v.getClass() + ":" + v.name() + ":" + v.ordinal()); 
    System.out.println("Say hello Cthulhu!"); 
    v.HelloWorld(); 
} 
} 

Mwu HA HA HA HA HA HA.

Se hai davvero bisogno di un Enum e vuoi che abbia metodi di istanza, e hai deciso di convocare gli antichi dei della riflessione per forzare questo abominio sul mondo, allora è utile.

Questo confonderà definitivamente altri sviluppatori in futuro.

Problemi correlati