"Hi, Amigo!"

"Hi, Ellie!"

"Today we're going to study I/O streams."

"Yes, I already know everything about them. We use the FileInputStream and FileOutputStream classes here."

"Yep, and which of these classes' methods do you know?"

"Sure. Here are the methods of FileInputStream:"

Method Description
int read() Reads one byte and returns it.
int read(byte b[]) Reads a byte array and returns it.
int read(byte b[], int off, int len) Reads a byte array from the stream.
long skip(long n) Skips n bytes, used when reading from the stream.
int available() Returns the number of bytes that can still be read from the stream.
void close() Closes the stream.

"Spot on! And the methods of FileOutputStream?"

"Take a look:"

Method Description
void write(int b) Writes one byte to the stream.
void write(byte b[]) Writes an array of bytes to the stream.
void write(byte b[], int off, int len) Writes an array of bytes to the stream.
void close() Closes the stream.

"Amigo, you surprise me!"

"And then some!"

"Fine, then I'll give you two new classes: ZipInputStream and ZipOutputStream."

FileInputStream, FileOutputStream, ZipOutputStream, ZipInputStream - 1

"Zip? Is that like a zip file?"

"Exactly. These streams are designed to work with zip files. You can use them to read or write straight to a zip file!"

"Holy moly! How interesting. But a zip file can have not one file, but several. How do they work?"

"For that, there's another special class: ZipEntry. It presents a file stored in the archive. You can only read ZipEntry objects from a ZipInputStream, and you can only write ZipEntry objects to a ZipOutputStream. But it turns out that you can read and write to a ZipEntry just like a regular file."

"Could you give me an example of how it works?"

"Of course. Here's an example where we create an archive and put a file in it:"

// Create an archive
FileOutputStream zipFile = new FileOutputStream("c:/archive.zip");
ZipOutputStream zip = new ZipOutputStream(zipFile);

//Put a ZipEntry into it
zip.putNextEntry(new ZipEntry("document.txt"));

//Copy the file «document-for-archive.txt» to the archive under the name «document.txt»
File file = new File("c:/document-for-archive.txt");
Files.copy(file.toPath(), zip);

// Close the archive

"How interesting! And unzipping files is just as easy?"

"Yep. Here is a brief description of the methods of the ZipEntry, ZipInputStream  and ZipOutputStream classes"

"ZipInputStream is a stream, so all the ZipEntry can only be read sequentially. Here are its methods:"

Method Description
ZipEntry getNextEntry() Returns an object describing the next ZipEntry (skips all bytes in the current entry).
void closeEntry() Closes input stream on the current ZipEntry (skips all bytes in the current entry).
int available() Returns 1 there are ZipEntries available, otherwise 0.
int read(byte[] b, int off, int len) Reads bytes from the current ZipEntry.
long skip(long n) Skips n bytes when reading from the stream.
void close() Closes the stream.

"I don't really understand."

"The best thing to do is imagine that you're reading a text file, and ZipEntries are like lines in the file. You can read data from the current line (the current ZipEntry) or jump from line to line (getNextEntry, closeEntry)."

"I think I understand, but I'm not sure."

"Here's ZipOutputStream and its methods:"

Method Description
void setComment(String comment) Sets a comment on the archive.
void setMethod(int method) Sets the compression method (type).
void setLevel(int level) Sets the compression level. The higher the compression, the slower it goes.
void putNextEntry(ZipEntry e) Adds a new ZipEntry.
void closeEntry() Closes the current ZipEntry
void write(byte[] b, int off, int len) Writes a set of bytes to the current ZipEntry.
void close() Closes the stream.

"But in the example above we used almost none of this."

"These are optional methods. You don't have to specify the compression level and method—the default settings will be used."

"Hmm. That's not so bad. And ZipEntry?"

"Sure. The only other information in a ZipEntry is housekeeping information:"

Method Description
String getName(), setName(String) Internal name file.
long getTime(), setTime(long) Last time the entry was modified.
long getCRC(), setCRC(long) Checksum.
long getSize(), setSize(long) Size before compression.
int getMethod(), setMethod(int) Compression method.
long get/setCompressedSize() Size after zipping.
boolean isDirectory() Is the entry a directory?

"That doesn't look very hard. What isn't there to love!"

"Excellent, then Diego will give you tasks on this topic as well."

"I should have kept my mouth shut."