Java 为什么类文件不包含足够的信息来提供NPE中为null的指针的名称?

Java 为什么类文件不包含足够的信息来提供NPE中为null的指针的名称?,java,nullpointerexception,.class-file,Java,Nullpointerexception,.class File,在答复中,他说: 否,类文件中的调试信息没有包含足够的信息来允许此操作 我的问题是,为什么不呢?实际的异常指向一条特定的字节码指令,但一条语言语句可能会扩展成几十条指令,并引用六个不同的指针。此外,指针可能在几个指令期间一直保存在临时存储器(字节码堆栈)中,因此与特定变量名的关联可能会丢失 一个花哨的调试器可以对“出错”的变量做出公正的猜测,但是,一般来说,指向失败的语句应该足够了(尽管要记住,失败可能是由于之前的语句延迟了操作)。它可能根本不是一个变量:它可能是一个临时结果,例如,方法调用的结

在答复中,他说:

否,类文件中的调试信息没有包含足够的信息来允许此操作


我的问题是,为什么不呢?

实际的异常指向一条特定的字节码指令,但一条语言语句可能会扩展成几十条指令,并引用六个不同的指针。此外,指针可能在几个指令期间一直保存在临时存储器(字节码堆栈)中,因此与特定变量名的关联可能会丢失


一个花哨的调试器可以对“出错”的变量做出公正的猜测,但是,一般来说,指向失败的语句应该足够了(尽管要记住,失败可能是由于之前的语句延迟了操作)。

它可能根本不是一个变量:它可能是一个临时结果,例如,方法调用的结果。当NPE出现时,它只是一个匿名堆栈槽。

因为代码中的行号足以跟踪它

从技术上讲,“字节码”指的是所有指令(或指令集本身)。那么,我是否可以建议堆栈跟踪无法报告NPE的原因与特定的解引用相关,因为考虑到获取此信息的其他方式(在调试器中复制和通过检查),这样做所需的开销被认为是不合理的?@KenTaylor-我认为,在JDK第一次被发明时,开发人员需要付出的努力比他们想要花费的要多,而且从那时起,就没有足够的需要克服改变JDK规范的固有阻力。(坦率地说,这个问题几乎不值一文——一旦我把它归结为一个具体的陈述,我就很少有困难找出空值的来源。)“需要付出的努力……比他们想要的更多”是我所说的“需要的开销……不被认为是有保证的”。我觉得这个问题值得讨论,因为我经常发现我无法重现一个只具有堆栈跟踪且被解引用的变量都不应为null的活动问题;我不想在解引用时检查null-我想追溯到引入null的位置并阻止它发生。如果我现在到底什么是空的,这缩小了搜索范围。@KenTaylor-问题是,即使你知道哪个变量是空的,你也不知道为什么,这通常是一个更困难的问题。在一个给定的语句中,有多个引用可以为空的情况实际上相当罕见,但这对于一个空引用在某段遥远的代码(时间和位置)中被设置为空。这个问题没有解决方法。请注意“方法调用的结果”确实有调试器应该知道的特定类。@JanDvorak当然知道,但问题是关于堆栈跟踪,而不是调试器。@JanDvorak所有这些问题都是针对我的吗?你似乎只是在和自己争论。相关的事实是类文件不一定包含局部变量名,而那个变量在任何情况下,名称都不是唯一的可能,这些都足以回答这个问题。@EJP:NPE可能不是对变量进行解引用的结果。但我们可以这样说。堆栈跟踪具有报告方法和行号的信息,但无法保留变量的名称(JD推测上面哪些是可用的信息)?奇怪的是,在我看来,所有必要的信息都可以在那里。也就是说,每个方法都有可选的
LocalVariableTable
LocalVariableTypeTable
(后者自Java 5以来)属性()。如果调试器中NPE上的断点,您将能够看到哪个值是
null
@JanDvorak-yesp,调试器可以更详细地了解情况,如果他们认为这是值得的。无需更改JVM。