📄 tij0115.html
字号:
use of the compression classes is straightforward – you simply wrap your
output stream in a
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>GZIPOutputStream</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
or
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>ZipOutputStream</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
and your input stream in a
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>GZIPInputStream</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
or
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>ZipInputStream</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">.
All else is ordinary IO reading and writing. This is, however, a good example
of when you’re forced to mix the old IO streams with the new:
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>in</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
uses the
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Reader</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
classes, whereas
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>GZIPOutputStream</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">’s
constructor can accept only an
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>OutputStream</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
object, not a
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Writer</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
object.
</FONT><a name="_Toc408018636"></a><P></DIV>
<A NAME="Heading341"></A><H3 ALIGN=LEFT>
Multi-file
storage with Zip
</H3>
<DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">The
Java 1.1<A NAME="Index1293"></A>
library that supports the Zip format is much more extensive. With it you can
easily store multiple files, and there’s even a separate class to make
the process of reading a Zip file easy. The library uses the standard Zip
format so that it works seamlessly with all the tools currently downloadable on
the Internet. The following example has the same form as the previous example,
but it handles as many command-line arguments as you want. In addition, it
shows the use of the <A NAME="Index1294"></A></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Checksum</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
classes to calculate and verify the checksum for the file. There are two
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Checksum</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
types: <A NAME="Index1295"></A></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Adler32</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
(which is faster) and <A NAME="Index1296"></A></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>CRC32</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
(which is slower but slightly more accurate).
</FONT><P></DIV>
<font color="#990000"><PRE><font color="#009900">//: ZipCompress.java</font>
<font color="#009900">// Uses Java 1.1 Zip compression to compress</font>
<font color="#009900">// any number of files whose names are passed</font>
<font color="#009900">// on the command line.</font>
<font color="#0000ff">import</font> java.io.*;
<font color="#0000ff">import</font> java.util.*;
<font color="#0000ff">import</font> java.util.zip.*;
<font color="#0000ff">public</font> <font color="#0000ff">class</font> ZipCompress {
<font color="#0000ff">public</font> <font color="#0000ff">static</font> <font color="#0000ff">void</font> main(String[] args) {
<font color="#0000ff">try</font> {
FileOutputStream f =
<font color="#0000ff">new</font> FileOutputStream("test.zip");
CheckedOutputStream csum =
<font color="#0000ff">new</font> CheckedOutputStream(
f, <font color="#0000ff">new</font> Adler32());
ZipOutputStream out =
<font color="#0000ff">new</font> ZipOutputStream(
<font color="#0000ff">new</font> BufferedOutputStream(csum));
out.setComment("A test of Java Zipping");
<font color="#009900">// Can't read the above comment, though</font>
<font color="#0000ff">for</font>(<font color="#0000ff">int</font> i = 0; i < args.length; i++) {
System.out.println(
"Writing file " + args[i]);
BufferedReader in =
<font color="#0000ff">new</font> BufferedReader(
<font color="#0000ff">new</font> FileReader(args[i]));
out.putNextEntry(<font color="#0000ff">new</font> ZipEntry(args[i]));
<font color="#0000ff">int</font> c;
<font color="#0000ff">while</font>((c = in.read()) != -1)
out.write(c);
in.close();
}
out.close();
<font color="#009900">// Checksum valid only after the file</font>
<font color="#009900">// has been closed!</font>
System.out.println("Checksum: " +
csum.getChecksum().getValue());
<font color="#009900">// Now extract the files:</font>
System.out.println("Reading file");
FileInputStream fi =
<font color="#0000ff">new</font> FileInputStream("test.zip");
CheckedInputStream csumi =
<font color="#0000ff">new</font> CheckedInputStream(
fi, <font color="#0000ff">new</font> Adler32());
ZipInputStream in2 =
<font color="#0000ff">new</font> ZipInputStream(
<font color="#0000ff">new</font> BufferedInputStream(csumi));
ZipEntry ze;
System.out.println("Checksum: " +
csumi.getChecksum().getValue());
<font color="#0000ff">while</font>((ze = in2.getNextEntry()) != <font color="#0000ff">null</font>) {
System.out.println("Reading file " + ze);
<font color="#0000ff">int</font> x;
<font color="#0000ff">while</font>((x = in2.read()) != -1)
System.out.write(x);
}
in2.close();
<font color="#009900">// Alternative way to open and read</font>
<font color="#009900">// zip files:</font>
ZipFile zf = <font color="#0000ff">new</font> ZipFile("test.zip");
Enumeration e = zf.entries();
<font color="#0000ff">while</font>(e.hasMoreElements()) {
ZipEntry ze2 = (ZipEntry)e.nextElement();
System.out.println("File: " + ze2);
<font color="#009900">// ... and extract the data as before</font>
}
} <font color="#0000ff">catch</font>(Exception e) {
e.printStackTrace();
}
}
} <font color="#009900">///:~ </PRE></font></font><DIV ALIGN=LEFT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">For
each file to add to the archive, you must call
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>putNextEntry( )
</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">and
pass it a <A NAME="Index1297"></A><A NAME="Index1298"></A></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>ZipEntry
</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">object.
The
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>ZipEntry</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
object contains an extensive interface that allows you to get and set all the
data available on that particular entry in your Zip file: name, compressed and
uncompressed sizes, date, CRC checksum, extra field data, comment, compression
method, and whether it’s a directory entry. However, even though the Zip
format has a way to set a password, this is not supported in Java’s Zip
library. And although
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>CheckedInputStream</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
and
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>CheckedOutputStream</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
support both
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Adler32</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
and
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>CRC32</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
checksums, the
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>ZipEntry</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
class supports only an interface for CRC. This is a restriction of the
underlying Zip format, but it might limit you from using the faster
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Adler32</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">.</FONT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">To
extract files,
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>ZipInputStream</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
has a
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>getNextEntry( )</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
method that returns the next
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>ZipEntry</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
if there is one. As a more succinct alternative, you can read the file using a
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>ZipFile</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
object, which has a method
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>entries( )
</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">to
return an
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Enumeration</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
to the
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>ZipEntries</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">.</FONT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">In
order to read the checksum you must somehow have access to the associated
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Checksum</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
object. Here, a handle to the
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>CheckedOutputStream</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
and
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>CheckedInputStream</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
objects is retained, but you could also just hold onto a handle to the
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Checksum</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
object.
</FONT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">A
baffling method in Zip streams is
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>setComment( )</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">.
As shown above, you can set a comment when you’re writing a file, but
there’s no way to recover the comment in the
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>ZipInputStream</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">.
Comments appear to be supported fully on an entry-by-entry basis only via
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>ZipEntry</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">.</FONT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">Of
course, you are not limited to files when using the
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>GZIP</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
or
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Zip</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
libraries – you can compress anything, including data to be sent through
a network connection.
</FONT><a name="_Toc408018637"></a><P></DIV>
<A NAME="Heading342"></A><H3 ALIGN=LEFT>
The
Java archive (jar) utility
</H3>
<DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">The
Zip format is also used in the <A NAME="Index1299"></A><A NAME="Index1300"></A>Java
1.1 JAR (Java ARchive) file format, which is a way to collect a group of files
into a single compressed file, just like Zip. However, like everything else in
Java, JAR files are cross-platform so you don’t need to worry about
platform issues. You can also include audio and image files as well as class
files.
</FONT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">JAR
files are particularly helpful when you deal with the Internet. Before JAR
files, your Web browser would have to make repeated requests of a Web server in
order to download all of the files that make up an applet. In addition, each of
these files was uncompressed. By combining all of the files for a particular
applet into a single JAR file, only one server request is necessary and the
transfer is faster because of compression. And each entry in a JAR file can be
digitally signed for security (refer to the Java documentation for details).
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -