jon hanson
jon hanson

Reputation: 9408

Java enum value fields not accessible outside of definition

In the following code the member fields of the Colours enum GREEN value are not accessible outside of the enum definition:

public class Test {

    enum Colours {
        RED,
        GREEN {
            public static final int hex = 0x00ff00;
            public final int hex2 = 0x00ff00;  // Try it without static, just in case...

            void f() {
                System.out.println(hex);    // OK
                System.out.println(hex2);   // OK
            }
        },
        BLUE
    }

    public static void main(String[] args) {
        System.out.println(Colours.GREEN.hex);      // COMPILE ERROR
        System.out.println(Colours.GREEN.hex2);     // COMPILE ERROR
    }
}

The offending lines give rise to the following compiler error:

Error:(38, 41) java: cannot find symbol
  symbol:   variable hex
  location: variable GREEN of type Test.Colours

Any idea why this doesn't work? I assume the Java standard forbids it, but why?

Upvotes: 2

Views: 720

Answers (2)

Karol Dowbecki
Karol Dowbecki

Reputation: 44960

As per JLS §8.9.1. Enum Constants an enum constant body is governed by the rules applicable to anonymous class, which restrict the accessibility of fields and methods:

The optional class body of an enum constant implicitly defines an anonymous class declaration (§15.9.5) that extends the immediately enclosing enum type. The class body is governed by the usual rules of anonymous classes; in particular it cannot contain any constructors. Instance methods declared in these class bodies may be invoked outside the enclosing enum type only if they override accessible methods in the enclosing enum type (§8.4.8).

Upvotes: 2

BackSlash
BackSlash

Reputation: 22243

enum Colours {
    RED,
    GREEN {
        public static final int hex = 0x00ff00;
        public final int hex2 = 0x00ff00;  // Try it without static, just in case...

        void f() {
            System.out.println(hex);    // OK
            System.out.println(hex2);   // OK
        }
    },
    BLUE
}

Here, both RED, GREEN and BLUE are of type Colours, which doesn't know about hex, hex2 or f, that's why your code doesn't compile.

What you can do is move them in the enum definition:

enum Colours {
    RED(0xff0000, 0xff0000),
    GREEN(0x00ff00, 0x00ff00),
    BLUE(0x0000ff, 0x0000ff);

    final int hex;
    final int hex2; 

    Colours(int hex, int hex2) {
        this.hex = hex;
        this.hex2 = hex2;
    }

    void f() {
        System.out.println(hex);    // OK
        System.out.println(hex2);   // OK
    }
}

This way all of these will compile:

System.out.println(Colours.GREEN.hex);
System.out.println(Colours.GREEN.hex2);
Colours.GREEN.f();

Upvotes: 1

Related Questions