7

我正在试验 Java 9 并查看以下场景:

实验一

  • 模块 A
  • 模块 B
  • 两者都声明了一个名为 com.foo 的非空包,但不导出它
  • 两者都是第三个模块 C 所必需的

从“C”运行 main 会产生运行时错误:

java.lang.RuntimeException:在模块 B 和模块 A 中都包 com.foo

实验二

和以前一样,但这次都导出 com.foo。

从 C 执行 main 的结果:

java.lang.module.ResolutionException:模块 B 和 A 将包 com.foo 导出到模块 C

实验三

与 2 相同,但这次我在模块 C 中声明了包 com.foo。

现在我得到一个编译错误: Error:(4, 1) java: module C reads package com.foo from both A and B

为什么在编译过程中也没有发现前两种情况?在执行程序之前是否有我不知道的运行时属性排除解决方案?

此外,就错误消息而言:实验 2 中的错误消息比实验 1 中给出的错误消息以何种方式更好。并不是说如果其中一个模块不导出它,最终结果会有所不同. 换句话说,产生不同错误信息背后的考虑是什么?

4

1 回答 1

7

实验#2 和#3 是拆分包问题,应该是编译时和运行时的错误。对于#2,我无法从您的帖子中看出为什么您在编译 C 时没有看到编译错误。您应该会看到带有“模块 C 从 A 和 B 读取包 com.foo”之类的错误。

实验 #1 可能是应用程序模块路径上的 A、B 和 C,由于重叠的包,它们不能都存在于相同的名称空间(相同的类加载器)中。您看到的错误消息在最近的版本中有所改进。

请注意,这里的实验已经在jigsaw-dev上的许多线程中讨论过,这可能是提出问题和经验的更好地方,至少在 JDK 9 仍在开发中时。

于 2017-03-28T07:25:18.760 回答