Click here to Skip to main content
Click here to Skip to main content

GZipStream - Compress/Decompress a string

By , 23 Jun 2008
 

Introduction

This article presents two methods to compress and decompress strings using System.IO.Compression.GZipStream.

Context/Problem

After converting code from VB.NET 1.1 to C#.NET 3.5, I needed to change some code using a third party zip class to GZipStream. Code samples found on the web or on VS help where presenting solutions dealing with FileStream but in this case, a string is given as an input parameter.

So the little challenge was to go from a string to a byte array (byte[]) and vice versa without losing a char nor changing its encoding because I ended up finding that System.Text.Encoding.Unicode.GetBytes()/GetString() previously used in the VB code was not acting properly, resulting in a loss of characters. Plus the Flush() method on GZipStream with the compression option doesn't flush everything...

Tips

So as I found no method transforming a string into a byte[] and vice versa without involving encoding specifications, I ended up with a loop and a cast. If you have a better idea, please tell me so.

And I found out, if you only flush a GZipStream instance and retrieve the data from the underlying stream without closing this GZipStream instance, you miss part of the data.

The Code

Compress/Zip a string:

    public static string Zip(string value)
    {
        //Transform string into byte[]  
        byte[] byteArray = new byte[value.Length];
        int indexBA = 0;
        foreach (char item in value.ToCharArray())
        {
            byteArray[indexBA++] = (byte)item;
        }
        
        //Prepare for compress
        System.IO.MemoryStream ms = new System.IO.MemoryStream();
        System.IO.Compression.GZipStream sw = new System.IO.Compression.GZipStream(ms,
            System.IO.Compression.CompressionMode.Compress);

        //Compress
        sw.Write(byteArray, 0, byteArray.Length);
        //Close, DO NOT FLUSH cause bytes will go missing...
        sw.Close();

        //Transform byte[] zip data to string
        byteArray = ms.ToArray();
        System.Text.StringBuilder sB = new System.Text.StringBuilder(byteArray.Length);
        foreach (byte item in byteArray)
        {
            sB.Append((char)item);
        }
        ms.Close();
        sw.Dispose();
        ms.Dispose();
        return sB.ToString();
    }

Decompress/Unzip a string: input value has been previously compressed with GZipStream.

    public static string UnZip(string value)
    {
        //Transform string into byte[]
        byte[] byteArray = new byte[value.Length];
        int indexBA = 0;
        foreach (char item in value.ToCharArray())
        {
            byteArray[indexBA++] = (byte)item;
        }
        
        //Prepare for decompress
        System.IO.MemoryStream ms = new System.IO.MemoryStream(byteArray);
        System.IO.Compression.GZipStream sr = new System.IO.Compression.GZipStream(ms,
            System.IO.Compression.CompressionMode.Decompress);
        
        //Reset variable to collect uncompressed result
        byteArray = new byte[byteArray.Length];
        
        //Decompress
        int rByte = sr.Read(byteArray, 0, byteArray.Length);

        //Transform byte[] unzip data to string
        System.Text.StringBuilder sB = new System.Text.StringBuilder(rByte);
        //Read the number of bytes GZipStream red and do not a for each bytes in
        //resultByteArray;
        for (int i = 0; i < rByte; i++)
        {
            sB.Append((char)byteArray[i]);
        }
        sr.Close();
        ms.Close();
        sr.Dispose();
        ms.Dispose();
        return sB.ToString();
    }

Points of Interest

Well, if you haven't dealt with a lot of streams like me, hopefully this will avoid loss of time!

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)

About the Author

Frankidoze
Systems Engineer
United States United States
Member
No Biography provided

Sign Up to vote   Poor Excellent
Add a reason or comment to your vote: x
Votes of 3 or less require a comment

Comments and Discussions

 
You must Sign In to use this message board.
Search this forum  
    Spacing  Noise  Layout  Per page   
GeneralMy vote of 1 PinmemberYclkvnc8 May '13 - 6:28 
GeneralMy vote of 4 PinmemberNasenbaaer12 Apr '13 - 6:24 
SuggestionSharing my code PinmemberSamNaseri16 Nov '11 - 18:38 
GeneralThis code will work properly if PinmemberMember 28508507 Jun '11 - 19:16 
GeneralThis article is full of bugs, don't use it! Pinmemberxxbbcc28 May '11 - 16:51 
GeneralMy vote of 1 Pinmemberxxbbcc28 May '11 - 16:42 
GeneralMy vote of 1 Pinmemberdjpitagora27 Sep '10 - 7:04 
GeneralDecompress bug fix Pinmemberfiloteanuadrian9 Apr '10 - 4:10 
GeneralDoesn't work at all PinmemberVikcia26 Mar '10 - 7:49 
GeneralPublic Class CZip .... PinmemberErfan2 Feb '10 - 19:45 
GeneralobjCompressedStream.Length not supported Pinmemberoops.uvj26 Aug '09 - 20:17 
GeneralPerformance Improvement/Cleanup Pinmembermatthias Weiser10 Dec '08 - 3:34 
GeneralIn the decompression to string the buffer size is wrong. A decompressed string may be larger than the original data. Pinmemberelinder91225 Sep '08 - 10:59 
GeneralFlush doesn't flush PinmemberRichard Birkby8 Sep '08 - 3:16 
Generalzipping don't work PinmemberMSaty9 Aug '08 - 3:32 
Questiondecompressing binary concatenated files PinmemberRobin Debnath25 Jul '08 - 3:27 
GeneralCompress persian or arabic string Pinmemberelahe babaee22 Jul '08 - 21:37 
GeneralEncoding PinmemberBTDex5 Jul '08 - 3:20 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Rant Rant    Admin Admin   

Permalink | Advertise | Privacy | Mobile
Web02 | 2.6.130523.1 | Last Updated 23 Jun 2008
Article Copyright 2008 by Frankidoze
Everything else Copyright © CodeProject, 1999-2013
Terms of Use
Layout: fixed | fluid