2014-10-12 62 views
3

我知道在Java中一个enum常量是隐含的static final变量。但enum类可以有一个实例变量say大小。所以每个enum常量都会有一个'size'的副本。 这是什么等效的Java代码?我的意思是“似乎”静态enum常量是使用非静态的实例变量,这是不可能正常?java如何支持java枚举常量的实例变量?

enum Members{ 
    A(1),B(2),C(3); // I have 3 enum constants here 

    private int size; 
    Members (int size) { 
     //System.out.println("Initializing var with size = "+size); 
    } 
} 

等效代码我知道到目前为止:

public final class Member extends Enums<Members> { 
    public static final Members A; 
    // ... 
    // What happened to size? How do A,B,C get a copy of size? 
} 

编辑:要重申我question- 我感兴趣的由编译器执行的场景背后。我已经知道如何使用枚举。我正在寻找编译器的功能? (例如,如果我简单地写A,编译器将其翻译为“公共静态最终成员A”。我想知道编译器如何给每个A,B,C一个大小的副本。

+0

不要混淆变量和引用与对象。 – 2014-10-12 14:51:14

回答

3

我的意思是“似乎”静态枚举常量是使用非静态的实例变量,这是不可能正常?

这是绝对可能的:在每个enum变量static是在自己的权利的对象,完成它的实例变量。enum中的实例为static,但它不会使实例本身的上下文成为静态上下文。

public final class Member extends java.lang.Enums<Members> { 
    public static final Members A = new Member(1) { 
     public String toString() { return "A:"+size; } 
    }; 
    public static final Members B = new Member(2) { 
     public String toString() { return "B:"+size; } 
    }; 
    public static final Members C = new Member(3) { 
     public String toString() { return "C:"+size; } 
    }; 
    private final int size; 
    protected Member(int size) { this.size = size; } 
} 
+1

为什么要创建一个新的每个'成员'变量的类? – msrd0 2014-10-12 14:51:48

+0

所以你在说什么是每个枚举常量A,B,C得到一个大小的副本,所以Java接受我的代码并将它转换为类似的东西(为A创建一个实例var,for B等),这意味着编译器正在做一些幕后的事情,我正在寻找幕后的东西 – rents 2014-10-12 15:38:36

+0

我的意思是“通常”是非枚举类中的静态变量不能访问非静态变量 – rents 2014-10-12 15:40:09

2

I意思是“似乎”静态枚举常量使用非静态实例变量,这是不可能正常吗?

我的意思是“通常”是非枚举类静态变量不能访问非静态变量

仍然是这样:静态变量不能访问非静态变量 在你的示例代码中,你不这样做这个: 没有静态变量访问非静态变量。

构造函数Members(int size)不在静态上下文中(构造函数永远不会)。 A,B和C都是枚举类型Members, 的所有实例,并且在创建这些实例时,将使用参数size调用构造函数。 一旦构建,这些对象将被视为静态常量值。

也许另一个例子可以帮助:

class Person { 
    private final String name; 
    Person(String name) { 
     this.name = name; 
    } 
} 
class EmployeeDatabase { 
    private static final Person CEO = new Person("Jack"); 
} 

这里EmployeeDatabase.CEO是与非静态字段name静态常量对象。 这就像Members.A,一个带有非静态字段size的静态常量对象。

我想知道编译器如何给每个A,B,C一个大小的副本。

与将构造函数参数传递给任何对象的方式完全相同。

你可以阅读所有关于docs中的枚举。

+0

这不会编译,'size'不能是最终的 – msrd0 2014-10-12 14:46:01

+0

当然可以。它不仅可以是最终的,它应该是最终的。一个可变的枚举将是非常薄弱的​​设计。 – janos 2014-10-12 14:47:22

+0

如果您有一个未初始化的final变量,那么不会显示错误消息吗?当一个'final'变量在ctor中初始化时? – msrd0 2014-10-12 14:49:27