jep122_JEP 181不兼容,嵌套类/ 2

jep122

JEP 181是基于嵌套的访问控制https://openjdk.java.net/jeps/181 。 它是在Java 11中引入的,它故意引入了与先前版本的不兼容性。 这是一个很好的例子,与Java的早期版本兼容并不是刻板的规则,而是保持语言的一致性和稳定发展。 在本文中,我将通过几年前遇到的一个示例来研究这种变化,以及在这种特殊情况下Java 11如何使生活更轻松,更一致。

Java向后兼容性仅限于功能而非行为

原始情况

几年前,当我编写可以用Java方法扩展的ScriptBasic for Java解释器时,使它们就像用BASIC编写一样可用,我创建了一些单元测试。 单元测试类包含一些内部类,其中具有一些可用于BASIC代码的方法。 内部类是静态的和私有的,因为它与除测试之外的任何其他类无关,但是,该类和方法仍可被测试代码访问,因为它们位于同一类中。 令我沮丧的是,这些方法无法通过BASIC程序访问。 当我尝试通过本身使用反射访问的BASIC解释器调用方法时,出现了IllegalAccessException

为了纠正这种情况,经过几个小时的调试和学习,我创建了以下简单代码:

package javax0;import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;public class ReflThrow {private class Nested {private void m(){System.out.println("m called");}}public static void main(String[] args)throws NoSuchMethodException,InvocationTargetException,IllegalAccessException {ReflThrow me = new ReflThrow();Nested n = me.new Nested();n.m();Method m = Nested.class.getDeclaredMethod("m");m.invoke(n);}
}

如果使用Java N(其中N <11)运行此代码,则会得到类似以下内容:

m called
Exception in thread "main" java.lang.IllegalAccessException: class ReflThrow cannot access a member of class ReflThrow$Nested with modifiers "private"at java.base/jdk.internal.reflect.Reflection.throwIllegalAccessException(Reflection.java:423)at java.base/jdk.internal.reflect.Reflection.throwIllegalAccessException(Reflection.java:414)
...

但是,它可以在Java 11上正常运行(并且大概在更高版本的Java中也可以正常运行)。

说明

直到Java 11版本,JVM都不处理内部和嵌套类。 JVM中的所有类都是顶级类。 Java编译器从内部和嵌套类创建一个特别命名的顶级类。 例如,一个Java编译器可以创建类文件ReflThrow.classReflThrow$Nested.class 。 因为它们是JVM的顶级类,所以当ReflThrow类是两个不同的顶级类时,它们中的代码无法调用Nested的私有方法m()

但是,在Java级别,从嵌套结构创建这些类是可能的。 为了实现这一点,编译器在Nested类中创建了一个额外的合成方法, ReflThrow中的代码可以调用该方法,而Nested已经存在的该方法将调用m()

合成方法具有修饰符SYNTHETIC因此编译器随后知道其他代码不应“看到”这些方法。 这样,调用方法m()效果很好。
另一方面,当我们尝试使用名称和反射访问来调用方法m() ,路由直接通过类边界,而无需调用任何合成方法,并且由于该方法对于它所在的类是私有的,因此调用引发异常。

Java 11对此进行了更改。 包含在已经发布的Java 11中的JEP 181引入了概念嵌套。 “嵌套允许类在逻辑上属于同一代码实体,但被编译成不同的类文件,而无需编译器插入可扩展访问性的桥方法,即可访问彼此的私有成员。” 它仅表示存在作为嵌套的类,并且存在属于嵌套​​的类。 从Java生成代码时,顶级类是嵌套类,而内部的类是嵌套的。 JVM级别的此结构为不同的语言结构留有很大空间,并且不会在执行环境中出现Java结构的麻烦。 JVM旨在成为多语言的,并且随着将来GraalVM的推出,它甚至将成为“更多”的多语言。 使用这种结构的JVM仅仅看到两个类在同一个嵌套中,因此它们可以互相访问private方法,字段和其他成员。 这也意味着没有桥接方法具有不同的访问限制,并且反射与普通的Java调用完全通过相同的访问边界。

摘要/外卖

Java不会一夜之间发生变化,并且大部分是向后兼容的。 但是,向后兼容性仅限于功能而非行为。 JEP181没有,并且它从未真正打算重现对嵌套类的反射访问的并非绝对完美的IllegalAccessException抛出行为。 此行为是实现行为/错误,而不是语言功能,并且已在Java 11中修复。

翻译自: https://www.javacodegeeks.com/2018/10/jep-181-incompatibility-nesting-classes.html

jep122

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/333205.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

文档中快速输入日期时间的方法

文章目录word文档excel表格日期输入后固定不变日期输入后会根据系统变化的输入法快速输入日期时间&#xff08;推荐&#xff09;word文档 输入 ctrl;&#xff0c;就可以直接输入当前日期 输入 ctrlshift;&#xff0c;就可以直接输入当前时间 如果是输入当前日期和时间&#xf…

=空值返回空值_@ParameterizedTest在@CvsSource中具有空值

空值返回空值在JUnit 4中编写参数化测试非常麻烦。 JUnit 5对框架进行了一些有用的改进&#xff0c;并且使用不同的参数运行相同的测试比以前的版本要简单得多。 但是&#xff0c;在这样的参数中传递空值存在一个小问题。 在本文中&#xff0c;我将向您展示如何在JUnit 5中的P…

MySQL的配置文件_选项文件_参数文件

文章目录WindowsLinux使用命令 locate 查找含有关键词 my.cnf 的文件路径查看是否使用了指定目录下的 my.cnf 文件查看 MySQL 默认读取 my.cnf 文件路径启动时没有读取任何配置文件主要的配置参数类似于 Oracle 的参数文件&#xff0c;MySQL 的选项文件&#xff08;即配置文件&…

java url参数转换:_提示:通过URL激活并发送参数

java url参数转换:世界上最安全的密码是不存在的密码。 使用完全随机的密钥从等式中删除用户。 公平地说&#xff0c;这有一些缺点&#xff0c;并且密码仍然存在于某处&#xff08;在您的电话/电子邮件中&#xff09;&#xff0c;但通常这样效果很好... 诀窍很简单&#xff0c…

简单的vue入门案例

一、 简单入门Hello World案例 二、插值表达式 三、点击事件 四、按键事件 1.如果按下不是 0 - 9 则阻止事件执行 2.打印按下什么按键 五、鼠标事件 1.打印绝对坐标 2.打印相对坐标 3.鼠标mousemove 4. 阻止冒泡(阻止事件的传播) 六、事件修饰符 1.阻止跳转页面v-on:submit.…

javafx 调用java_Java,JavaFX的流畅设计风格进度栏

javafx 调用java按照承诺&#xff0c;刚刚发布的Java JavaFX主题JMetro版本4.6为进度栏带来了新样式。 进度栏有两种可能的状态&#xff1a;确定和不确定&#xff0c;新的JMetro版本针对这两种具有不同的样式。 在本文中&#xff0c;我还将详细介绍我在JMetro中遵守的一些API设…

vue基本用法

一、v-text与v-html.html v-html 可以解析标签&#xff0c;解析样式,v-text不能解析&#xff0c;只能原样输出 二、v-bind绑定参数 v-bind简写方式 <!-- 完整语法 --> <a v-bind:href"url">...</a> <!-- 缩写 --> <a :href"url&q…

类Unix系统下,vim各种模式之间的切换

文章目录普通命令模式插入模式&#xff08;编辑模式&#xff09;临时切换到普通命令模式可视模式&#xff08;文本选择模式&#xff09;底行命令模式&#xff08;EX 命令模式&#xff09;普通命令模式 vim 的默认模式就是普通命令模式&#xff0c; 使用 vim 打开文件就进入普通…

jdk12 switch_玩JDK 12的Switch表达式

jdk12 switch在博客文章“操作中的JDK语言功能预览&#xff1a;切换表达式 ”中&#xff0c;我讨论了JEP 325 [“切换表达式&#xff08; 预览 &#xff09;”&#xff09;如何作为指定的“ 预览语言功能 ”的早期应用&#xff0c;如JEP 12所述。预览语言和VM功能”]。 JEP 325…

VueJS生命周期

一、生命周期 vue在生命周期中有这些状态&#xff0c; beforeCreate,created,beforeMount,mounted,beforeUpdate,updated,beforeDestroy,destroyed。Vue 在实例化的过程中&#xff0c;会调用这些生命周期的钩子&#xff0c;给我们提供了执行自定义逻辑的机会。 vue对象初始化过…

Linux的命令之 man -- 查看帮助文档

文章目录浏览文本内容的快捷键向前滚屏向后滚屏跳跃搜索使用这个命令可以查看任何命令的在线帮助文件&#xff0c;例如&#xff0c;查看命令 find 的在线帮助文档&#xff1a; [roothtlwk0001host ~]# man find打开命令的帮助文档后&#xff0c;可以使用鼠标滚轮上下滚动来浏览…

jdk8切换成jdk6_运行中的JDK语言功能预览:切换表达式

jdk8切换成jdk6JEP 12 [“预览语言和VM功能”]在其主页上描述如下&#xff1a; 预览语言或VM功能是Java SE平台的一项新功能&#xff0c;该功能已完全指定&#xff0c;完全实现但不是永久性的。 JDK功能发布中提供了该功能&#xff0c;以根据实际使用情况激发开发人员反馈。 这…

VueJS ajax综合案例

一、目录结构和注意事项 1.目录结构 2.注意事项 &#xff08;1&#xff09;data.html里面的Vue &#xff08;2&#xff09;箭头函数 二、引入依赖 <?xml version"1.0" encoding"UTF-8"?><project xmlns"http://maven.apache.org/POM/4.0…

Linux 下如何查找 MySQL 数据库的数据根目录呢?

笔者的服务器系统和MySQL版本如下&#xff1a; [roothtlwk0001host ~]# mysql -V mysql Ver 14.14 Distrib 5.7.31, for Linux (x86_64) using EditLine wrapper [roothtlwk0001host ~]# cat /etc/redhat-release CentOS Linux release 8.2.2004 (Core) MySQL 的配置文件路径…

libreoffice_利用Excel或LibreOffice的业务输入进行单元测试约束

libreoffice业务专家向我们&#xff08;开发人员&#xff09;解释业务限制。 但是&#xff0c;如何确保我们正确理解它们呢&#xff1f; 或更糟糕的是&#xff0c;一旦约束条件正式化&#xff0c;我们如何测试他们之间是否同意&#xff1f; 好吧&#xff0c;有一种很棒的方法可…

VueJS ajax综合案例(修改用户信息实现步骤)

修改用户信息 1.过程演示 2.代码实现

MacOS下如何通过命令搜索文件和打开文件

文章目录find 命令查找名称含有指定关键词的文件和目录locate 命令查找以指定字符串结尾的文件路径查看命令 locate 的使用说明mdfind 命令查找名称中含有指定关键词的文件搜索内容中包含指定关键词的文件在指定目录中搜索内容包含指定关键词或者名称含有指定关键词的文件搜索并…

多云和混合云_多云互操作性!=云服务聚合

多云和混合云多云定义为一种方法&#xff0c;该方法将来自多个云供应商的多个云&#xff08;公共云或私有云&#xff09;组合在一起。 但是&#xff0c;这不是来自不同供应商的各种服务的集合&#xff0c;它需要一种强制性的胶合剂–云不可知的方法&#xff0c;并在所有提供商之…

安装、启动、配置zookeeper(window版)

安装zookeeper (1)解压安装包 &#xff08;2&#xff09;修改zoo_sample.cfg文件名为&#xff1a;zoo.cfg (3)在加压文件下建立data文件夹 &#xff08;4&#xff09;修改zoo.cfg (5)启动 注意如果zookeeper启动失败有可能是&#xff0c;第二步的zoo_sample.cfg文件名没改&…

命令终端(CMD)自动补全功能 — Tab Complete 功能

处理特殊字符 如果目录中有特殊字符&#xff08;空格&#xff0c;括号&#xff0c;引号&#xff0c;[]&#xff0c;!&#xff0c;$&#xff0c;&&#xff0c;*&#xff0c;;&#xff0c;|&#xff0c;\&#xff09;&#xff0c;必须使用特殊的语法来表示这些字符。例如&am…