Работа с ZIP/архивами в C# (.NET): полное руководство

Онлайн-тренажер Python для начинающих

Изучайте Python легко и без перегрузки теорией. Решайте практические задачи с автоматической проверкой, получайте подсказки на русском языке и пишите код прямо в браузере — без необходимости что-либо устанавливать.

Начать курс

Работа с ZIP-архивами в C# (.NET)

В современной разработке на платформе .NET работа с архивами — одна из часто встречающихся задач. Будь то упаковка логов, создание резервных копий или передача данных по сети — умение эффективно сжимать и распаковывать файлы необходимо каждому C#-разработчику. В этой статье мы подробно разберём два основных подхода: встроенное пространство имён System.IO.Compression и стороннюю библиотеку SharpZipLib.

Встроенные средства .NET: System.IO.Compression

Начиная с .NET Framework 4.5, платформа предоставляет нативный API для работы с ZIP-архивами. Основные классы находятся в пространстве имён System.IO.Compression.

Создание ZIP-архива

Для создания архива используется класс ZipArchive в паре с ZipFile:

using System.IO;
using System.IO.Compression;

string sourceDirectory = @"C:\Data\Reports";
string zipPath = @"C:\Archives\reports.zip";

if (File.Exists(zipPath))
    File.Delete(zipPath);

ZipFile.CreateFromDirectory(sourceDirectory, zipPath);
Console.WriteLine("Архив создан: " + zipPath);

Извлечение архива

Распаковка выполняется аналогично — методом ExtractToDirectory:

string extractPath = @"C:\Data\Extracted";
ZipFile.ExtractToDirectory(zipPath, extractPath);
Console.WriteLine("Архив извлечён в: " + extractPath);

Работа с отдельными записями

Для более тонкого контроля используйте ZipArchive напрямую:

using (FileStream zipStream = new FileStream(zipPath, FileMode.Open))
using (ZipArchive archive = new ZipArchive(zipStream, ZipArchiveMode.Read))
{
    foreach (ZipArchiveEntry entry in archive.Entries)
    {
        Console.WriteLine($"Файл: {entry.FullName}, Размер: {entry.Length} байт");
        
        // Извлечение конкретного файла
        entry.ExtractToFile(Path.Combine(extractPath, entry.FullName), true);
    }
}

Библиотека SharpZipLib

SharpZipLib — это мощная сторонняя библиотека с открытым исходным кодом, предоставляющая расширенные возможности по сравнению со встроенными средствами. Она поддерживает больше форматов (GZip, BZip2, Tar) и даёт более гибкий контроль над процессом сжатия.

Установка SharpZipLib

Установите библиотеку через NuGet Package Manager:

Install-Package SharpZipLib

Или через .NET CLI:

dotnet add package SharpZipLib

Создание архива с SharpZipLib

using ICSharpCode.SharpZipLib.Zip;
using ICSharpCode.SharpZipLib.Core;

string outputZip = @"C:\Archives\backup.zip";
string[] filesToZip = Directory.GetFiles(@"C:\Data\Files", "*.*", SearchOption.AllDirectories);

using (FileStream fsOut = File.Create(outputZip))
using (ZipOutputStream zipStream = new ZipOutputStream(fsOut))
{
    zipStream.SetLevel(9); // Максимальное сжатие (0-9)

    foreach (string filename in filesToZip)
    {
        FileInfo fi = new FileInfo(filename);
        string entryName = ZipEntry.CleanName(fi.Name);
        ZipEntry newEntry = new ZipEntry(entryName);
        newEntry.DateTime = fi.LastWriteTime;
        newEntry.Size = fi.Length;

        zipStream.PutNextEntry(newEntry);

        byte[] buffer = new byte[4096];
        using (FileStream fsInput = File.OpenRead(filename))
        {
            StreamUtils.Copy(fsInput, zipStream, buffer);
        }
        zipStream.CloseEntry();
    }
}

Извлечение архива с SharpZipLib

string inputZip = @"C:\Archives\backup.zip";
string outputDir = @"C:\Data\Restored";

using (FileStream fsIn = File.OpenRead(inputZip))
using (ZipInputStream zipStream = new ZipInputStream(fsIn))
{
    ZipEntry entry;
    while ((entry = zipStream.GetNextEntry()) != null)
    {
        if (!entry.IsDirectory)
        {
            string fullPath = Path.Combine(outputDir, entry.Name);
            string dirName = Path.GetDirectoryName(fullPath);
            
            if (!Directory.Exists(dirName))
                Directory.CreateDirectory(dirName);

            byte[] buffer = new byte[4096];
            using (FileStream streamWriter = File.Create(fullPath))
            {
                StreamUtils.Copy(zipStream, streamWriter, buffer);
            }
        }
    }
}

Сравнение подходов

Выбор между встроенными средствами и SharpZipLib зависит от конкретных задач:

  • System.IO.Compression — идеален для простых операций: создать архив, извлечь все файлы, прочитать метаданные. Не требует установки дополнительных пакетов.
  • SharpZipLib — рекомендуется для сложных сценариев: работа с большими архивами, потоковое

Рекомендаций