Java编译器使用什么搜索顺序来解析以下类中的Foo
?
class Test
{
Foo f;
}
经验测试揭示了以下搜索顺序:
但我想知道Java Language Specification中讨论的内容。
答案 0 :(得分:3)
我认为你的意思并不存在搜索顺序。相反,我认为这条规则适用:
6.5.5类型名称的含义分类为a的名称的含义 TypeName的确定如下。6.5.5.1简单类型名称如果类型名称由单个标识符组成, 那么标识符必须出现在 一个可见的范围 声明具有此名称的类型, 或发生编译时错误。该 类型名称的含义就是那种类型。
在此上下文中,import作为声明计算;见JLS 6.1。然而,复杂的因素是影子规则(JLS 6.3.1),它说某些类型的声明(在这种情况下是类型)隐藏了现有的声明,而其他声明则没有。具体而言,“按需导入”(例如import java.util.*;
或隐式导入java.lang.*
)不会影响其他声明。
所以例如;
package foo;
import java.sql.Date;
import java.util.*; // import on demand: java.util.Date does not shadow java.sql.Date
import java.awt.*; // import on demand: java.awt.List does not shadow java.util.List
class Integer { // (foo.)Integer shadows java.lang.Integer
...
static class Integer { // (foo.Integer.)Integer shadows foo.Integer.
...
List t = ... // Compilation error, because there are currently two visible
// declarations of List (JLS 6.5.5.1)
}
}
另一个问题是,“单一类型导入”(如上面的import java.sql.Date;
)阴影类型在同一个包中声明,类型是按需导入的,但它不会影响通过另一个导入的其他类型“单一类型导入“(JLS 6.3.1)。例如,以下是编译错误:
import java.sql.Date;
import java.util.Date; // Compilation error
答案 1 :(得分:2)
它应遵循与Scope of Local Variable Declarations中提供的不同范围相同的顺序。
编辑:我对JVM规范的链接指的是执行阶段,而不是编译阶段,由OP Gili
评论由于这不是一个完整的答案,我把它留在这里作为CW来启动线程。