作者
John Zukowski
翻譯
Roger Sun
原文來源
#
譯文地址
bin/forum/topic
cgi?forum=
&topic=
==============================================
JAR文件是打包基於JAVA技術的解決方案的標准方法
它允許開發者將所有相關內容(
class
圖片
聲音
及所有支持的文件)打包到一個文件中
JAR格式支持壓縮
認證
版本號及其他很多特性
從JAR文件中讀取文件是很麻煩的事情
但是也不一定全是這樣
本文將告訴你如何從JAR文件中讀取文件
首先
得到JAR文件中的文件目錄
然後在進行具體的某一個文件的操作
如果你對於常用的ZIP格式比較熟悉的話
JAR文件也就差不多
JAR文件提供一種將多個文件打包到一個文件中的方法
其中每一個文件可能獨立地被壓縮
JAR文件所增加的內容是manifest
它允許開發者可以提供附加的關於內容的信息
例如
manifest表明JAR文件中的哪個文件是用來運行一個程序的
或者庫的版本號等
J
SEDK提供了一個jar工具
你可以用它從控制台讀寫JAR文件
然而
如果你需要在程序中代碼讀寫JAR文件
可能需要一點時間(本文只包含如何在程序中讀寫JAR文件)
好消息是你可以做到這一點
而且你不用擔心解壓的事
因為類庫將幫助你完成這些
你所需要的類文件位於java
util
jar包中
這裡主要的類是JarFile
它是
jar文件自身的一個引用
較大文件中的每一個單獨的文件是通過一個JarEntry引用的
首先
通過把將JAR文件位置傳給構造函數
創建一個JarFile的實例
位置可能是String或File的形式
如下
JarFile jarFile = new JarFile(
thefile
jar
);
或者
File file = new File(
thefile
jar
);
JarFile jarFile = new JarFile(file);
你可能注意到當文件不在class path中時
JarFile類對於從JAR中讀取文件文件是很有用的
當你想指定目標JAR文件時
JarFile類對於從JAR中讀取文件同樣也很有用
當然
如果JAR文件在class path中
從其中讀取文件的方法比較簡單
你可以用下面的方法
URL url = ClassLoader
getSystemResource(name);
或者
InputStream stream =
ClassLoader
getSystemResourceAsStream(name);
這種技術允許你從在class path中的JAR文件裡讀取文件
你不必指定JAR文件名
還有其他的構造函數
如認證支持
標志要刪除的文件等
這些構造函數在這兒不做說明
當你有了該JAR文件的一個引用之後
你就可以讀取其文件內容中的目錄信息了
JarFile的entries方法返回所有entries的枚舉集合(Enumeration)
通過每一個entry
你可以從它的manifest文件得到它的屬性
任何認證信息
以及其他任何該entry的信息
如它的名字或者大小等
Enumeration enum = jarFile
entries();
while (enum
hasMoreElements()) {
process(enum
nextElement());
}
正如前面提到的
每一個entry是一個JarEntry
該類有getName
getSize
getCompressedSize等方法
下面
讓我們舉例說明在程序中如何使用這些特性
下面的程序顯示你指定的JAR文件中內容的名稱
大小
壓縮大小等(這有點類似於在使用jar命令時
指定
t
和
v
選項)
import java
io
*;
import java
util
*;
import java
util
jar
*;
public class JarDir {
public static void main (String args[])
throws IOException {
if (args
length !=
) {
System
out
println(
Please provide a JAR filename
);
System
exit(
);
}
JarFile jarFile = new JarFile(args[
]);
Enumeration enum = jarFile
entries();
while (enum
hasMoreElements()) {
process(enum
nextElement());
}
}
private static void process(Object obj) {
JarEntry entry = (JarEntry)obj;
String name = entry
getName();
long size = entry
getSize();
long compressedSize = entry
getCompressedSize();
System
out
println(
name +
\t
+ size +
\t
+ compressedSize);
}
}
如果你用J
SE
中的jce
jar作為參數運行上面的JarDir程序
你將看到類似於下面的輸出(
部分為省略掉的輸出)
META
INF/MANIFEST
MF
META
INF/
JCEJARS
SF
META
INF/
JCEJARS
DSA
META
INF/
javax/
javax/crypto/
javax/crypto/interfaces/
javax/crypto/interfaces/DHKey
class
javax/crypto/interfaces/DHPublicKey
class
javax/crypto/interfaces/DHPrivateKey
class
javax/crypto/interfaces/PBEKey
class
javax/crypto/SecretKey
class
注意輸出最開始的META
INF行
這是manifest和安全認證信息
字節的entries不是文件
但是有點相當於目錄
為了從JAR文件中真正讀取一個指定的文件
你必須到其entry的InputStream
這和JarEntry不一樣
這是因為JarEntry只是包含該entry的有關信息
但是並不實際包含該entry的內容
這和File和FileInputStream的區別有點兒相似
訪問文件沒有打開文件
它只是從目錄中讀取了該文件的信息
下面是如何得到entry的InputStream
InputStream input = jarFile
getInputStream(entry);
當你有了輸入流
你就可以像讀取其他流一樣讀取它
在文本流中(text stream)
記得使用讀取器(Reader)從流中取得字符
對於面向字節的流
如圖片文件
直接讀取就行了
下面的程序演示如何從JAR文件中讀取文件
指定JAR文件的名稱
要讀取的文件的名稱(打包JAR文件中的某一個文件)作為參數來調用該程序
要讀取的文件應該有一個文本類型的
import java
io
*;
import java
util
jar
*;
public class JarRead {
public static void main (String args[])
throws IOException {
if (args
length !=
) {
System
out
println(
Please provide a JAR filename and file to read
);
System
exit(
);
}
JarFile jarFile = new JarFile(args[
]);
JarEntry entry = jarFile
getJarEntry(args[
]);
InputStream input = jarFile
getInputStream(entry);
process(input);
jarFile
close();
}
private static void process(InputStream input)
throws IOException {
InputStreamReader isr =
new InputStreamReader(input);
BufferedReader reader = new BufferedReader(isr);
String line;
while ((line = reader
readLine()) != null) {
System
out
println(line);
}
reader
close();
}
}
假設在myfiles
jar文件中有一個spider
txt文件
spider文件的內容如下
The itsy bitsy spider
Ran up the water spout
Down came the rain and
Washed the spider out
你可以通過下面的命令來顯示該文本文件的內容
java JarRead myfiles
jar spider
txt
有關JAR文件的更多內容
請參考JAR文件規范
From:http://tw.wingwit.com/Article/program/Java/hx/201311/26791.html