zoukankan      html  css  js  c++  java
  • 压缩文件程.ZIP

    压缩:

        /// <summary>
        /// 压缩文件
        /// </summary>
        public class ZipFile
        {
            public ZipFile()
            {
               
            }

            /// <summary>
            ///  获取文件压缩进度
            /// </summary>
            /// <param name="CurrentZipFileLength">当前文件压缩的流长</param>
            /// <param name="length">当前压缩文件的总长度</param>
            public delegate void GetZipFileProgress(int CurrentZipFileLength,long length);

            /// <summary>
            /// 获取文件压缩进度事件
            /// </summary>
            public event GetZipFileProgress GetZipFileProgressEvent;

            /// <summary>
            ///  获取文件夹压缩进度
            /// </summary>
            /// <param name="count">当前压缩有几个文件</param>
            /// <param name="counts">当前问价有几个文件</param>
            public delegate void GetZipFolderProgress(int count, int counts);

            /// <summary>
            /// 获取文件夹压缩进度事件
            /// </summary>
            public event GetZipFolderProgress GetZipFolderProgressEvent;

            /// <summary>
            /// 压缩单个文件
            /// </summary>
            /// <param name="FileToZip">需要压缩的源文件路径及名称</param>
            /// <param name="ZipedFile">压缩后的文件名</param>
            /// <param name="CompressionLevel">压缩等级(0-9)</param>
            /// <param name="BlockSize">每次压缩的大小</param>
            /// <returns></returns>
            public bool Zip(string FileToZip, string ZipedFile, int CompressionLevel, int BlockSize)
            {
                //如果文件没有找到,则报错
                System.Diagnostics.Debug.Assert(File.Exists(FileToZip), "该文件不存在");
                //if (!System.IO.File.Exists(FileToZip))
                //{
                //    //文件不存在
                //    //return;
                //   
                //    //throw new System.IO.FileNotFoundException("文件不存在 " + FileToZip + " could not be found. Zipping aborderd");
                //}
                bool result = true;
                //获取源文件名
                int index = FileToZip.LastIndexOf('\\')+1;

                //打开源文件并读取它
                FileStream StreamToZip = new FileStream(FileToZip, FileMode.Open, FileAccess.Read);
                //获取源文件长度
                long length = StreamToZip.Length;
                FileStream ZipFile = File.Create(ZipedFile);
                ZipOutputStream ZipStream = new ZipOutputStream(ZipFile);
              
                ZipEntry ZipEntry = new ZipEntry(FileToZip.Substring(index));
                ZipStream.PutNextEntry(ZipEntry);
                //压缩等级
                ZipStream.SetLevel(CompressionLevel);
                byte[] buffer = new byte[BlockSize];
                Int32 size = StreamToZip.Read(buffer, 0, buffer.Length);
                ZipStream.Write(buffer, 0, size);
                try
                {
                    while (size < StreamToZip.Length)
                    {
                        int sizeRead = StreamToZip.Read(buffer, 0, buffer.Length);
                        ZipStream.Write(buffer, 0, sizeRead);
                        size += sizeRead;
                        if(GetZipFileProgressEvent!=null)
                        {
                            GetZipFileProgressEvent(size, length);
                        }
                    }
                }
                catch (Exception ex)
                {
                    Logger.Trace(ex);
                    result = false;
                }
                finally
                {
                    if (ZipStream!=null)
                    {
                         ZipStream.Finish();
                         ZipStream.Close();
                    }
                    if (StreamToZip!=null)
                    {
                       StreamToZip.Close();
                    }
                }
                return result;
            }

            /// <summary>
            /// 压缩文件夹(直接压缩),返回是否成功
            /// </summary>
            /// <param name="sRootDir"></param>
            /// <param name="zipFileName"></param>
            /// <returns></returns>
            public bool ZipDir(string sRootDir, string zipFileName)
            {
                return ZipFileMain(new string[] { sRootDir, zipFileName });
            }

            /// <summary>
            /// 获取压缩文件夹中文件是否成功的信息
            /// </summary>
            /// <param name="args"></param>
            /// <returns></returns>
            private bool ZipFileMain(string[] args)
            {
                string[] filenames = Directory.GetFiles(args[0]);
                //获取文件夹有几个文件
                int counts = filenames.Length;
                int count = 0;
                Crc32 crc = new Crc32();
                ZipOutputStream s = new ZipOutputStream(File.Create(args[1]));
                bool result = true;
                try
                {
                    s.SetLevel(6); // 0 - store only to 9 - means best compression

                    foreach (string file in filenames)
                    {
                        //打开压缩文件
                        FileStream fs = File.OpenRead(file);

                        byte[] buffer = new byte[fs.Length];
                        fs.Read(buffer, 0, buffer.Length);
                        ZipEntry entry = new ZipEntry(file.Replace(args[0], ""));

                        entry.DateTime = DateTime.Now;

                        entry.Size = fs.Length;
                        fs.Close();

                        crc.Reset();
                        crc.Update(buffer);

                        entry.Crc = crc.Value;

                        s.PutNextEntry(entry);

                        s.Write(buffer, 0, buffer.Length);
                        count++;

                        if (GetZipFolderProgressEvent != null)
                        {
                            GetZipFolderProgressEvent(count, counts);
                        }

                    }
                    string[] dirs = Directory.GetDirectories(args[0]);
                    foreach (string dir in dirs)
                    {
                        //if (dir.IndexOf("tempdoc") > 0) continue;
                        ZipDir(args[0], dir, s, crc);
                    }
                }
                catch (Exception ex)
                {
                    Logger.Trace(ex);
                    return false;
                }
                finally
                {
                    if (s != null)
                    {
                        s.Finish();
                        s.Close();
                    }
                }
                return result;
            }

            /// <summary>
            /// 文件夹压缩
            /// </summary>
            /// <param name="sRootDir"></param>
            /// <param name="sDir"></param>
            /// <param name="s"></param>
            /// <param name="crc"></param>
            private void ZipDir(string sRootDir, string sDir, ZipOutputStream s, Crc32 crc)
            {
                string[] filenames = Directory.GetFiles(sDir);
                string[] dirs = Directory.GetDirectories(sDir);
                foreach (string file in filenames)
                {
                    //打开压缩文件
                    FileStream fs = File.OpenRead(file);
                    byte[] buffer = new byte[fs.Length];
                    fs.Read(buffer, 0, buffer.Length);
                    ZipEntry entry = new ZipEntry(file.Replace(sRootDir, ""));
                    entry.DateTime = DateTime.Now;
                    entry.Size = fs.Length;
                    fs.Close();
                    crc.Reset();
                    crc.Update(buffer);
                    entry.Crc = crc.Value;
                    s.PutNextEntry(entry);
                    s.Write(buffer, 0, buffer.Length);
                }
                foreach (string dir in dirs)
                {
                    //if (dir.IndexOf("tempdoc") > 0) continue;
                    ZipDir(sRootDir, dir, s, crc);
                }
            }

            /// <summary>
            /// 获取压缩文件夹中部分文件
            /// </summary>
            /// <param name="args"></param>
            /// <param name="files">文件夹中不需要压缩文件的名称</param>
            /// <returns></returns>
            public bool ZipFolderContainFile(string[] args,string[] files)
            {
                string[] filenames = Directory.GetFiles(args[0]);
                //获取文件夹有几个文件是要压缩的
                int counts = filenames.Length-files.Length;
                int count = 0;
                Crc32 crc = new Crc32();
                ZipOutputStream s = new ZipOutputStream(File.Create(args[1]));
                bool result = true;
                try
                {
                    s.SetLevel(6); // 0 - store only to 9 - means best compression

                    foreach (string file in filenames)
                    {
                        foreach(string filename in files)
                        {
                            if(file==filename)
                            {
                                break;
                            }
                            //打开压缩文件
                            FileStream fs = File.OpenRead(file);

                            byte[] buffer = new byte[fs.Length];
                            fs.Read(buffer, 0, buffer.Length);
                            ZipEntry entry = new ZipEntry(file.Replace(args[0], ""));

                            entry.DateTime = DateTime.Now;

                            entry.Size = fs.Length;
                            fs.Close();

                            crc.Reset();
                            crc.Update(buffer);

                            entry.Crc = crc.Value;

                            s.PutNextEntry(entry);

                            s.Write(buffer, 0, buffer.Length);
                            count++;

                            if (GetZipFolderProgressEvent != null)
                            {
                                GetZipFolderProgressEvent(count, counts);
                            }

                        }
                      
                    }
                    string[] dirs = Directory.GetDirectories(args[0]);
                    foreach (string dir in dirs)
                    {
                        //if (dir.IndexOf("tempdoc") > 0) continue;
                        ZipDir(args[0], dir, s, crc);
                    }
                }
                catch (Exception ex)
                {
                    Logger.Trace(ex);
                    result = false;
                }
                finally
                {
                    if (s != null)
                    {
                        s.Finish();
                        s.Close();
                    }
                }
                return result;
            }

            /// <summary>
            /// 压缩文件列表
            /// </summary>
            /// <param name="fileNameList">要压缩的文件列表</param>
            /// <param name="zipFileName">压缩后的生成文件</param>
            /// <returns>true表示压缩成功,false表示压缩失败</returns>
            public bool ZipFiles(List<string> fileNameList,string zipFileName)
            {
                string[] filenames = fileNameList.ToArray();
                //获取文件夹有几个文件
                int counts = filenames.Length;
                int count = 0;
                Crc32 crc = new Crc32();
                ZipOutputStream s = new ZipOutputStream(File.Create(zipFileName));
                bool result = true;
                try
                {
                    s.SetLevel(6); // 0 - store only to 9 - means best compression

                    foreach (string file in filenames)
                    {
                        //打开压缩文件
                        FileStream fs = File.OpenRead(file);
                        long pai = 1024 * 1024 * 1;//每1兆写一次
                        long forint = fs.Length / pai + 1;
                        byte[] buffer = null;
                        string replacePath = Path.GetDirectoryName(file);
                        string filename = file.Replace(replacePath + "\\", "");//只是获取文件名,但是没有目录
                        ZipEntry entry = new ZipEntry(filename);
                        entry.DateTime = DateTime.Now;
                        entry.Size = fs.Length;
                        s.PutNextEntry(entry);

                        //分段压缩
                        for (long i = 1; i <= forint; i++)
                        {
                            if (pai * i < fs.Length)
                            {
                                buffer = new byte[pai];
                                fs.Seek(pai * (i - 1), System.IO.SeekOrigin.Begin);
                            }
                            else
                            {
                                if (fs.Length < pai)
                                {
                                    buffer = new byte[fs.Length];
                                }
                                else
                                {
                                    buffer = new byte[fs.Length - pai * (i - 1)];
                                    fs.Seek(pai * (i - 1), System.IO.SeekOrigin.Begin);
                                }
                            }
                            fs.Read(buffer, 0, buffer.Length);
                            crc.Reset();
                            crc.Update(buffer);
                            s.Write(buffer, 0, buffer.Length);
                            s.Flush();
                        }

                        fs.Close();

                        count++;
                        if (GetZipFolderProgressEvent != null)
                        {
                            GetZipFolderProgressEvent(count, counts);
                        }
                    }              
                }
                catch (Exception ex)
                {
                    Logger.Trace(ex);
                    result= false;
                }
                finally
                {
                    if (s != null)
                    {
                        s.Finish();
                        s.Close();
                    }
                }
                return result;           
            }

            /// <summary>
            /// 压缩多层目录(压缩文件夹采用分阶段压缩) 
            /// </summary> 
            /// <param name="strDirectory">要压缩的目录</param> 
            /// <param name="zipedFile">压缩后的生成文件</param>
            /// <returns>true表示压缩成功,false表示压缩失败</returns>
            public static bool ZipFileDirectory(string strDirectory, string zipedFile)
            {
                //要压缩的目录不存在
                if (!Directory.Exists(strDirectory))
                {
                    return false;
                }
                bool zipIsSuccess;
                using (FileStream zipFile = System.IO.File.Create(zipedFile))
                {
                    using (ZipOutputStream zipOutputStream = new ZipOutputStream(zipFile))
                    {
                        zipIsSuccess = ZipSetp(strDirectory, zipOutputStream, "", zipedFile);
                    }
                }
                return zipIsSuccess;
            }

            /// <summary>
            /// 压缩多层目录(压缩文件夹采用分阶段压缩) 
            /// </summary> 
            /// <param name="strDirectory">要压缩的目录</param> 
            /// <param name="zipedFile">压缩后的生成文件</param>
            /// <returns>true表示压缩成功,false表示压缩失败</returns>
            public static bool ZipFileDirectory(string strDirectory, string zipedFile, List<string> withoutDirectorys)
            {
                //要压缩的目录不存在
                if (!Directory.Exists(strDirectory))
                {
                    return false;
                }
                bool zipIsSuccess;
                using (FileStream zipFile = System.IO.File.Create(zipedFile))
                {
                    using (ZipOutputStream zipOutputStream = new ZipOutputStream(zipFile))
                    {
                        zipIsSuccess = ZipSetp(strDirectory, zipOutputStream, "", withoutDirectorys, zipedFile);
                    }
                }
                return zipIsSuccess;
            }


            /// <summary> 
            /// 递归遍历目录 
            /// </summary> 
            /// <param name="strDirectory">要压缩的目录</param> 
            /// <param name="zipOutputStream">压缩后的生成文件流</param> 
            /// <param name="parentPath">当前父目录</param>
            /// <returns>true表示压缩成功,false表示压缩失败</returns>
            private static bool ZipSetp(string strDirectory, ZipOutputStream zipOutputStream, string parentPath, string targetZipPath)
            {
                if (strDirectory[strDirectory.Length - 1] != Path.DirectorySeparatorChar)
                {
                    strDirectory += Path.DirectorySeparatorChar;
                }

                try
                {
                    Crc32 crc = new Crc32();
                    string[] filenames = Directory.GetFileSystemEntries(strDirectory);
                    foreach (string file in filenames)// 遍历所有的文件和目录
                    {
                        if (Directory.Exists(file))// 当是目录时,就递归该目录下面的文件
                        {
                            string pPath = parentPath;
                            pPath += file.Substring(file.LastIndexOf("\\") + 1);
                            pPath += "\\";
                            ZipSetp(file, zipOutputStream, pPath, targetZipPath);
                        }
                        else // 否则直接压缩文件
                        {
                            if (file != targetZipPath)
                            {
                                using (FileStream fs = File.OpenRead(file))
                                {
                                    //分段压缩,主要解决单个文件太大
                                    long pai = 1024 * 1024 * 1;//每1兆写一次
                                    long forint = fs.Length / pai + 1;
                                    byte[] buffer = null;
                                    string filename = parentPath + file.Substring(file.LastIndexOf("\\") + 1);//获取文件名,但有目录
                                    ZipEntry entry = new ZipEntry(filename);
                                    entry.DateTime = DateTime.Now;
                                    entry.Size = fs.Length;
                                    zipOutputStream.PutNextEntry(entry);
                                    for (long i = 1; i <= forint; i++)
                                    {
                                        if (pai * i < fs.Length)
                                        {
                                            buffer = new byte[pai];
                                            fs.Seek(pai * (i - 1), System.IO.SeekOrigin.Begin);
                                        }
                                        else
                                        {
                                            if (fs.Length < pai)
                                            {
                                                buffer = new byte[fs.Length];
                                            }
                                            else
                                            {
                                                buffer = new byte[fs.Length - pai * (i - 1)];
                                                fs.Seek(pai * (i - 1), System.IO.SeekOrigin.Begin);
                                            }
                                        }
                                        fs.Read(buffer, 0, buffer.Length);
                                        crc.Reset();
                                        crc.Update(buffer);
                                        zipOutputStream.Write(buffer, 0, buffer.Length);
                                        zipOutputStream.Flush();
                                    }
                                    //直接压缩
                                    //byte[] buffer = new byte[fs.Length];
                                    //fs.Read(buffer, 0, buffer.Length);
                                    //string fileName = parentPath + file.Substring(file.LastIndexOf("\\") + 1);
                                    //ZipEntry entry = new ZipEntry(fileName);
                                    //entry.DateTime = DateTime.Now;
                                    //entry.Size = fs.Length;
                                    //fs.Close();
                                    //crc.Reset();
                                    //crc.Update(buffer);
                                    //entry.Crc = crc.Value;
                                    //zipOutputStream.PutNextEntry(entry);
                                    //zipOutputStream.Write(buffer, 0, buffer.Length);
                                }
                            }
                        }
                    }
                }
                catch (Exception exception)
                {
                    zipOutputStream.Flush();
                    zipOutputStream.Close();
                    return false;
                }
                return true;
            }

            /// <summary> 
            /// 递归遍历目录 
            /// </summary> 
            /// <param name="strDirectory">要压缩的目录</param> 
            /// <param name="zipOutputStream">压缩后的生成文件流</param> 
            /// <param name="parentPath">当前父目录</param>
            /// <returns>true表示压缩成功,false表示压缩失败</returns>
            private static bool ZipSetp(string strDirectory, ZipOutputStream zipOutputStream, string parentPath, List<string> withoutDirectorys, string targetZipPath)
            {
                if (strDirectory[strDirectory.Length - 1] != Path.DirectorySeparatorChar)
                {
                    strDirectory += Path.DirectorySeparatorChar;
                }

                try
                {
                    Crc32 crc = new Crc32();
                    string[] filenames = Directory.GetFileSystemEntries(strDirectory);
                    foreach (string file in filenames)// 遍历所有的文件和目录
                    {
                        if (Directory.Exists(file))// 当是目录时,就递归该目录下面的文件
                        {
                            if (withoutDirectorys.Contains(file))
                                continue;
                            string pPath = parentPath;
                            pPath += file.Substring(file.LastIndexOf("\\") + 1);
                            pPath += "\\";
                            ZipSetp(file, zipOutputStream, pPath, targetZipPath);
                        }
                        else // 否则直接压缩文件
                        {
                            using (FileStream fs = File.OpenRead(file))
                            {
                                //分段压缩,主要解决单个文件太大
                                long pai = 1024 * 1024 * 1;//每1兆写一次
                                long forint = fs.Length / pai + 1;
                                byte[] buffer = null;
                                string filename = parentPath + file.Substring(file.LastIndexOf("\\") + 1);//获取文件名,但有目录
                                ZipEntry entry = new ZipEntry(filename);
                                entry.DateTime = DateTime.Now;
                                entry.Size = fs.Length;
                                zipOutputStream.PutNextEntry(entry);
                                for (long i = 1; i <= forint; i++)
                                {
                                    if (pai * i < fs.Length)
                                    {
                                        buffer = new byte[pai];
                                        fs.Seek(pai * (i - 1), System.IO.SeekOrigin.Begin);
                                    }
                                    else
                                    {
                                        if (fs.Length < pai)
                                        {
                                            buffer = new byte[fs.Length];
                                        }
                                        else
                                        {
                                            buffer = new byte[fs.Length - pai * (i - 1)];
                                            fs.Seek(pai * (i - 1), System.IO.SeekOrigin.Begin);
                                        }
                                    }
                                    fs.Read(buffer, 0, buffer.Length);
                                    crc.Reset();
                                    crc.Update(buffer);
                                    zipOutputStream.Write(buffer, 0, buffer.Length);
                                    zipOutputStream.Flush();
                                }
                                //直接压缩
                                //byte[] buffer = new byte[fs.Length];
                                //fs.Read(buffer, 0, buffer.Length);
                                //string fileName = parentPath + file.Substring(file.LastIndexOf("\\") + 1);
                                //ZipEntry entry = new ZipEntry(fileName);
                                //entry.DateTime = DateTime.Now;
                                //entry.Size = fs.Length;
                                //fs.Close();
                                //crc.Reset();
                                //crc.Update(buffer);
                                //entry.Crc = crc.Value;
                                //zipOutputStream.PutNextEntry(entry);
                                //zipOutputStream.Write(buffer, 0, buffer.Length);
                            }
                        }
                    }
                }
                catch (Exception exception)
                {
                    return false;
                }
                return true;
            } 

            /// <summary>
            /// 更新 Zip 包中的文件
            /// </summary>
            /// <param name="srcZipFileName">Zip 包的全名</param>
            /// <param name="srcFileName">要添加到包中的文件名</param>
            /// <param name="destPath">文件在Zip包中的相对位置</param>
            public void UpdateZipFile(String srcZipFileName, String srcFileName, String destPath)
            {
                string[] unZipFileInfos = new string[2];
                unZipFileInfos[0] = srcZipFileName;
                //获取临时解压目录
                string tempDirectory = Path.GetDirectoryName(srcZipFileName) + Path.DirectorySeparatorChar + System.Guid.NewGuid().ToString().Replace("-", "") + Path.DirectorySeparatorChar;
                //要更新的文件在临时文件夹中位置
                string destFilePath=tempDirectory+destPath;
                unZipFileInfos[1] = tempDirectory;
                //如果临时文件夹目录不存在则创建
                if (!System.IO.Directory.Exists(tempDirectory))
                {
                    System.IO.Directory.CreateDirectory(tempDirectory);
                }
                CommonLibrary.UnZipFile unZipFile = new UnZipFile();
                //解压文件到临时文件夹
                unZipFile.UnZip(unZipFileInfos);
                //更新需要更新的文件
                System.IO.File.Copy(srcFileName,destFilePath, true);
                //更新完成后重新压缩文件到临时文件夹
                ZipFileDirectory(tempDirectory, tempDirectory + Path.GetFileName(srcZipFileName));
                //更新zip文件
                System.IO.File.Copy(tempDirectory + Path.GetFileName(srcZipFileName), srcZipFileName, true);
                //删除临时文件夹
                System.IO.Directory.Delete(tempDirectory, true);
                //ICSharpCode.SharpZipLib.Zip.ZipFile zipFileEntry = new ICSharpCode.SharpZipLib.Zip.ZipFile(srcZipFileName);
                //// Must call BeginUpdate to start, and CommitUpdate at the end.
                //zipFileEntry.BeginUpdate();
            
                ////添加文件到 Zip 包中
                //IStaticDataSource fileEntry = new FileEntry(srcFileName);
                //zipFileEntry.Add(fileEntry, destPath);
                //// Both CommitUpdate and Close must be called.
                //zipFileEntry.CommitUpdate();
                //((FileEntry)fileEntry).FileStream.Close();
                //zipFileEntry.Close();
            }//end method
        }//end class

        public class FileEntry : IStaticDataSource
        {
             private   FileStream fileStream;

            public FileEntry(String filename)
            {
                fileStream = File.OpenRead(filename);
               // fileStream.Close();
            }
            public Stream GetSource()
            {
                return fileStream;
            }
            /// <summary>
            /// 对象流
            /// </summary>
            public FileStream FileStream
            {
                get { return fileStream; }
            }

        }//end class

  • 相关阅读:
    XOR linked list
    Doubly Linked List&DLL(双向链表)
    circular linked list&CLL(循环链表)
    Linked list(单链表)
    malloc() & free()
    Mysql 1045
    DoublePointer (**)
    java.sql.SQLException: Operation not allowed after ResultSet closed
    Array
    java-方法
  • 原文地址:https://www.cnblogs.com/chengjunwei/p/2557623.html
Copyright © 2011-2022 走看看