C# 使用C压缩单个文件#

C# 使用C压缩单个文件#,c#,.net,zip,zipfile,C#,.net,Zip,Zipfile,我使用的是.NET4.5,如果我试图用“CreateFromDirectory”压缩整个目录,ZipFile类将非常有用。但是,我只想压缩目录中的一个文件。我试图指向一个特定的文件(folder\data.txt),但这不起作用。我考虑过ZipArchive类,因为它有一个“CreateEntryFromFile”方法,但它似乎只允许您在现有文件中创建条目 如果不创建一个空的zipfile(有它的问题),然后使用ZipArchiveExtension的“CreateEntryFromFile”方

我使用的是.NET4.5,如果我试图用“CreateFromDirectory”压缩整个目录,ZipFile类将非常有用。但是,我只想压缩目录中的一个文件。我试图指向一个特定的文件(folder\data.txt),但这不起作用。我考虑过ZipArchive类,因为它有一个“CreateEntryFromFile”方法,但它似乎只允许您在现有文件中创建条目

如果不创建一个空的zipfile(有它的问题),然后使用ZipArchiveExtension的“CreateEntryFromFile”方法,就无法简单地压缩一个文件

**这也是假设我正在从事一个目前无法使用第三方附加组件的公司程序

示例来自:


但是,如果startPath是
@“c:\example\start\myFile.txt;”
,则会抛出一个错误,即目录无效。

在.NET中,对于单个文件,有很多方法可以解决此问题。如果您不想在那里了解所有内容,您可以获得一个抽象库,如SharpZipLib(长期存在的开源库)、sevenzipsharp(下面需要7zip libs)或DotNetZip。

使用文件(或任何)流:

或简述者:

// reference System.IO.Compression
using (var zip = ZipFile.Open("file.zip", ZipArchiveMode.Create))
    zip.CreateEntryFromFile("file.txt", "file.txt");
确保添加对System.IO.Compression的引用

更新

另外,也可以查看新的DotnetAPI文档。这里有几个例子。还有一个关于引用
System.IO.Compression.FileSystem
以使用
ZipFile
的警告

要使用ZipFile类,必须引用 项目中的System.IO.Compression.FileSystem程序集

使用“关闭存档”和“使用文件或内存流”:

using (MemoryStream ms = new MemoryStream())
using (ZipArchive arch = new ZipArchive(ms, ZipArchiveMode.Create))
{
    arch.CreateEntryFromFile(@"C:\Temp\data.xml", "data.xml");
}
如果您可以创建zip文件并添加到其中,请使用filestream:

using (FileStream fs = new FileStream(@"C:\Temp\output.zip",FileMode.Create))
using (ZipArchive arch = new ZipArchive(fs, ZipArchiveMode.Create))
{
    arch.CreateEntryFromFile(@"C:\Temp\data.xml", "data.xml");
}
或者,如果您需要在内存中执行所有操作并在完成后写入文件,请使用内存流:

using (MemoryStream ms = new MemoryStream())
using (ZipArchive arch = new ZipArchive(ms, ZipArchiveMode.Create))
{
    arch.CreateEntryFromFile(@"C:\Temp\data.xml", "data.xml");
}
那你就可以了


最简单的方法就是使用一个临时文件夹

对于拉链:

  • 创建临时文件夹
  • 将文件移动到文件夹
  • 压缩文件夹
  • 删除文件夹
  • 对于解压缩:

  • 解压存档
  • 将文件从临时文件夹移动到您的位置
  • 删除临时文件夹

  • 只需使用以下代码压缩文件

    public void Compressfile()
            {
                 string fileName = "Text.txt";
                 string sourcePath = @"C:\SMSDBBACKUP";
                 DirectoryInfo di = new DirectoryInfo(sourcePath);
                 foreach (FileInfo fi in di.GetFiles())
                 {
                     //for specific file 
                     if (fi.ToString() == fileName)
                     {
                         Compress(fi);
                     }
                 } 
            }
    
    public static void Compress(FileInfo fi)
            {
                // Get the stream of the source file.
                using (FileStream inFile = fi.OpenRead())
                {
                    // Prevent compressing hidden and 
                    // already compressed files.
                    if ((File.GetAttributes(fi.FullName)
                        & FileAttributes.Hidden)
                        != FileAttributes.Hidden & fi.Extension != ".gz")
                    {
                        // Create the compressed file.
                        using (FileStream outFile =
                                    File.Create(fi.FullName + ".gz"))
                        {
                            using (GZipStream Compress =
                                new GZipStream(outFile,
                                CompressionMode.Compress))
                            {
                                // Copy the source file into 
                                // the compression stream.
                                inFile.CopyTo(Compress);
    
                                Console.WriteLine("Compressed {0} from {1} to {2} bytes.",
                                    fi.Name, fi.Length.ToString(), outFile.Length.ToString());
                            }
                        }
                    }
                }
            }
    
        }
    

    但那不起作用
    什么不起作用?代码在哪里?指向特定文件与“CreateFromDirectory”不兼容。我在原来的问题中添加了微软的例子。你可以使用ZipArchive类创建一个新的Zip存档,尽管它并不完全是一行程序。有关如何操作,请参阅。(如果这太麻烦,您可能会考虑使用更好的第三方库进行压缩处理,例如)或者您可以将文件移动到一个临时文件夹进行压缩,并在删除后附加到同一临时文件夹?但最好的解决方案是获得更好的库。@elgonzo我提到我不能使用第三方解决方案,但谢谢你的建议。参考答案中的人似乎试图从头开始创建新文件并写入流,但我将尝试从那里找到解决方案。谢谢,谢谢你的建议。对于任何好奇的人来说,我用它来添加一个应用程序,该应用程序将Lotus Notes附件作为嵌入对象移动到MSWord文件中,但两种古老的文件类型本机不受支持,因此采用了zip解决方案。更像是:先压缩,然后解压缩。。。好啊GG可能是一个愚蠢的问题……但是即使在添加dll引用之后,ZipArchiveMode也不能被识别为System.IO.Compression命名空间的一部分。我看到有文档记录,但VS2012似乎无法找到它(“当前上下文中不存在名称'ZipArchiveMode')?@AIng请确保添加对System.IO.Compression的引用。如果要使用CreatEntryFromFile,请同时参考System.IO.Compression.FileSystem。这应该是可接受的解决方案。虽然AlexanderBrevig的解决方案可能有效,但临时创建一个文件夹以生成zip文件需要很多额外的步骤,这些步骤是不必要的。约翰·科尔纳的解决方案更简单,但可能更简单。如果用一个文件流代替他的MemoryStream,就不需要第二步将MemoryStream写入磁盘。也许有一个我不知道的速度或内存使用优势,但如果ZIP文件是最终目标,那么直接访问FileStream会更好。仅供参考:使用ZipArchive时,需要向项目添加
    System.IO.Compression
    引用。不仅仅是
    System.IO.Compression.FileSystem
    。这是针对GZIP的,而不是针对ZIP的
    using (FileStream file = new FileStream("file.bin", FileMode.Create, System.IO.FileAccess.Write)) {
       byte[] bytes = new byte[ms.Length];
       ms.Read(bytes, 0, (int)ms.Length);
       file.Write(bytes, 0, bytes.Length);
       ms.Close();
    }
    
    public void Compressfile()
            {
                 string fileName = "Text.txt";
                 string sourcePath = @"C:\SMSDBBACKUP";
                 DirectoryInfo di = new DirectoryInfo(sourcePath);
                 foreach (FileInfo fi in di.GetFiles())
                 {
                     //for specific file 
                     if (fi.ToString() == fileName)
                     {
                         Compress(fi);
                     }
                 } 
            }
    
    public static void Compress(FileInfo fi)
            {
                // Get the stream of the source file.
                using (FileStream inFile = fi.OpenRead())
                {
                    // Prevent compressing hidden and 
                    // already compressed files.
                    if ((File.GetAttributes(fi.FullName)
                        & FileAttributes.Hidden)
                        != FileAttributes.Hidden & fi.Extension != ".gz")
                    {
                        // Create the compressed file.
                        using (FileStream outFile =
                                    File.Create(fi.FullName + ".gz"))
                        {
                            using (GZipStream Compress =
                                new GZipStream(outFile,
                                CompressionMode.Compress))
                            {
                                // Copy the source file into 
                                // the compression stream.
                                inFile.CopyTo(Compress);
    
                                Console.WriteLine("Compressed {0} from {1} to {2} bytes.",
                                    fi.Name, fi.Length.ToString(), outFile.Length.ToString());
                            }
                        }
                    }
                }
            }
    
        }