【问题标题】:Can I maintain directory structure when zipping file?压缩文件时可以维护目录结构吗?
【发布时间】:2021-11-14 02:37:45
【问题描述】:

我正在尝试压缩一些文件,但这些文件可能存在于不同的目录中。压缩部分工作正常,但我不知道如何让它保留 zip 文件中的目录结构。

这是我目前所拥有的:

public static void CreateZipFile(IEnumerable<FileInfo> files, string archiveName)
{
  using (var stream = File.OpenWrite(archiveName))
  using (var archive = new ZipArchive(stream, ZipArchiveMode.Create))
  {
    foreach (var item in files)
    {
      archive.CreateEntryFromFile(item.FullName, item.Name, CompressionLevel.Optimal);
    }
  }
}

这可能吗?

【问题讨论】:

标签: c# .net zip directoryinfo


【解决方案1】:

@ErocM @Flydog57 提供的链接为您提供了您想要的。您没有正确利用entryName 参数(调用CreateEntryFromFile 时的第二个参数)。

独立于要添加到存档的文件(来自不同文件夹的相同文件),您必须使用 C# api 提供给您的 entryName 参数来构建存档。

如果您的文件全名是/tmp/myfile.txt,而您使用的是archive.CreateEntryFromFile(item.FullName, item.Name),那么存档条目名称将为myfile.txt。没有作为条目名称创建的文件夹在其名称中不包含文件夹结构。

但是,如果您调用archive.CreateEntryFromFile(item.FullName, item.FullName),您将在存档中拥有您的文件夹结构。

您可以尝试使用您的函数,只需将 item.Name 更改为 item.FullName

在 Windows 上要小心;例如,如果您的路径是 C:\tmp\myfile.txt,则存档将无法正确提取。然后,您可以添加一些小代码以从文件的全名中删除 C:

一些实施示例:

using System;
using System.IO;
using System.Collections.Generic;
using System.IO.Compression;

namespace ConsoleApp
{
    internal class Program
    {
        static void Main(string[] args)
        {
            FileInfo f1 = new FileInfo(@"/tmp/test1.txt");
            FileInfo f2 = new FileInfo(@"/tmp/testdir/test2.txt");

            List<FileInfo> files = new();
            files.Add(f1);
            files.Add(f2);

            CreateZipFile(files, @"/tmp/archive.zip");

        }

        public static void CreateZipFile(IEnumerable<FileInfo> files, string archiveName)
        {
            using (var stream = File.OpenWrite(archiveName))
            using (var archive = new ZipArchive(stream, ZipArchiveMode.Create))
            {
                foreach (var item in files)
                {
                    // Here for instance, I put all files in the input list in the same directory, without checking from where they are in the host file system.
                    archive.CreateEntryFromFile(item.FullName, $"mydir/{item.Name}", CompressionLevel.Optimal);

                    // Here, I am just using the actual full path of the file. Be careful on windows with the disk name prefix (C:, D:, etc...).
                    // archive.CreateEntryFromFile(item.FullName, item.FullName, CompressionLevel.Optimal);
                }
            }
        }
    }

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-07-10
    • 1970-01-01
    • 2020-05-29
    • 2016-10-03
    • 2016-08-11
    • 1970-01-01
    相关资源
    最近更新 更多