2013-03-09 5 views
25

Was ist der Unterschied zwischen den endgültigen Variablen und den Kompilierzeitkonstanten?Unterschied zwischen Endvariablen und Kompilierzeitkonstante

Betrachten Sie den folgenden Code

final int a = 5; 
final int b; 
b=6; 
int x=0; 
switch(x) 
{ 
    case a: //no error 
    case b: //compiler error 
} 

Was bedeutet das? Wann und wie sind den finalen Variablen ein Wert zugeordnet? Was passiert zur Laufzeit und was passiert zur Kompilierzeit? Warum sollten wir eine Kompilierzeitkonstante angeben? Welche anderen Strukturen von Java erfordern eine Kompilierzeitkonstante?

+0

Bitte beachten Sie den Link zu diesem bestimmten Teil des Themas in JLS –

Antwort

26

Das Problem ist, dass alle case: Anweisungen zur Kompilierzeit Ultimate sein müssen. Ihre erste Aussage ist ultimate. a wird für 100% kein anderer Wert als 5 sein.

final int a = 5; 

Dies ist jedoch nicht für b garantiert. Was wäre, wenn es eine if-Anweisung um b gäbe?

final int b; 
if(something()) 
    b=6; 
else 
    b=5; 
2

Die switch-Anweisung benötigt eine Konstante. Da finale Variablen verzögert initialisiert werden können und der Compiler nicht für b bestimmen kann, dass er einen Wert in der Case-Verzweigung hat.

+6

Sicher, aber ich habe immer noch nicht die Antwort für meine Fragen –

7

Was bedeutet das?

Es bedeutet, dass 'b' keine Compilierzeitkonstantenausdruck ist, und die JLS erfordert es zu sein.

Wann und wie sind den finalen Variablen ein Wert zugewiesen?

Formal, wenn die Zuweisungsanweisung oder der Initialisierer ausgeführt wird.

Wenn jedoch in der Praxis die final eine Kompilierzeitkonstante deklariert, wird der Ausdruck zur Kompilierzeit ausgewertet und sein Wert ist fest in den Code eingebunden.

Was passiert zur Laufzeit und was passiert zur Kompilierzeit?

Siehe oben.

Warum sollten wir Switch eine Kompilierzeitkonstante geben?

Da die JLS erfordert es.

Es ist notwendig, dass der Bytecode-Compiler prüft, ob die switch-Anweisung gut gebildet ist; d.h., dass die Werte der Schalterkonstanten nicht kollidieren. Es ermöglicht dem JIT-Compiler außerdem, Code zu generieren, der für die tatsächlichen Werte der Switch-Konstanten optimiert wird.

Welche anderen Strukturen von Java erfordern eine Kompilierzeitkonstante?

Keine, die ich mir vorstellen kann, von der Spitze meines Kopfes.

3

Aus Kompilersicht versuchen Sie eine Variable b zu verwenden, die möglicherweise nicht initialisiert wird. Die switch-Anweisung wird in JVM-Bytecode-Tabellenschalter oder Lookup-Schalter kompiliert, der erfordert, dass die in case-Anweisung verwendeten Werte beide kompilierzeitkonstant und eindeutig sind.

final int a = 4; // compiler is sure a is initialized 
final int b;// variable b is not guranted to be assigned 

z.B. Obwohl diese Anweisung letztlich b initialisiert, kann der Compiler sie jedoch nicht erkennen.

if (a < 4) b= 10; 
if (a >= 4) b = 8 
2

final int b; kann einmal vergeben werden und der Wert ist nicht sicher, dass auf Laufzeit abhängig von den Bedingungen entschieden werden. das ist der Grund, auch wenn es eine endgültige Variable ist, ist es nicht COMPILE TIME konstant, obwohl es eine RUN TIME Konstante und Fall muss kompilieren Zeit Konstanten sein.