为什么注释字符串值不实习? [英] Why are annotation string values not interned?

查看:30
本文介绍了为什么注释字符串值不实习?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

尽管重用了字符串常量和文字,以下代码段仍打印了 4 个不同的哈希代码.为什么字符串值不在注释元素中?

The following snippet prints 4 distinct hash codes, despite reusing a string constant and literal. Why are string values not interned on annotation elements?

public class Foo {
    @Retention(RetentionPolicy.RUNTIME)
    @interface Bar {
        String CONSTANT = "foo";

        String value() default CONSTANT;
    }

    public static void main(String[] args) throws Exception {
        System.out.println(System.identityHashCode(Bar.CONSTANT));
        System.out.println(System.identityHashCode(Foo.class.getMethod("test1").getAnnotation(Bar.class).value()));
        System.out.println(System.identityHashCode(Foo.class.getMethod("test2").getAnnotation(Bar.class).value()));
        System.out.println(System.identityHashCode(Foo.class.getMethod("test3").getAnnotation(Bar.class).value()));
    }

    @Bar
    public void test1() {}

    @Bar("foo")
    public void test2() {}

    @Bar(Bar.CONSTANT)
    public void test3() {}
}

推荐答案

字符串字面量是固定的,但注释需要解析,并且它们存储在字节数组中.如果您查看 java.lang.reflect.Method 类,您可以看到:

String literal are interned but annotations are subject to parse and they are stored in byte arrays. If you look at the class java.lang.reflect.Method you can see this:

private byte[]              annotations;
private byte[]              parameterAnnotations;
private byte[]              annotationDefault;  

再看看同一个类的public Object getDefaultValue()方法,看看AnnotationParser是如何调用的.流程一直持续到这里AnnotationParser.parseConst 并输入

Take also a look at the method public Object getDefaultValue() of the same class to see how the AnnotationParser is called. The flow continues till here AnnotationParser.parseConst and enter in

case 's':
  return constPool.getUTF8At(constIndex);

方法 ConstantPool.getUTF8At 是本地方法的委托.您可以在此处查看代码 本机实现获取UFT8At.解析的常量永远不会被实习,也永远不会从 StringTable(字符串被实习的地方)中检索.

The method ConstantPool.getUTF8At is a delegate to a native method. You can see the code here native implementation getUFT8At. The parsed constant is never interned and is never retrieved from the StringTable (where string are interned).

我认为这可能是实现的一种选择.创建实习是为了在字符串文字之间进行更快速的比较,因此仅用于可在方法实现中使用的实习文字.

I think it could be a choice of implementation. Interning has been created to make more fast comparison between String literal and so is used only for interning literal usable in method implementation.

这篇关于为什么注释字符串值不实习?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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