C # Create a compressed file

Source: Internet
Author: User

Source: http://www.cnblogs.com/sparkdev/

It is very important to compress and decompress files in the program, which can not only reduce the volume of files, but also protect the files. If you build a file that users can download, it can also greatly reduce network traffic and increase download speed. Recently used in a C # project to create a compressed file function, here and students to share the experience.

SharpZipLib Library

Since it is very important to use the energy, then if everyone in the use of the basic API to achieve a time clearly does not meet the efficiency of the first production requirements. As a more experienced developer, you will be sure to search for a feature-rich, well-regarded open source class library in the first time to do the work. On the. NET platform, to manipulate compressed files, your first choice must be sharpziplib. SharpZipLib is an open source, compressed, uncompressed class library based on the. NET platform. Characterized by long-term development and use has become very stable, can be assured that the application to the product. Here's an example of how to use it to create a compressed file in C # code, and how to handle some common problems. For sharpziplib download please visit here. Compilation is also very simple, with VisualStudio Open Direct compilation can be successful. If you want to fully master the use of SharpZipLib, it is recommended that you read the SharpZipLib documentation, this article only describes the basic usage and some of the use of experience.

Basic compression operations

SharpZipLib supports mainstream compression formats such as ZIP,GZIP,TAR,BZIP2. This article is introduced in the ZIP format, and the other formats are poorly used. For the ZIP compression format, the type used to create the compressed file is primarily Zipoutputstream and zipentry. Here are some typical use cases to describe their usage.

Read the files on the hard disk and add the compressed package

This is probably the simplest and most common usage, directly on the code:

The resulting compressed file is test.zipusing (FileStream fsout = file.create ("Test.zip")) {The constructor of the//zipoutputstream class requires a stream, a file stream, a memory stream,    The compressed content is written to this stream.        using (Zipoutputstream ZipStream = new Zipoutputstream (fsout)) {//Prepare to add the Vcredist_x86.exe file under the G-Packing directory to the compression package.        String fileName = @ "G:\vcredist_x86.exe";        FileInfo fi = new FileInfo (fileName);        EntryName is the name of the file in the compressed package.        String entryName = "Vcredist_x86.exe";        The ZipEntry class represents an item in a compressed package, either as a file or as a directory.        ZipEntry newEntry = new ZipEntry (entryName); Newentry.datetime = fi.        LastWriteTime; Newentry.size = fi.        Length;        Adds the information for the compressed item to the Zipoutputstream.        Zipstream.putnextentry (NewEntry);        byte[] buffer = new byte[4096];        Copy the files that need to be compressed into zipoutputstream in a file stream. using (FileStream StreamReader = File.openread (fileName)) {streamutils.copy (StreamReader, ZipStream, BU        Ffer);        } zipstream.closeentry (); Add multiple files//If you want to compress a folder, it is by traversing all the files under the Add Folder String fileName2 = @ "G:\share\web.dll";        FileInfo fi2 = new FileInfo (fileName2);        The path of the file in the compressed package string entryName2 = "Share\\web.dll";        ZipEntry NewEntry2 = new ZipEntry (entryName2); Newentry2.datetime = Fi2.        LastWriteTime; Newentry2.size = Fi2.        Length;        Zipstream.putnextentry (NewEntry2);        byte[] Buffer2 = new byte[4096]; using (FileStream StreamReader = File.openread (fileName2)) {streamutils.copy (StreamReader, ZipStream, b        UFFER2);        } zipstream.closeentry (); Be sure to set Isstreamowner to False when using flow operations.        Otherwise it is very easy to happen after the file stream is closed.        Zipstream.isstreamowner = false;        Zipstream.finish ();    Zipstream.close (); }}

The code is not complicated and detailed comments are added, so it is no longer discussed. At this point, the file has been added to the compression package, the contents of the compressed package are as follows:

Note that the Web.dll file is in the share folder.

Add in-memory data to a compressed package

Sometimes the object we want to compress is not the file on disk, but the data in memory. For example, there are strings in the results of database query operations that you want to write to a text file in a compressed package. Of course, you can save these strings to a file on disk, and then write to the compressed package by the method in the previous example, which can accomplish the task, but it is not an efficient method. First of all, disk IO is very slow and expensive, and in some Web applications you don't have permission to write files. This requires that we write the data directly to the compression package:

We have a string that we want to write directly to the City.csv file in the compressed package. byte[] string1 = Encoding.UTF8.GetBytes ("washington,shanghai,tianjin,dongjing"); using (FileStream fsout = file.create ("Test1.zip")) {    using (zipoutputstream zipStream = new Zipoutputstream (fsout))    {        ZipEntry entry = new ZipEntry ("City.csv" );        Entry. DateTime = DateTime.Now;        Zipstream.putnextentry (entry);        The Write method is the same as the Streamutils.copy method used earlier, but this is a byte array.        zipstream.write (string1, 0, string1. Length);        Zipstream.closeentry ();        Zipstream.isstreamowner = false;        Zipstream.finish ();        Zipstream.close ();    }}

This time we write a string in memory directly to the City.csv file in the compressed package. It looks good, at least the code looks refreshing. Now, let's see what else we could do.

Keep the compression package in memory

In the above example, we mentioned that sometimes there is no permission to write files, then how to create a compressed file ah? It's too contradictory! In fact, there are such use cases in real life. For example, if you have a website, when the user clicks the download button, you need to save the data to a compressed file and return it to the user. You can not write files throughout the process, only by manipulating memory to achieve:

byte[] string1 = Encoding.UTF8.GetBytes ("washington,shanghai,tianjin,dongjing"); byte[] result = null;using ( MemoryStream ms = new MemoryStream ()) {    using (zipoutputstream zipStream = new Zipoutputstream (ms))    {        ZipEntry entry = new ZipEntry ("City.csv");        Entry. DateTime = DateTime.Now;        Zipstream.putnextentry (entry);        Zipstream.write (string1, 0, string1. Length);        Zipstream.closeentry ();        Zipstream.isstreamowner = false;        Zipstream.finish ();        Zipstream.close ();        Ms. Position = 0;        The compressed data is saved in the byte[] array.        result = Ms. ToArray ();    }}

The byte array result is now the data for the compressed package. If you want to return to the user via HttpResponse, you can do so by calling HttpResponse's BinaryWrite method, as long as the result is a parameter.

Problems with Chinese file names

After the happy completion of the task of creating a compressed file, it's time to open the zipped package and look at the files we generated! Let's change the previous example a little bit:

byte[] string1 = Encoding.UTF8.GetBytes ("washington,shanghai,tianjin,dongjing"); using (FileStream fsout = file.create ("Test1.zip")) {    using (zipoutputstream zipStream = new Zipoutputstream (fsout))    {        //filename changed to Chinese        zipentry entry = new ZipEntry ("City. csv");        Entry. DateTime = DateTime.Now;        ...    }}

Run the above code generation Test1.zip, and open Test1.zip in Explorer. What? Where did it go wrong? Why is there nothing in the compression pack!

In fact, this is a very typical problem, of course, it is easy to solve! The reason for the problem is because my operating system is in English, and I did not tell ZipEntry how to handle the Chinese file name "city. csv". The reason is found, then we plainly tell ZipEntry how to deal with the text:

Entry. Isunicodetext = true;

C # Create a compressed file

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.