qiqiblack
qiqiblack
2010-01-25 14:49

虚拟机装载class,interface的疑问

已采纳

近日在《深入Java虚拟机》7.1中看到 如下一段话
"任何一个类的初始化都要求它的超类在此之前已经初始化了。以此类推,该规则就意味着某个类的所有祖先类必须在该类之前被初始化。然而,对于接口来说,[color=red]这条规则并不适用。只有在某个接口所声明的非常量字段被使用时,该接口才会被初始化[/color],而不因为实现这个接口的子接口或类要初始化而初始化"
为不浪费大家的时间,我再三确对了红色部分的内容(不排除书印刷错误)。
这里我就看不懂啦 产生2个疑问
1.接口中的“非常量字段被使用时”,我所了解到的是接口中都是 final static 的 即使不写
2.“该接口才会被初始化”,我开始以为是说 他的实现或者什么的,但后面有句“而不因为实现这个接口的子接口或类要初始化而初始化”。
实在是不明白,望指点!

  • 点赞
  • 写回答
  • 关注问题
  • 收藏
  • 复制链接分享
  • 邀请回答

3条回答

  • rednaxelafx rednaxelafx 11年前

    顶楼引用的[url=http://www.artima.com/insidejvm/ed2/lifetype.html]那段话的原文[/url]是:
    [quote]As mentioned in the previous list, initialization of a class requires prior initialization of its superclass. Applied recursively, this rule means that all of a class's superclasses must be initialized prior to the initialization of the class. The same is not true, however, of interfaces. An interface is initialized only because a non-constant field declared by the interface is used, never because a subinterface or class that implements the interface needs to be initialized. Thus, initialization of a class requires prior initialization of all its superclasses, but not its superinterfaces. Initialization of an interface does not require initialization of its superinterfaces.[/quote]
    这本书的中文翻译本来就很糟糕,看不懂的时候请参考原文。
    顶楼引用的这段翻译倒没什么大问题。描述的状况就是一个类在进行初始化之前,其超类必须已经完成初始化(否则子类的初始化就会触发超类的初始化),但它所实现的接口却不须要已经完成初始化。一个接口在初始化的时候也不要求其超接口已经完成初始化。
    这是由于接口只在它所声明的非常量域被使用时才必须初始化。没错,接口上的成员都是隐式声明为public,接口上的域都隐式声明为static final,但为这些域提供值的初始化表达式却不一定要是“常量表达式”。请参考[url=http://java.sun.com/docs/books/jvms/second_edition/html/Concepts.doc.html#18349]JVM规范第2版2.13.3.1 Interface (Constant) Fields小节[/url]。

    例如
    [code="java"]public interface IFoo {
    int INIT_TIME = System.nanoTime(); // 非常量表达式初始化的域
    int ONE = 1; // 常量表达式初始化的域
    }

    《深入Java虚拟机》7.1节所说的“非常量字段”指的就是这种接口上使用非常量表达式初始化的域。
    之所以会引起混淆是因为Java语言中没有区分编译时常量与运行时不变量,两者都使用final关键字来修饰。在C#里这两个概念就被清晰的分开,编译时常量用const、运行时不变量用readonly关键字来修饰。顶楼所引用的文字说的就是运行时不变量,而楼主心里想的是编译时常量。

    点赞 评论 复制链接分享
  • wocsok wocsok 11年前

    [color=indigo]我个人认为是这样的 它说的 接口初始化 应该是指 用到接口里的常量 在没有枚举类型的时候 咱们不也经常这么用么.
    平常接口的实现类,只是按照这个接口 来实现自己的方法 而没有把接口实例化。[/color]

    点赞 评论 复制链接分享
  • mginobili mginobili 11年前
    1. 非常量字段的意思指 接口的字段是运行时才得到的而非编译期就能得到的吧

    要注意的是 [quote]字段并不是接口的一部分,而是保存于那个接口的static存储区域中[/quote]

    1. 这个意思指A implements B A初始化时 B并未初始化 这个跟 A extends B不同
    点赞 评论 复制链接分享

相关推荐