如何为 Java 6 枚举实现 values()? [英] How is values() implemented for Java 6 enums?

查看:24
本文介绍了如何为 Java 6 枚举实现 values()?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在 Java 中,您可以按如下方式创建枚举:

In Java, you can create an enum as follows:

public enum Letter {
    A, B, C, D, E, F, G;

    static {
       for(Letter letter : values()) {
          // do something with letter
       }
    }
}

这个问题与values()"方法有关.具体是如何实施的?通常,我可以在 Eclipse 中使用 F3 或 CTRL+Click 跳转到 Java 类的源代码(甚至对于像 String、Character、Integer 甚至 Enum 这样的类).可以查看其他枚举方法的来源(例如,valueOf(String)).

This question concerns the "values()" method. Specifically, how is it implemented? Usually, I could jump to the source for Java classes using F3 or CTRL+Click in Eclipse (even for classes like String, Character, Integer, and even Enum). It is possible to view the source of the other enum methods (e.g., valueOf(String)).

values()"每次被调用时都会创建一个新数组吗?如果我将它分配给一个局部变量,然后修改其中一个元素,会发生什么(显然这不会影响 values() 返回的值,这意味着每次分配一个新数组).

Does "values()" create a new array each time it is invoked? If I assign it to a local variable and then modify one of the elements, what happens (clearly this won't affect the value returned by values(), which implies that a new array is allocated each time).

它的代码是原生的吗?还是JVM/编译器有没有特殊处理,只有在不能证明不会被修改的情况下才从values()返回一个新的实例.

Is the code for it native? Or does the JVM / compiler treat it specially, only returning a new instance from values() when it cannot prove that it will not be modified.

推荐答案

基本上,编译器 (javac) 在编译时将枚举转换为包含所有值的静态数组.当您调用 values() 时,它会为您提供此数组的 .clone'd() 副本.

Basically, the compiler (javac) translates your enum into a static array containing all of your values at compile time. When you call values(), it gives you a .clone'd() copy of this array.

鉴于这个简单的枚举:

public enum Stuff {
   COW, POTATO, MOUSE;
}

你其实可以看看Java生成的代码:

You can actually look at the code that Java generates:

public enum Stuff extends Enum<Stuff> {
    /*public static final*/ COW /* = new Stuff("COW", 0) */,
    /*public static final*/ POTATO /* = new Stuff("POTATO", 1) */,
    /*public static final*/ MOUSE /* = new Stuff("MOUSE", 2) */;
    /*synthetic*/ private static final Stuff[] $VALUES = new Stuff[]{Stuff.COW, Stuff.POTATO, Stuff.MOUSE};

    public static Stuff[] values() {
        return (Stuff[])$VALUES.clone();
    }

    public static Stuff valueOf(String name) {
        return (Stuff)Enum.valueOf(Stuff.class, name);
    }

    private Stuff(/*synthetic*/ String $enum$name, /*synthetic*/ int $enum$ordinal) {
        super($enum$name, $enum$ordinal);
    }
}

您可以通过创建一个临时目录并运行来查看 javac 如何翻译"您的类:

You can look at how javac 'translates' your classes by making a temporary directory and running:

javac -d <output directory> -XD-printflat filename.java

这篇关于如何为 Java 6 枚举实现 values()?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆