2011-11-26 130 views
2

主類的名字有沒有辦法找到用來啓動當前JVM的主類的名稱,從在JVM上運行任意代碼?由於任意,我的意思是代碼不一定在主線程中運行,或者可能在main被調用之前在主線程中運行(例如,用戶提供的java.system.classloader中的代碼,它在main之前運行,因爲它用於加載main) - 因此檢查調用堆棧是不可能的。移植的方式找到Java代碼

+0

在JVM上,首先調用主類的主要方法。 (也http://java.sun.com/docs/books/jls/third_edition/html/execution.html#12.1見)那麼,你是什麼意思「可以在主線程中運行的主要甚至被稱爲前」 。我認爲這個短語提到「靜態初始化程序」或「線程#運行()」。 – cocoatomo

+0

@cocoatomo:我錯過了一些東西。該鏈接是否顯示解決原始海報問題的解決方案?如果是這樣,雖然我回顧了一下,但我錯過了它。 –

+0

@Hovercraft全鰻魚:對不起,我錯把推回車鍵我已經完成了我的意見了。我想了解BeeOnRope的意圖,所以我要確保的條件BeeOnRope希望見面。 – cocoatomo

回答

8

這是最接近我可以,你可以把它從這兒過得也不能保證它是真正便攜的,如果任何方法調用的另一種主要方法是行不通class.Let我知道如果你發現更乾淨的解決方案

import java.util.Map.Entry; 

public class TestMain { 

    /** 
    * @param args 
    * @throws ClassNotFoundException 
    */ 
    public static void main(String[] args) throws ClassNotFoundException { 
     System.out.println(findMainClass()); 
    } 

    public static String findMainClass() throws ClassNotFoundException{ 
     for (Entry<Thread, StackTraceElement[]> entry : Thread.getAllStackTraces().entrySet()) { 
      Thread thread = entry.getKey(); 
      if (thread.getThreadGroup() != null && thread.getThreadGroup().getName().equals("main")) { 
       for (StackTraceElement stackTraceElement : entry.getValue()) { 
        if (stackTraceElement.getMethodName().equals("main")) { 

         try { 
          Class<?> c = Class.forName(stackTraceElement.getClassName()); 
          Class[] argTypes = new Class[] { String[].class }; 
          //This will throw NoSuchMethodException in case of fake main methods 
          c.getDeclaredMethod("main", argTypes); 
          return stackTraceElement.getClassName(); 
         } catch (NoSuchMethodException e) { 
          e.printStackTrace(); 
         } 
        } 
       } 
      } 
     } 
     return null; 
    } 
} 
+0

謝謝,我知道這種方法,但不幸的是它不適用於我,因爲它還需要在包含main的類加載之前工作(請參閱我的評論添加到類加載器的問題)。 – BeeOnRope

+0

無論如何都要接受這個問題,因爲它確實是對的,如果我願意推遲基於主類的工作,我可以使用它。 – BeeOnRope

+0

順便說一句,如果你想避免更多的誤報,我想你可以看看調用main的類,並驗證它是一個期望的JDK特定類 - 儘管這會引入對特定JDK或JDK的依賴。 – BeeOnRope