我知道一个枚举
enum Year
{
First, Second, Third, Fourth;
}
被转换成
final class Year extends Enum<Year>
{
public static final Year First = new Year();
public static final Year Second = new Year();
public static final Year Third = new Year();
public static final Year Fourth = new Year();
}
当我尝试实例化枚举(而不是类)时,我收到编译时错误:
error: enum types may not be instantiated
Year y = new Year();
据我所知,私有构造函数使类不可实例化。我认为编译器提供了一个私有构造函数。但当看到我们可以使用默认修饰符为枚举定义构造函数但仍然无法创建枚举类型的对象时,我再次感到困惑。
enum Year
{
First, Second, Third, Fourth;
Year()
{
}
}
class Example
{
public static void main(String[] args)
{
Year y = new Year();
}
}
我的疑问是,如果它与构造函数无关,那么是什么使得 Java 中的枚举不可实例化?
它被指定在Java语言规范 https://docs.oracle.com/javase/specs/jls/se8/html/index.html:
8.9。枚举类型 https://docs.oracle.com/javase/specs/jls/se8/html/jls-8.html#jls-8.9
...
除了由其枚举常量定义的实例之外,枚举类型没有任何实例。尝试显式实例化枚举类型是一个编译时错误(第 15.9.1 节)。
因此compiler确保满足此要求。由于编译器“知道”该类型是enum
,它可以区分enum Year
and final class Year
.
此外,枚举构造函数不允许访问修饰符:
8.9.2.枚举体声明 https://docs.oracle.com/javase/specs/jls/se8/html/jls-8.html#jls-8.9
...
如果枚举声明中的构造函数声明是公共的或受保护的,则会出现编译时错误。
...
在枚举声明中,没有访问修饰符的构造函数声明是私有的.
因此,在实践中,enum
构造函数看起来像是包范围的(没有访问修饰符),但它确实是私有的。
最后,同一节还指出
在没有构造函数声明的枚举声明中,隐式声明了默认构造函数。默认构造函数是私有的,没有形式参数,也没有 throws 子句。
这使得enum
即使没有显式声明构造函数,也是不可实例化的。
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)