2011-09-06 80 views
1

我剛剛問了一個關於分發可執行JAR及其依賴關係的最新問題,這讓我意識到我對JAR的理解可能存在根本性缺陷。編譯Java和JAR

因此,有些人可能會說:「嘿現在!這這裏是一個重複的問題!」但是我會拒絕,這個問題的this 原來的問題一個完全獨立的分支,並涉及Java的基礎!

如果我有一個依賴於Apache Commons CLI和JODA Time的應用程序,並且將此應用程序打包爲可分發的JAR,我的原始問題是:不包括CLI和JODA JAR我的JAR,程序如何在客戶端運行?

我現在在想,因爲我的代碼使用CLI和JODA編譯到類文件中,並且字節碼是打包的,所以不需要包含CLI或JODA(或任何其他第三方JAR )在我的JAR中,因爲它現在都在運行字節碼。

有人可以確認或糾正我嗎?這個啓示雖然很晚,但卻令人震驚。

+0

一個的* .jar *是你應該在包裝罐中的清單文件中指定的類路徑基本上是一個* .zip *,所以我建議你通過解壓幾個* .jar *然後看看裏面是什麼來自己做實驗。請注意,您可以**將「罐子放在罐子裏」*,但是您需要編寫自己的類加載器(或者使用一個程序來完成這一切)。另一種方法是將你所依賴的* .class *(*即*字節碼)放在你的* .jar *文件中(不推薦,但它可以工作)。 – SyntaxT3rr0r

+0

你的應用程序。有一個GUI? –

+0

@Mara:btw你的* .class *文件不包含整個CLI和JODA庫。 .class文件具有依賴性:您需要在* .jar *或CLI和JODA *中使用來自CLI和JODA的.class文件。jar *某處。運行* .jar *時,這些依賴關係將得到解決(或嘗試解決)。如果你有自己的類加載器,默認的類加載器將檢查幾個地方(在路徑中,在你的*。jar *中,在jar中的jar中)等,並看看它是否能解決你的依賴。 – SyntaxT3rr0r

回答

1

不,這不太對。一切的關鍵是類路徑。是類路徑中的所有編譯代碼和/或其他資源?如果您將所有資源打包在一個jar文件中,那麼是的,它位於classpath中,JVM將定位所有要運行的資源。否則,您需要指定(使用.bat或.sh文件或其他東西)應用程序所依賴的所有資源,以便JVM能夠適當地查找這些資源(無論是Java代碼或屬性文件還是其他任何資源)。

另外,如果我正在閱讀你的問題,你是否假設CLI和JODA代碼被編譯到你的代碼中?如果是這樣,我不想破壞你的泡沫,但事實並非如此。當你的代碼編譯時,它不會引入依賴關係(不是你可能會想到的)。它在概念層面上做了什麼(糾正我,如果我錯了JVM大師)是否引用其他類。這些引用是您編寫類並編譯它時構建的內容。在運行時,JVM將嘗試在引用後面定位已編譯的類,並且這是您需要帶有類路徑中的這些類的jar或者需要那些可執行jar中的類的地方。

有意義嗎?

+0

Chris thios確實有道理 - 謝謝!但是現在我想我很困惑,我不知道該怎麼問......在Eclipse中,我在類路徑中擁有所有的JAR,因此Eclipse知道如何鏈接到所有正確的資源。在我的Ant build.xml文件中,如何將JAR添加到類路徑中(從Ant內部),以便當我的可執行JAR作爲獨立命令行工具運行時,一切正常? – IAmYourFaja

+0

Java使用類路徑知道在哪裏查找.class文件。通常,將.jar文件添加到類路徑中,Java將加載這些文件。您可以通過幾種不同的方式設置課程路徑。對於你的情況,你應該在MANIFEST.MF文件中設置'Class-Path'屬性。螞蟻可以在這裏幫助你。只需在'jar'任務中添加一個'manifest'元素並設置'Main-Class'和'Class-Path'屬性即可。有關更多詳細信息,請參閱http://ant.apache.org/manual/Tasks/jar.html –