2
class revi {

    static {
        i = 3;
        System.out.println("Hello World!");
    }
    static int i = 15;

    public static void main(String[] args) {
        System.out.println("Hello World!");
    }
}

above program does not give any error at i=3; but when we call the i in println() method of static block it showing error

revi.java:6: error: illegal forward reference System.out.println("Hello World!"+i); ^ 1 error

class revi {

    static {
        i = 3;
        System.out.println("Hello World!" + i);
    }
    static int i = 15;

    public static void main(String[] args) {
        System.out.println("Hello World!");
    }
}

but if modify the above program like this it working(static variable first loaded ) no error in println method

class revi {

    static int i = 15;

    static {
        i = 3;
        System.out.println("Hello World!" + i);
    }

    public static void main(String[] args) {
        System.out.println("Hello World!");
    }
}

please explain internal flow ...

2
  • It is as you can see: static initialization blocks can only refer to static variables declared previously. Commented Dec 20, 2014 at 17:43
  • 2
    "it showing error" is never enough information. Please tell us what error you're seeing. Commented Dec 20, 2014 at 17:44

3 Answers 3

7

This is covered in section 8.3.3 of the JLS:

Use of class variables whose declarations appear textually after the use is sometimes restricted, even though these class variables are in scope (§6.3). Specifically, it is a compile-time error if all of the following are true:

  • The declaration of a class variable in a class or interface C appears textually after a use of the class variable;

  • The use is a simple name in either a class variable initializer of C or a static initializer of C;

  • The use is not on the left hand side of an assignment;

  • C is the innermost class or interface enclosing the use.

In your case, all of them are true when you're printing the value, hence the error.

After changing your code to move the declaration, the first bullet is no longer true, so it compiles.

Sign up to request clarification or add additional context in comments.

2 Comments

Do you know why they decided that writing i = 3; is not an illegal forward reference, whereas writing System.out.println(i); is. What's the point?
@pbabcdefp: I honestly couldn't tell you that. I suspect it's because the former doesn't need the existing value to be known, whereas the latter does - it may make it easier to work out the order in which to emit code. Not sure though.
1

In case1, You are initializing the variable i with 3 and at line 2 with 15. So end result is that variable i holds 15.

In case 2 you will get Illegal forward reference error because you are trying to use the variable i before it is defined. Updated As per JLS static variables that are not yet defined can only be used in the assignment unless they are prefixed with class name(in which case they get there default value). E.g.1

static {
    i = 3;
    i = i * 2; // will give you compile error
    System.out.println("Hello World!" );
}

E.g.2 In this case you are accessing variable i prefixed with class name. But remember that revi.i will have value 0 not 15, so the output will be 0

static {
    i = revi.i * 2; // this line is similar to  revi.i = revi.i * 2;
    System.out.println("Hello World!" + revi.i );
}
static int i = 15;


In case 3 first you declared and initialize i=5 and then assigned 3 to it. So after initialization i will hold 3 as its value

2 Comments

Can you say something more about second case? Why if we use revi.i instead of i problem disappears System.out.println("Hello World!" + revi.i);?
I was interested more in "why revi.i is allowed while i isn't", not in "how it will work". IMO JLS just confirms it, not explains. Will need to look a this closer someday.
0

When a java class is getting executed there are few steps which JVM performs few steps sequentially.

Identify the static members from top to bottom. Executes static variables assignments and static blocks from top to bottom. Executes the main method. During these phases there is one such state called RIWO(Read Indirectly Write Only) for a static variable.

During RIWO a variable cannot be accessed directly with its reference. Instead we need to use an indirect way to call certain variables.

RIWO State

you can refer to that link for detailed information.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.