Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why Java wouldn't allow initialisation of static final variable (e.g. static final int d) in constructor? [duplicate]

I was experimenting with initialisation of different type of variables in Java. I can initialise final variable (e.g. final int b) and static variable (e.g. static int c) in constructor but I can't initialise static final variable (e.g. static final int d) in constructor. The IDE also display error message.

Why might Java not allow initialisation of static final variable in constructor?

public class InitialisingFields {
    int a;
    final int b;
    static int c;
    static final int d;

    InitialisingFields(){
        a = 1;
        b = 2;
        c = 3;
        d = 4;
    }

    public static void main(String[] args) {
        InitialisingFields i = new InitialisingFields(); 
    }

}

Error message:

Exception in thread "main" java.lang.RuntimeException: Uncompilable source code - cannot assign a value to final variable d
    at JTO.InitialisingFields.<init>(InitialisingFields.java:22)
    at JTO.InitialisingFields.main(InitialisingFields.java:26)
Java Result: 1
like image 590
Thor Avatar asked Jan 06 '23 07:01

Thor


2 Answers

A static variable is shared by all instances of the class, so each time to create an instance of your class, the same variable will be assigned again. Since it is final, it can only be assigned once. Therefore it is not allowed.

static final variables should be guaranteed to be assigned just once. Therefore they can be assigned either in the same expression in which they are declared, or in a static initializer block, which is only executed once.

like image 190
Eran Avatar answered Apr 27 '23 01:04

Eran


Because

  1. the static variable must be set whether or not you create an instance of the class, so it must happen outside a constructor;
  2. it can only be set once, so you couldn't change its value the second time you create an instance.

You can read a static final variable before it is initialised, and its value would be the default value for the type, e.g.

class Nasty {
  static final int foo = yuk();
  static final int bar = 1;

  static int yuk() {
    System.out.println(bar);  // prints 0.
    return 99;
  }
}

However, this is a bizarre case, and almost certainly not what is desired.

like image 35
Andy Turner Avatar answered Apr 26 '23 23:04

Andy Turner