我发现了以下问题: $0 (Program Name) in Java? Discover main class? 但接受的答案在这种情况下失败了:
public class Derived extends Base { }
class Base {
public static void main(String[] args){
System.out.println(getTheClassName());
}
static String getTheClassName(){
StackTraceElement[] stack = Thread.currentThread().getStackTrace();
StackTraceElement main = stack[stack.length - 1];
return main.getClassName();
}
}
致电:
java Derived
不幸的是,Base
输出不是Derived
。
是否可以获得真正的主类的名称? (btw。jps
工具正确检测主类,但要获得正确的名称,我需要知道当前VM的ID,这也是一个问题)
最好的问候。
编辑:准确地说:我需要知道传递给JVM的命令行参数传递的类的名称是什么。 jps
工具以我想要的方式执行,但由于其他问题(例如未知的VMid),我无法使用此工具。
Edit2:全球回复Thorbjørn的回答:
对于您的工作方法,您需要使用非静态方法。做了 非静态的,在Derived中有一个main()做一个新的Derived()。getTheClassName()
我想知道如果不在Derived类中实现main方法,我就可以得到这个名字。
解决方案:我将提供Derived
类初始化的(Thorbjørn和erickson)机制;-)所有答案都非常有用。我接受了Thorbjørn,因为他早于Erickson发布了他的回答。谢谢。
答案 0 :(得分:5)
静态方法属于它们所定义的类,而不属于类的实例(与静态/非静态方法相同)。因此,当您在getTheClassName中时,您处于Base类中定义的静态方法中。
对于您的工作方法,您需要使用非静态方法。使它成为非静态的,在Derived中有一个main()做一个新的Derived()。getTheClassName()
答案 1 :(得分:3)
当Derived
入口点在main
时,您为什么期望Base
?声明为static
的成员属于类,不会继承。按原样运行程序时,甚至不会加载类Derived
,因为它从未被引用。
考虑将派生类的名称作为Base
类的参数。除了使目标类明确外,它可能是实现其他功能的一个方便的地方。
class Base {
public static void main(String... argv) throws Exception {
Class<?> clz = Class.forName(argv[0]);
Method mth = clz.getMethod("main", String[].class);
String[] sub = new String[argv.length - 1];
System.arraycopy(argv, 1, sub, 0, sub.length);
mth.invoke(null, sub);
}
}
答案 2 :(得分:1)
试试这个:
for(final Map.Entry<String, String> entry : System.getenv().entrySet()){
if(entry.getKey().startsWith("JAVA_MAIN_CLASS"))
return entry.getValue();
}
但你仍然应该看看别人的答案。即使这样有效,这也是一种非常糟糕的做法。