eclipse 在已编译的 Java 类中保留参数/参数名称

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/939194/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-19 13:45:03  来源:igfitidea点击:

Preserving parameter/argument names in compiled java classes

javaeclipsecompilationjavac

提问by Lena Schimmel

When I compile something like this:

当我编译这样的东西时:

public class MyClass
{
    void myMethod(String name, String options, String query, String comment)
    {
        ...
    }
}

and compile this to a class file, it seems that argument names are lost. That is, when some other Java code references MyClassand wants to call or overwrite myMethod, my IDE (currently Eclipse) seems to get this method signature from the class-file:

并将其编译为类文件,似乎参数名称丢失了。也就是说,当其他一些 Java 代码引用MyClass并想要调用或覆盖 时myMethod,我的 IDE(当前为 Eclipse)似乎从类文件中获取此方法签名:

void myMethod(String arg0, String arg1, String arg2, String arg3);

I know that Eclipse (and possibly other IDEs too) allows me to provide a link to the source or the javadoc (as Bishiboosh pointed out)of MyClassand can take advantage of this. But I'm curious if there is some way to tell javacto include the names into the class-file, so that users of that class can see the argument names even if they only have the class file.

我知道 Eclipse(也可能还有其他 IDE)允许我提供指向源代码或 javadoc (正如 Bishiboosh 指出的)的链接MyClass并且可以利用这一点。但是我很好奇是否有某种方法可以告诉javac将名称包含在类文件中,以便该类的用户即使只有类文件也可以看到参数名称。

Solution for classes

课堂解决方案

When I compile a class with java -g:vars, the names of parameters are included in the class file. -g:varsseems to be equivalent to Eclipse -> project properties -> Java compiler -> Add variable attributes to generated class files.

当我用 编译一个类时java -g:vars,参数的名称包含在类文件中。-g:vars好像相当于Eclipse->项目属性->Java编译器->给生成的类文件添加变量属性。

This solution was suggested by several authors, but the answer from Nick finally made me believe.

这个解决方案是由几位作者提出的,但尼克的回答终于让我相信了。

On my machine, Eclipse sometimes used this info, sometimes it didn't, which was probably my fault or a bug in Eclipse, but not a problem with the class files or the compile. Anyway, now I know that the information is definitely present.

在我的机器上,Eclipse 有时使用此信息,有时不使用,这可能是我的错或 Eclipse 中的错误,但不是类文件或编译的问题。无论如何,现在我知道信息肯定存在。

But no solution for interfaces

但是没有接口的解决方案

While this works (kind of) fine for classes, it's not working for interfaces.

虽然这对类工作(有点)很好,但它不适用于接口。

For me, the logical reason seems to be, that -g:vars only provides the names of local variables, which is what the documentation for javac also states. In the body of a method, it's parameters are very similar to local variables, thus they are covered by -g:vars. interface methods don't have bodies, so they can't have local varibles.

对我来说,逻辑上的原因似乎是,-g:vars 只提供了局部变量的名称,javac 的文档也说明了这一点。在方法体中,它的参数与局部变量非常相似,因此它们被 -g:vars 覆盖。接口方法没有主体,所以它们不能有局部变量。

My initial question only asked for classes, because I was not aware that there might be any difference.

我最初的问题只要求上课,因为我不知道可能会有什么不同。

Class file format

类文件格式

As gidpointed out, the class file format does not support storrage of parameter names. I found a section in the class file specthat descibes a data struture which should holf the parameter names of methods, but this is definitely not used when compiling interfaces.

正如gid 所指出的,类文件格式不支持参数名称的存储。我在类文件规范中找到了一个部分,该部分描述了一个数据结构,它应该包含方法的参数名称,但这在编译接口时绝对不会使用。

When compiling a class, I can't tell if the mentioned data structure is used, or if Eclipse infers the parameter names from the usage of parameters inside the method body. An expert could clarify this, but it's not that relevant I think.

编译一个类时,我不知道是否使用了提到的数据结构,或者Eclipse是否从方法体内部参数的使用中推断出参数名称。专家可以澄清这一点,但我认为这并不重要。

采纳答案by Pool

To preserve names in the class file for debugging purposes try project properties, Java compiler, then "Add variable attributes to generated class files" (See Eclipse Help).

要在类文件中保留名称以进行调试,请尝试项目属性、Java 编译器,然后“将变量属性添加到生成的类文件”(请参阅Eclipse 帮助)。

Compiling the following source:

编译以下源码:

public class StackOverflowTest {
    public void test(String foo, String bar) {
        // blah
    }
}

Is decompiled into:

被反编译成:

// Compiled from StackOverflowTest.java (version 1.5 : 49.0, super bit)
public class StackOverflowTest {

    // Method descriptor #6 ()V
    // Stack: 1, Locals: 1
    public StackOverflowTest();
        0  aload_0 [this]
        1  invokespecial java.lang.Object() [8]
        4  return
        Line numbers:
            [pc: 0, line: 1]
        Local variable table:
            [pc: 0, pc: 5] local: this index: 0 type: StackOverflowTest

    // Method descriptor #15 (Ljava/lang/String;Ljava/lang/String;)V
    // Stack: 0, Locals: 3
    public void test(java.lang.String foo, java.lang.String bar);
        0  return
        Line numbers:
            [pc: 0, line: 4]
        Local variable table:
            [pc: 0, pc: 1] local: this index: 0 type: StackOverflowTest
            [pc: 0, pc: 1] local: foo index: 1 type: java.lang.String
            [pc: 0, pc: 1] local: bar index: 2 type: java.lang.String
}

See the parameter names are preserved in the class files.

请参阅参数名称保留在类文件中。

I would suggest you look into how your source is being compiled, which version it is compiled for etc.

我建议你看看你的源代码是如何编译的,它是为哪个版本编译的等等。

EDIT:

编辑:

Ah, I see this is different for interfaces - they don't seem to have this information available for the debugger which I guess makes sense. I don't think there'll be a way round this, if you just want to see the parameter names when you're editing source you'll need to go the javadoc route as Nagrom_17 suggests (attach the source).

啊,我看到这对于接口来说是不同的 - 他们似乎没有为调试器提供这些信息,我认为这是有道理的。我认为没有办法解决这个问题,如果您只想在编辑源代码时查看参数名称,则需要按照 Nagrom_17 的建议(附上源代码)使用 javadoc 路由。

回答by Valentin Rocher

You don't specially need the source to make arg names appear in Eclipse...If you specify the Javadoc, Eclipse will display the args.

您不需要特别需要源代码来在 Eclipse 中显示 arg 名称...如果您指定 Javadoc,Eclipse 将显示 args。

回答by starblue

It might help to compile with debug support, which stores all names in the .class file.

使用调试支持进行编译可能会有所帮助,它将所有名称存储在 .class 文件中。

though I don't know whether Eclipse takes that into account.

虽然我不知道 Eclipse 是否考虑到了这一点。

回答by Gareth Davis

There is no support in the class file data structure for storing the parameter names to any method, no matter what javac options you use.

无论您使用什么 javac 选项,类文件数据结构都不支持将参数名称存储到任何方法。

In order to see the original names in an IDE you have to supply them with either the javadoc or the source.

为了在 IDE 中查看原始名称,您必须向它们提供 javadoc 或源代码。

If you have a particular need to get at them at runtime it is possible to add annotations to parameters, but you'll have to create your own as there isn't a standard set to use.

如果您特别需要在运行时获取它们,则可以向参数添加注释,但您必须创建自己的注释,因为没有可使用的标准集。

Sorry can't be more helpful

抱歉不能更有帮助

EDIT: I stand completely corrected...the class file format does clearly have space for named parameters (JLS 4.7)

编辑:我完全更正了……类文件格式显然有命名参数的空间(JLS 4.7

What I can't see is how the hell you can get at them using java.lang.reflect.*

我看不到的是你怎么能用它们来对付他们 java.lang.reflect.*

回答by Aaron Digulla

Eclipse will pick up the names of arguments if you include debug information in the class file: javac -g:varsshould be enough.

如果您在类文件中包含调试信息,Eclipse 将获取参数的名称:javac -g:vars应该足够了。

回答by MESLewis

You don't need a separate Javadoc file you can create 'inline' javadocs in Eclipse using a special comment with two asterisks(*) after the first slash of a multi-line comment.

您不需要单独的 Javadoc 文件,您可以在多行注释的第一个斜杠后使用带有两个星号 (*) 的特殊注释在 Eclipse 中创建“内联”javadoc。

example code:

示例代码:

   public class MyClass
{
 /**
  * documentation of your method
  * 
  * @param name    a String describing the name
  * @param options used to describe current option
  * @param query
  * @param comment
  * @return void
  */
    void myMethod(String name, String options, String query, String comment)
    {
        ...
    }
}