Why the compiler adds special methods to enum.
So that you can easily get at the values of the enum type, basically.
The only extra methods are valueOf and values. In addition, there are public static final fields, one for each value of the type - again, so that you can actually access the constrainted set of values of that type.
Imagine that the compiler didn't add valueOf and values methods (or at least the values method) - how would you access "all the values of the enum type"? It's often a useful thing to do.
Now EnumSet provides similar facilities, but to get "all the values" you have to provide a Class<> reference, which can be a pain. The values method is somewhat simpler to invoke (although potentially more expensive as well).
See the JLS section 8.9 for more details of exactly what's provided.
To answer the matter of how the values are stored, it's specified that there's a static field per value, but as an implementation detail the Oracle Java compiler also includes a static field with an array - that array is basically cloned in the values method.
You can see this for yourself:
enum Foo {
BAR, BAZ;
}
Compile:
javac Foo.java
Decompile:
javap -private Foo
Compiled from "Foo.java"
final class Foo extends java.lang.Enum<Foo> {
public static final Foo BAR;
public static final Foo BAZ;
private static final Foo[] $VALUES;
public static Foo[] values();
public static Foo valueOf(java.lang.String);
private Foo();
static {};
}
If you use javap -c you'll see that values() is basically:
public static Foo[] values() {
return (Foo[]) $VALUES.clone();
}
The static initializer block creates the limited set of instances and sets the fields.