2012-10-22 10 views
8

Ich weiß nicht, ob ich der Einzige bin, der das weiß, aber die Werte eines Enums sind nicht implizit endgültig und können geändert werden.Java enums Wandelbarkeit Use Cases und Möglichkeiten?

enum EnumTest { 
    TOTO("TOTO 1"), 
    TATA("TATA 2"), 
    ; 

    private String str; 

    private EnumTest(String str) { 
     this.str = str; 
    } 

    @Override 
    public String toString() { 
     return str; 
    } 
    } 

    public static void main(String[] args) { 
    System.out.println(EnumTest.TATA); 
    EnumTest.TATA.str = "newVal"; 
    System.out.println(EnumTest.TATA); 
    } 

TATA 2 
newVal 

Diese Werte werden oftenly bei Instanzerstellung initialisiert (TOTO("TOTO 1")), aber außer mir, ich habe noch nie jemanden gesehen, das letzte Schlüsselwort für Enum-Variablen, die unveränderlich sein sollte. Das ist nicht der Punkt der Frage, ich frage mich nur, ob ich der Einzige bin, der sich dessen bewusst ist.


Was würde ich gerne wissen, wenn es einen Anwendungsfall gab, um veränderbare enums zu erstellen?

Und ich würde auch gerne die Grenzen dessen kennen, was wir mit enums machen können (gute Praxis oder nicht). Ich habe es nicht getestet, aber vielleicht kann ein Enum mit Spring Bohnen injiziert werden? Zumindest scheint es, dass wir jede Instanz (z. B. @Deprecated funktioniert gut) und auch die Methoden kommentieren können.

+7

Die Verwendung von "final" für Felder ist in enums üblich. –

Antwort

7

Ein möglicher Anwendungsfall wäre die Lazy-Initialisierung (einige Feldwerte bei der ersten Verwendung berechnen, wenn sie oft gar nicht verwendet werden) oder ein "normales" veränderbares Singleton-Objekt (wie eine Registrierung oder Ähnliches).

In den meisten Fällen sollten Enum-Objekte jedoch unveränderlich sein und ihre Felder sind endgültig.

-3

Was würde ich gerne wissen, wenn es einen Anwendungsfall gab, um veränderbare enums zu erstellen?

Die Enum-Konstanten sind nicht selbst veränderbar, ihre Felder sind veränderbar.

+1

Das meint er so, wie ich es verstanden habe. –

+0

Ja, das ist was ich meine, aber der "allgemeine" Usecase ist das Erstellen unveränderlicher Enums, aber niemand verwendet "final" –

+0

Das liegt daran, dass es selten eine'Enum' mit einem 'public' Feld oder eine öffentliche Methode gibt, um ein Feld IMHO zu ändern . Aber ich stimme zu, dass die Felder als "endgültig" deklariert werden sollten. –

6

Während Sie hier auf eine interessante Tatsache hinweisen, gibt es, soweit es mich betrifft, keinen Anwendungsfall für veränderbare enum-Felder. Es gibt viele Gründe, warum die Verwendung dieser Sprache "Feature" ("Bug"?) Eine schlechte Idee wäre, nicht zuletzt die Möglichkeit, andere Entwickler zu verwirren.

+3

Ich stimme darin überein, dass Enums im Allgemeinen als unveränderlich angesehen werden und dadurch veränderbare Enums erzeugen könnten, die zu Missbrauch führen könnten. Ich würde vorschlagen, dass veränderbare Werte, die enums zugeordnet sind, am besten in einer "EnumMap" helfen würden. Das heißt, ich denke, es ist "kein Usecase" zu stark. Enums stellen in der Praxis eine Erweiterung des Singlton-Musters (eine feste Anzahl von Instanzen) dar und könnten in diesem Sinne wie jede andere Klasse verwendet werden. Ich wiederhole noch einmal, dass die meisten Entwickler es gewohnt sind, sie als unnachgiebig zu betrachten, und daher könnten veränderbare Enums zu Wartungsproblemen führen. –

+0

Gott sei Dank, da sie angenommen werden, gibt es in der Regel keinen Setzer :) –

+0

@JohnB, wenn Sie sich ein gutes Beispiel für eine Situation vorstellen können, in der die Verwendung einer Enum mit veränderbaren Feldern wohl besser ist als jede andere Alternative, würde ich es begrüßen eine separate Antwort. Aber meine Antwort ist immer noch: Für mich gibt es keinen Anwendungsfall, zumindest keinen Anwendungsfall, der mit einer gewöhnlichen Klasse nicht besser bedient werden könnte. Sie haben Recht, was Enums "in der Praxis" sind, aber konzeptionell sind sie näher an einem 'boolean' (der einen festen Satz von 2 möglichen Werten hat) oder einem'int' (fester Satz von 2^32-1 möglichen Werten) . Kannst du dir vorstellen, veränderliche Felder auf "wahr" zu haben? –

3

Als Antwort auf Alex Ds Antwort und Kommentar nehme ich seinen Vorschlag, einen möglichen Anwendungsfall zu veröffentlichen. Nehmen wir das alte Standard-Enum-Beispiel von Planeten, aus denen die Gravitation usw. berechnet werden kann. Stellen Sie sich vor, Sie wollten die Anzahl menschlicher Kolonien auf jedem Planeten erhalten. Ja, Sie könnten eine EnumMap verwenden, aber ich könnte einen Fall sehen, wo mehr und mehr veränderbare Felder benötigt werden könnten und entweder eine separate Map für jeden Wert oder eine separate Klasse für die veränderlichen Werte, die mit einer Enumeration verbunden sind, wäre nicht intuitiv.

Wie ich in meinen Kommentaren sagte, im Allgemeinen glaube ich Enums sind in der Regel und sollte unveränderlich sein, aber ich finde, dass die Aussage, dass es keine Anwendungsfälle gibt, zu stark ist.

1

Ich sehe keinen Grund, die Verwendung von veränderbaren Feldern in enum s zu verbieten. Man verwendet einen enum, um anzugeben, dass der Wert des Typs zu einem endlichen (und bekannten) Satz von Möglichkeiten gehört. Es bedeutet nicht, dass diese Werte keine Eigenschaften haben können, die sich im Laufe der Zeit entwickeln.

Einige haben nach Anwendungsfällen für ein solches Szenario gefragt. Ein Beispiel wäre die Verwendung eines enum Typs wie ErrorCategory, der einen Fehler in eine beliebige Anzahl vordefinierter Kategorien einteilen würde (zB: DocumentationError, SemanticError, LayoutError ...).

Angenommen, diese ErrorCategories haben Eigenschaften wie requiresInstantIntervention oder shouldFailBuild. Ich kann mir vorstellen, dass sich der Wert dieser Eigenschaften im Laufe der Zeit ändern kann oder dass sie vom Benutzer konfigurierbar sein können.

ich erkennen, dass es (viele) andere Wege, diese Umsetzung (wie in der Tat EnumMaps oben erwähnt), und man kann immer über den Stil streiten, aber für mich, eine solche Verwendung von enum s ist an sich nicht falsch. Da enum s Referenztypen in Java sind, bleibt das Verhalten von == das gleiche wie wenn es überhaupt keine änderbaren Eigenschaften gäbe.

0

Eine Enum-Instanz ist ein öffentliches statisches Endfeld der Enum-Klasse. Wenn es veränderbar ist, können Sie seinen Status in einem anderen Thread ändern. Dies ist möglicherweise nicht das, was Sie wollen und kann Probleme verursachen, wenn Sie dies nicht erkennen.