Страницы

Поиск по вопросам

Показаны сообщения с ярлыком zip. Показать все сообщения
Показаны сообщения с ярлыком zip. Показать все сообщения

воскресенье, 29 марта 2020 г.

можно ли дозаписать в файл zip в конец файла не распаковывая его на диске на Linux?

#linux #bash #centos #zip #sh


Как дозаписать в файл упакованный в zip не распаковывая его на Linux из скрипта?
Может можно распаковать в оперативку и там дописать и запаковать заново? 
Есть идея монтировать раздел в оперативной памяти для этого, но кажется, что это
не лучший вариант
    


Ответы

Ответ 1



Обновить существующий архив новыми или измененными файлами, рекурсивно: zip -ur ARCH.zip FOLDER|FILE ...

пятница, 14 февраля 2020 г.

Как связаны zlib, gzip и zip? Что у них общего и какие у них отличия?

#zip #png #gzip #сжатие #zlib


Алгоритм сжатия, используемый в zlib, почти тот же, что и в gzip и zip. Чем они отличаются?
    


Ответы

Ответ 1



tl;dr: zip — формат архивов, использующий, как правило, алгоритм Deflate для сжатия; zip-архив может содержать несколько файлов, которые сжимаются отдельно друг от друга. gzip сжимает ровно один файл (этим одним файлом может быть tar-архив) и тоже использует алгоритм Deflate. Библиотека zlib реализует Deflate и используется в zip, gzip, png и многих других приложениях. Формат zip был разработан Филом Кацем как открытый формат, но его реализация, PKZIP, была условно-бесплатной (shareware). В этом формате архива хранятся файлы и структура каталогов, и каждый файл сжимается независимо от других файлов. Файлы и структура каталогов также могут быть зашифрованы. Формат ZIP поддерживает несколько методов сжатия: 0 - The file is stored (no compression) 1 - The file is Shrunk 2 - The file is Reduced with compression factor 1 3 - The file is Reduced with compression factor 2 4 - The file is Reduced with compression factor 3 5 - The file is Reduced with compression factor 4 6 - The file is Imploded 7 - Reserved for Tokenizing compression algorithm 8 - The file is Deflated 9 - Enhanced Deflating using Deflate64(tm) 10 - PKWARE Data Compression Library Imploding (old IBM TERSE) 11 - Reserved by PKWARE 12 - File is compressed using BZIP2 algorithm 13 - Reserved by PKWARE 14 - LZMA (EFS) 15 - Reserved by PKWARE 16 - Reserved by PKWARE 17 - Reserved by PKWARE 18 - File is compressed using IBM TERSE (new) 19 - IBM LZ77 z Architecture (PFS) 97 - WavPack compressed data 98 - PPMd version I, Rev 1 Методы с 1 по 7 являются историческими и не используются. Методы с 9 по 98 добавлены относительно недавно и используются нечасто. Единственным широко распространённым методом является метод 8, Deflate и, в некоторой степени, метод 0, который просто хранит файлы без сжатия. Большинство zip-файлов, с которыми вы столкнётесь, будут использовать только методы 8 и 0. Стандарт ISO/IEC 21320-1:2015 для файловых контейнеров является ограниченным форматом zip, используемым в файлах Java (.jar), Office Open XML (Microsoft Office .docx, .xlsx, .pptx), Office Document Format (.odt, .ods, .odp) и EPUB (.epub). Этот стандарт допускает только методы сжатия 0 и 8, а также имеет другие ограничения вроде отсутствия шифрования или подписей. Примерно в 1990 году группа Info-ZIP написала переносимые и свободные реализации утилит zip и unzip с поддержкой сжатия Deflate и распаковки более старых форматов. Это значительно расширило использование формата .zip. В начале 90-х формат gzip был разработан для замены Unix-утилиты compress. Утилита compress сжимала ровно один файл и добавляла к файлу расширение .Z. Она использовала алгоритм LZW, который в то время защищался патентами, что затрудняло его использование. Хотя некоторые конкретные реализации Deflate были запатентованы Филом Кацем, сам формат патентами не защищается, так что можно написать реализацию Deflate без нарушения патентов. Утилита gzip была задумана как прозрачная замена утилиты compress и фактически может распаковывать сжатые compressом данные. gzip при сжатии добавляет расширение .gz к имени файла. gzip использует формат сжатия Deflate, который позволяет сжимать немного лучше чем compress, быстро распаковывается и проверяет целостность данных с помощью CRC-32. Заголовок формата gzip также позволяет хранить исходное имя файла и время его изменения. Утилита compress сжимает ровно один файл, и для сжатия нескольких файлов с сохранением атрибутов и структуры каталогов обычно создавались архивы tar, которые затем сжимались с помощью compress для получения .tar.Z файла. Чтобы не сжимать всё вручную, утилита tar имела и до сих пор имеет опцию для автоматического включения сжатия с помощью compress; с появлением gzip также добавилась опция для включения gzip-сжатия и создания .tar.gz файлов. Архивы .tar.gz сжимаются лучше чем zip, так как файлы сжимаются не по отдельности и gzip имеет возможность эффективнее работать с избыточностью, особенно если в архиве много мелких файлов. .tar.gz широко распространён в Unix из-за его хорошей переносимости, но есть и более эффективные методы сжатия, так что могут встретиться архивы .tar.bz2 и .tar.xz. В отличие от .tar, .zip архивы хранят список файлов отдельно в конце файла. С учётом того, что каждый файл сжимается независимо, это позволяет прочитать отдельные файлы в архиве без распаковки всего архива целиком. А архив .tar должен быть распакован и прочитан целиком, чтобы даже просто увидеть список файлов в архиве, и это создаёт трудности в некоторых ситуациях. Вскоре после появления gzip, примерно в середине 1990-х годов, те же проблемы с патентами поставили под вопрос бесплатное использование формата изображений .gif, очень широко используемого на досках объявлений (BBS) и во всемирной паутине (WWW — новинка того времени). Так что небольшая группа создала PNG — формат изображений со сжатием без потерь — чтобы заменить GIF. PNG тоже использует формат Deflate для сжатия. Чтобы способствовать широкому использованию формата PNG, были созданы две свободные библиотеки: libpng реализует все функции формата PNG, а zlib предоставляет код сжатия и распаковки для использования в libpng и для других приложений. zlib был адаптирован из кода gzip. Все упомянутые патенты уже истекли. Библиотека zlib поддерживает Deflate, а также три обёртки (wrapping) для потоков Deflate. К ним относятся: отсутствие обёртки вообще («сырой» Deflate), обёртка zlib, который используется в блоках данных формата PNG, и обёртка gzip. Основное различие между обёртками zlib и gzip в том, что zlib-обёртка более компактна: всего 6 байт против как минимум 18 байт для gzip, а проверка целостности Adler-32 выполняется быстрее, чем CRC-32, который используется в gzip. Сырой метод Deflate используется программами, которые читают и записывают формат .zip, который по-своему работает с данными Deflate. Библиотека zlib используется очень широко в том числе в качестве реализации формата gzip; например, она используется в большинстве браузеров и веб-серверов для сжатия передаваемых в HTTP данных (при этом обычно используется формат gzip, так как с форматом zlib возникли некоторые исторические трудности). Разные реализации Deflate могут сжимать одни и те же данные с разной эффективностью, о чем свидетельствует наличие выбираемых уровней сжатия, которые позволяют выбирать между эффективностью сжатия и затраченным временем. zlib и PKZIP - не единственные реализации Deflate. 7-Zip или zopfli могут затратить очень много времени, чтобы сжать данные на несколько процентов эффективнее чем zlib. Утилита pigz, многопоточная реализация gzip, может использовать zlib (уровни сжатия 1-9) или zopfli (уровень сжатия 11) и несколько уменьшает затрачиваемое время с помощью сжатия больших файлов на нескольких ядрах процессора. Слегка вольный перевод ответа от Mark Adler на enSO с некоторыми дополнениями.

воскресенье, 9 февраля 2020 г.

zipfile не распаковывает архив

#python #python_2x #zip #ziparchive


# -*- coding: utf-8 -*-
import zipfile
root = "C:"
z = zipfile.ZipFile(root + '\\ProgramData\\boot//s0urc3.zip','r')
z.extractall()


Все выполняется без ошибок, но архив не распаковывается, почему?
    


Ответы

Ответ 1



Файлы распаковываются в текущую рабочую папку. Добавьте в начало скрипта: import os print os.getcwd() Это покажет вам рабочую папку (обычно это папка, где лежит запускаемый скрипт) и там будут распакованные файлы А в конец скрипта добавьте z.close() Чтобы указать папку, куда нужно сохранить, нужно передать ее в качестве параметра: path_to_extract = 'C:\\Data' z.extractall(path_to_extract) Если в этой папке окажутся файлы с именами, совпадающими с файлами в архиве, они будут перезаписаны без предупреждения.

среда, 29 января 2020 г.

Поворот матрицы (двумерного массива) на 90 градусов в Python с помощью zip

#python #массивы #python_3x #матрицы #zip


Как сделать поворот матрицы в одну строчку без numpy и циклов?

Например если исходная матрица

[[1, 2],
 [3, 4]]


то результирующая должна быть:

[[3, 1],
 [4, 2]]

    


Ответы

Ответ 1



Вполне себе рабочий вариант, если скорость не критична. Но если есть требования по скорости обработки, то лучше все-таки воспользоваться NumPy. Сравнение производительности для массива 100x100: In [72]: a = np.random.randint(0, 99, (100, 100)) In [73]: m = a.tolist() In [74]: a.shape Out[74]: (100, 100) In [75]: %timeit tuple(zip(*m[::-1])) 10000 loops, best of 3: 71 µs per loop In [76]: %timeit np.rot90(a, 3) The slowest run took 9.64 times longer than the fastest. This could mean that an intermediate result is being cached. 100000 loops, best of 3: 2.63 µs per loop Сравнение производительности для массива 1000x1000: In [77]: a = np.random.randint(0, 99, (1000, 1000)) In [78]: m = a.tolist() In [79]: a.shape Out[79]: (1000, 1000) In [80]: %timeit tuple(zip(*m[::-1])) 10 loops, best of 3: 32.6 ms per loop In [81]: %timeit np.rot90(a, 3) The slowest run took 7.54 times longer than the fastest. This could mean that an intermediate result is being cached. 100000 loops, best of 3: 2.59 µs per loop Сравнение производительности для массива 10000x10000: In [82]: a = np.random.randint(0, 99, (10000, 10000)) In [83]: m = a.tolist() In [84]: a.shape Out[84]: (10000, 10000) In [85]: %timeit tuple(zip(*m[::-1])) 1 loop, best of 3: 4.43 s per loop In [86]: %timeit np.rot90(a, 3) The slowest run took 11.29 times longer than the fastest. This could mean that an intermediate result is being cached. 100000 loops, best of 3: 2.59 µs per loop

Ответ 2



​Нашел довольно элегантный способ сделать поворот матрицы в одну строчку без numpy и циклов. В рунете ничего толкового не смог найти, может кому то поможет. Оригинал здесь: Линк на оригинал rotated = zip(*original[::-1]) # Python 2 rotated = tuple(zip(*original[::-1])) # Python 3 Как это работает. original = [[1, 2], [3, 4]] Сначала работает реверс >>> original[::-1] [[3, 4], [1, 2]] И далее этот уже обернутый список передаётся функции zip() zip([3, 4], [1, 2]) # ^ ^----column 2 # |-------column 1 Надеюсь, кому-то пригодится, а то начинают перебор через встроенные циклы и т.д.

воскресенье, 26 января 2020 г.

Как создать zip-архив блоками заданного размера?

#c_sharp #zip


Это продолжение предыдущего вопроса, где я пытаюсь для создания zip-файлов использовать
open source библиотеку SharpZipLib. Возник вопрос организации архивов в виде томов
определенного размера (например, для записи архивов >4Гб на FAT32 диск). Может кто-то
из тех, кто использовал данную библиотеку, подсказать вариант выполнения?
З.Ы. Документация по либе крайне скудная и плохо организована, поэтому сам найти
способ не смог :( 
    


Ответы

Ответ 1



Попробуйте dotNetZip - он позволяет решить вашу задачу. DotNetZip example: int SegmentsCreated ; using (ZipFile zip = new ZipFile()) { zip.UseUnicode= true; // utf-8 zip.AddDirectory(@"MyDocuments\ProjectX"); zip.Comment = "This zip was created at " + System.DateTime.Now.ToString("G") ; zip.MaxOutputSegmentSize = 100*1024 ; // 100k segments zip.Save("MyFiles.zip"); SegmentsCreated = zip.NumberOfSegmentsForMostRecentSave ; }

Ответ 2



Можете простым кодом вроде этого поделить уже готовый zip-файл на части: public static void SplitFile(string source, long partSize, string destinationFormat, int firstFileNumber = 0) { var sourceStream = File.OpenRead(source); var buffer = new byte[80*1024]; var position = sourceStream.Position; var fileNumber = firstFileNumber; while (position < sourceStream.Length) { var filename = String.Format(destinationFormat, fileNumber); using(var destinationStream = File.Create(filename)) { var count = 0; do { count = sourceStream.Read(buffer, 0, (int)Math.Min(buffer.LongLength, partSize - destinationStream.Position)); destinationStream.Write(buffer, 0, count); position += count; } while (count > 0); } fileNumber++; } } вызов: SplitFile( source: @"C:\test\test.zip", destinationFormat: @"C:\test\test.z{0:D2}", partSize: 100000*1024 ); Если хотите сразу писать в несколько файлов, то конструктору ZipFile можно подавать в качестве аргумента экземпляры Stream/Filestream. При желании, можно сделать наследника для одного из этих классов, который и будет автоматически писать в несколько файлов. Это не сложно, просто кода нужно относительно много, т.к. требуется что бы поток был Seekable и Readable(не смотря на то, что мы собираемся только писать в поток)

пятница, 24 января 2020 г.

Какие способы есть для сжатия JSON данных на стороне клиента перед отправкой на сервер?

#json #javascript #zip


При получении данных с сервера можно использовать Gzip, т.е. на сервере включается
соответствующая опция или модуль и данные отправляются клиенту в сжатом виде. Как сделать
что-нибудь подобное и на клиенте чтобы например при отправке запроса POST'ом данные
сжимались?    


Ответы

Ответ 1



Jsend Демонстрация работы

пятница, 10 января 2020 г.

Массовая распаковка zip файлов в один каталог под ОС windows

#windows #файлы #zip


Есть каталог с кучей zip файлов, необходимо содержимое этих файлов свалить в один
каталог за один проход любым способом. ОС windows.
    


Ответы

Ответ 1



Помог бесплатный архиватор 7zip (консольная версия), по подсказке @Pink Tux (выражаю ему свою благодарность за помощь) созрел следующий консольный сценарий: for %f in (*.zip) do 7z x %f выполнять из под командной строки находясь в каталоге с zip-файлами и использовать опцию e вместо x если не надо соблюдать вложенность внутренних каталогов архивов. Если утилита 7z у вас не прописана в системной переменной path, то можете ее просто положить в каталог с zip-файлами.

суббота, 4 января 2020 г.

Как можно редактировать имена txt файлов в архиве zip

#c_sharp #replace #zip


Есть zip архив. В нем 1000 txt файлов. Мне надо всех их редактировать(если можно
то без распаковки, просто имя поменять им) 

Пример:
name-lord


первая замена ame-lord (Remove(0,1)) 
вторая замена ame-word (Replace("-l","-w")) 
и последняя same-word (Добавить букву в начале имени файла)


Как сделать через c# ?

В какой архив закинул там и будет выполнятся алгоритм....
    


Ответы

Ответ 1



Используя библиотеку DotNetZip, можно сделать так: Пример взять отсюда using (ZipFile zip2 = ZipFile.Read(ExistingZipFile)) { foreach (ZipEntry e in zip2) { if (e.FileName.EndsWith(".txt")) { var newname = e.FileName + "rename"; e.FileName = newname; } } zip2.Save(); } Переименовываем все файлы с расширением .txt, добавляю к существующему названию каждого файла суффикс rename Для вашего случая замените соответствующую строку на следующий код: var newname = e.FileName.Substring(1, s.Length - 1); // первая замена newname = newname.Replace("-l", "-w" ); // вторая замена newname = "s" + newname; // третья замена

Ответ 2



Согласно спецификации, имя файла хранится без сжатия в достаточно простой структуре Local File Header (4.3.7). Так что достаточно минимально разобрать файл и внести правки.

вторник, 24 декабря 2019 г.

Как упаковать несколько файлов в zip,которые лежат в разных папках?

#c_sharp #zip


Есть List в котором содержатся пути(Path) всех файлов, которые я хочу упаковать.

Проблема в том что эти файлы в разных папках. Можно как то скопировать их в новую
папку, а потом их упаковать, но количество этих файлов очень велико, так неудобно.

Есть ли какой нибудь способ?

Код создания архива:

using (ZipFile zip = new ZipFile())
{
    zip.CompressionLevel = Ionic.Zlib.CompressionLevel.BestCompression;
    zip.AddDirectory(@"C:\project\");
    zip.AddFile(@"c:\Temp\Import.csv");
    zip.Save(@"C:\Temp\PackedProject.zip");
}

    


Ответы

Ответ 1



Приведенный вами код, к сожалению, не работоспособен. Класс ZipFile есть в библиотеке классов, но он статический и не рекомендован Microsoft для использования в приложениях для Windows Store, там же рекомендовано использовать класс ZipArchive. MSDN Если полные имена (путь+имя) файлов уже содержатся в List fileNames, то не важно в каких папках они находятся, главное чтобы были права на чтение этих файлов. Если все условия выполнены, то дальше все довольно просто: using System; using System.IO; using System.IO.Compression; using (FileStream zipToOpen = new FileStream(@"newArchive.zip", FileMode.OpenOrCreate)) { using (ZipArchive archive = new ZipArchive(zipToOpen, ZipArchiveMode.Update)) { foreach (string fileName in fileNames) { FileInfo fi = new FileInfo(fileName) ZipArchiveEntry fileEntry = archive.CreateEntryFromFile(fi.FullName,fi.Name,CompressionLevel.Optimal); } } } как-то так. Более подробно читать в MSDN Можно улучшить результат если собирать файлы не в string, а сразу в FileInfo и List соответственно. Преимущество использования 'FileInfo' для хранения информации о файлах заключается в том, что есть ряд методов получения уже готовых коллекций этих объектов, например как дочерние узлы DirectoryInfo, и "из коробки" получаем легкие манипуляции с именами файлов. как то выделение пути из полного имени, получение только имени без пути плюс дополнительная функциональность, которая может внезапно понадобиться при работе с файлом. например уточнить права доступа.

понедельник, 23 декабря 2019 г.

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

#java #android #zip


Здравствуйте! Уже несколько дней мучаюсь с проблемой:
Мне нужно программно создать архив, и поместить в него файлы из массива.
Использовал cледующий код:

private static final int BUFFER = 80000;

public void zip(String[] _files, String zipFileName) {
    try {
        BufferedInputStream origin = null;
        FileOutputStream dest = new FileOutputStream(zipFileName);
        ZipOutputStream out = new ZipOutputStream(new BufferedOutputStream(
                dest));
        byte data[] = new byte[BUFFER];

        for (int i = 0; i < _files.length; i++) {
            Log.v("Compress", "Adding: " + _files[i]);
            FileInputStream fi = new FileInputStream(_files[i]);
            origin = new BufferedInputStream(fi, BUFFER);

            ZipEntry entry = new ZipEntry(_files[i].substring(_files[i].lastIndexOf("/")
+ 1));
            out.putNextEntry(entry);
            int count;

            while ((count = origin.read(data, 0, BUFFER)) != -1) {
                out.write(data, 0, count);
            }
            origin.close();
        }

        out.close();
    } catch (Exception e) {
        e.printStackTrace();
    }
}


Вроде все идет хорошо, архив на месте, но:
Сам архив должен весить порядка 15 МБ, а весит всего 10,56 МБ, и архиватор говорит:
"Архив поврежден". Возможно, конечно, вес сокращен из-за сжатия, но почему архиватор
отказывается открывать его, и как убрать сжатие? Подскажите, пожалуйста. Заранее спасибо!
    


Ответы

Ответ 1



Проблема у вас в том, что вы обрабатываете не все исключения и закрываете выходной поток не в секции finally, вот так примерно должен выглядеть рабочий код private static final int BUFFER = 80000; public void zip(String[] files, String zipFileName) { ZipOutputStream out = null; try { out = new ZipOutputStream(new BufferedOutputStream(new FileOutputStream(zipFileName))); byte data[] = new byte[BUFFER]; for (int i = 0; i < files.length; i++) { processFile(out, data, files[i]); } } catch (IOException e) { e.printStackTrace(); } finally { close(out); } } private void processFile(ZipOutputStream out, byte[] data, String file) { BufferedInputStream origin = null; try { origin = new BufferedInputStream(new FileInputStream(file), BUFFER); ZipEntry entry = new ZipEntry(file.substring(file.lastIndexOf("/") + 1)); out.putNextEntry(entry); int count; while ((count = origin.read(data, 0, BUFFER)) != -1) { out.write(data, 0, count); } } catch (IOException e) { e.printStackTrace(); } finally { close(origin); } } private void close(Closeable closeable){ if (null != closeable){ try { closeable.close(); } catch (IOException ignored) { } } }

суббота, 14 декабря 2019 г.

Распаковка массива zip архивов в одну папку с переименованием файлов

#windows #файлы #cmd #powershell #zip


Есть папка с большим количеством zip-архивов.
Каждый архив содержит внутри папку(имя папки то же, что и у архива) с 1+ файлов.
Как c помощью средств windows(и какого-нибудь архиватора)извлечь все файлы в одну
папку так, чтобы конечные файлы были переименованы по шаблону "<имя папки>-<имя файла>"?

    


Ответы

Ответ 1



Kак подсказал @nick_gabpe, нужно распаковать в папку: FOR %%Z IN ("%src_dir%\*.zip") DO ( 7z e "%%Z" -o"%tgt_dir%" ) Далее PowerShell скрипт выполнит остальное: $fiels = Get-ChildItem -Path . -rec -Filter "*.txt" # найти все файлы из директории, откуда запускается (.), с расширением txt foreach($f in $fiels){ $dirName = (Get-Item $f.FullName).Directory.Name # получаем имя папки # копируем файл с новым именем. Путь C:\temp\1111 должен существовать Copy-Item -Path $f.FullName -Destination "C:\temp\1111\$($dirName+ "-" + $f.Name)" }

Ответ 2



Вариант на чистом PowerShell (без использования внешних утилит): # Указываем папку с архивами $rootPath = 'D:\TEST' # Извлекаем и удаляем все архивы Add-Type -AssemblyName System.IO.Compression.FileSystem Get-Item "$rootPath\*.zip" | ForEach-Object { [System.IO.Compression.ZipFile]::ExtractToDirectory($_.FullName, $rootPath) Remove-Item $_.FullName -Verbose } # Избавляемся от папок Get-ChildItem $rootPath -Directory | ForEach-Object { Get-ChildItem $_.FullName | ForEach-Object { Move-Item $_.FullName -Destination "$($_.Directory.Parent.FullName)\$($_.Directory.BaseName)-$($_.Name)" -Verbose } Remove-Item $_.FullName -Verbose }

понедельник, 15 июля 2019 г.

Сохранение нескольких json файлов в zip архив

Есть вот такой метод:
public boolean saveZip(File zipFile) { Log.d(LOG_TAG, zipFile.getAbsolutePath()); boolean result = false;
if (!zipFile.exists()) zipFile.getParentFile().mkdirs();
try { ZipOutputStream zipOutputStream = new ZipOutputStream(new BufferedOutputStream(new FileOutputStream(zipFile)));
JsonWriter writer = new JsonWriter(new OutputStreamWriter(zipOutputStream, "UTF-8")); // Запись таблицы DB_TABLE_NAME в архив Log.d(LOG_TAG, "ЗАПИСЬ: " + DB_TABLE_NAME + ".json"); Cursor cursor = getAllData(); // основная таблица данных; { ZipEntry entry = new ZipEntry(DB_TABLE_NAME + ".json"); zipOutputStream.putNextEntry(entry); writer.beginArray(); while (cursor.moveToNext()) { writer.beginObject(); writer.name(_ID) .value(cursor.getLong(cursor.getColumnIndex(_ID))); writer.name(COLUMN_PARENT) .value(cursor.getLong(cursor.getColumnIndex(COLUMN_PARENT))); writer.name(COLUMN_THING_NAME) .value(cursor.getString(cursor.getColumnIndex(COLUMN_THING_NAME))); writer.name(COLUMN_DESCRIPTION) .value(cursor.getString(cursor.getColumnIndex(COLUMN_DESCRIPTION))); writer.name(COLUMN_DATE) .value(cursor.getString(cursor.getColumnIndex(COLUMN_DATE))); writer.name(COLUMN_ISBOX) .value(cursor.getInt(cursor.getColumnIndex(COLUMN_ISBOX))); writer.endObject(); } writer.endArray(); cursor.close(); writer.close(); zipOutputStream.closeEntry();
} // Запись таблицы DB_TABLE_NAME_FOTOS в архив Log.d(LOG_TAG, "ЗАПИСЬ: " + DB_TABLE_NAME_FOTOS + ".json"); cursor = getAllDataNameFotos(); List fotos = new ArrayList<>(); { ZipEntry entry = new ZipEntry(DB_TABLE_NAME_FOTOS + ".json"); zipOutputStream.putNextEntry(entry); writer.beginArray(); while (cursor.moveToNext()) { writer.beginObject(); writer.name(_ID) .value(cursor.getLong(cursor.getColumnIndex(_ID))); writer.name(COLUMN_ID_THING) .value(cursor.getLong(cursor.getColumnIndex(COLUMN_ID_THING))); writer.name(COLUMN_NAME_FOTO) .value(cursor.getString(cursor.getColumnIndex(COLUMN_NAME_FOTO))); fotos.add(cursor.getString(cursor.getColumnIndex(COLUMN_NAME_FOTO))); writer.name(COLUMN_DESCRIPTION_FOTO) .value(cursor.getString(cursor.getColumnIndex(COLUMN_DESCRIPTION_FOTO))); writer.name(COLUMN_DATE) .value(cursor.getString(cursor.getColumnIndex(COLUMN_DATE))); writer.endObject(); } cursor.close(); writer.endArray(); zipOutputStream.closeEntry(); }
// Сохраняем фотки в архив { Log.d(LOG_TAG, "Сохраняем фото в архив"); for (String fotoName : fotos) { File fileFoto = new File(fotoDir, fotoName); if (fileFoto.isFile()) { ZipEntry entry = new ZipEntry(fileFoto.getName()); zipOutputStream.putNextEntry(entry); byte[] buffer = new byte[1024]; int length; InputStream inputStream = new FileInputStream(fileFoto); while ((length = inputStream.read(buffer)) > -1) { zipOutputStream.write(buffer, 0, length); } inputStream.close(); zipOutputStream.closeEntry(); }
} }
// запись таблицы DB_TABLE_NAME_ATTR Log.d(LOG_TAG, "ЗАПИСЬ: " + DB_TABLE_NAME_ATTR + ".json"); cursor = getAllDataNameAttr(); { ZipEntry entry = new ZipEntry(DB_TABLE_NAME_ATTR + ".json"); zipOutputStream.putNextEntry(entry); writer.beginArray(); while (cursor.moveToNext()) { writer.beginObject(); writer.name(_ID) .value(cursor.getLong(cursor.getColumnIndex(_ID))); writer.name(COLUMN_NAME_ATTR) .value(cursor.getString(cursor.getColumnIndex(COLUMN_NAME_ATTR))); writer.endObject(); } writer.endArray(); cursor.close(); zipOutputStream.closeEntry(); }
// запись таблицы DB_TABLE_NAME_LIST_ATTR cursor = getAllDataNameListAttr(); { ZipEntry entry = new ZipEntry(DB_TABLE_NAME_LIST_ATTR + ".json"); zipOutputStream.putNextEntry(entry); writer.beginArray(); while (cursor.moveToNext()) { writer.beginObject(); writer.name(_ID) .value(cursor.getLong(cursor.getColumnIndex(_ID))); writer.name(COLUMN_ID_THING) .value(cursor.getLong(cursor.getColumnIndex(COLUMN_ID_THING))); writer.name(COLUMN_ID_ATTR) .value(cursor.getLong(cursor.getColumnIndex(COLUMN_ID_ATTR))); writer.name(COLUMN_DESCRIPTION_ATTR) .value(cursor.getString(cursor.getColumnIndex(COLUMN_DESCRIPTION_ATTR))); writer.endObject(); } writer.endArray(); cursor.close(); zipOutputStream.closeEntry(); }
zipOutputStream.close();
} catch (IOException e){ Log.d(LOG_TAG, e.toString()); return result; } result = true; return result;
}
Проблема в том что метод writer.close() полностью закрывает и zipOutputStream, и дальше метод 'zipOutputStream.closeEntry()' не срабатывает. А если убрать метод writer.close(), то работает, но файлы в архиве пустые получаются.


Ответ

В итоге нашел два способа решения проблемы:
1) Для каждого нового файла json, создавать новый объект writer, в конце создания файла использовать метод writer.flush() (как и подсказали в комментариях), только ни в коем случае не использовать метод writer.close
2) Использовать свой класс наследованный от ZipOutputStream. Вот какой класс у меня получился:
private class MyZipOutputStream extends ZipOutputStream{ public MyZipOutputStream(OutputStream os) { super(os); } @Override public void close() throws IOException { super.closeEntry(); } public void closeclose() throws IOException { super.close(); } }
Получается что объект при использовании метода close() закрывает Entry. То есть при закрытии writer, не происходит полное закрытие 'zipOutputStream'. Только отдельно добавлен метод closeclose() который и будет осуществлять полное закрытие zip-файла.

понедельник, 15 апреля 2019 г.

zipfile не распаковывает архив

# -*- coding: utf-8 -*- import zipfile root = "C:" z = zipfile.ZipFile(root + '\\ProgramData\\boot//s0urc3.zip','r') z.extractall()
Все выполняется без ошибок, но архив не распаковывается, почему?


Ответ

Файлы распаковываются в текущую рабочую папку. Добавьте в начало скрипта:
import os print os.getcwd()
Это покажет вам рабочую папку (обычно это папка, где лежит запускаемый скрипт) и там будут распакованные файлы
А в конец скрипта добавьте
z.close()
Чтобы указать папку, куда нужно сохранить, нужно передать ее в качестве параметра:
path_to_extract = 'C:\\Data' z.extractall(path_to_extract)
Если в этой папке окажутся файлы с именами, совпадающими с файлами в архиве, они будут перезаписаны без предупреждения

пятница, 29 марта 2019 г.

Поворот матрицы (двумерного массива) на 90 градусов в Python с помощью zip

Как сделать поворот матрицы в одну строчку без numpy и циклов?
Например если исходная матрица
[[1, 2], [3, 4]]
то результирующая должна быть:
[[3, 1], [4, 2]]


Ответ

Вполне себе рабочий вариант, если скорость не критична.
Но если есть требования по скорости обработки, то лучше все-таки воспользоваться NumPy.
Сравнение производительности для массива 100x100:
In [72]: a = np.random.randint(0, 99, (100, 100))
In [73]: m = a.tolist()
In [74]: a.shape Out[74]: (100, 100)
In [75]: %timeit tuple(zip(*m[::-1])) 10000 loops, best of 3: 71 µs per loop
In [76]: %timeit np.rot90(a, 3) The slowest run took 9.64 times longer than the fastest. This could mean that an intermediate result is being cached. 100000 loops, best of 3: 2.63 µs per loop
Сравнение производительности для массива 1000x1000:
In [77]: a = np.random.randint(0, 99, (1000, 1000))
In [78]: m = a.tolist()
In [79]: a.shape Out[79]: (1000, 1000)
In [80]: %timeit tuple(zip(*m[::-1])) 10 loops, best of 3: 32.6 ms per loop
In [81]: %timeit np.rot90(a, 3) The slowest run took 7.54 times longer than the fastest. This could mean that an intermediate result is being cached. 100000 loops, best of 3: 2.59 µs per loop
Сравнение производительности для массива 10000x10000:
In [82]: a = np.random.randint(0, 99, (10000, 10000))
In [83]: m = a.tolist()
In [84]: a.shape Out[84]: (10000, 10000)
In [85]: %timeit tuple(zip(*m[::-1])) 1 loop, best of 3: 4.43 s per loop
In [86]: %timeit np.rot90(a, 3) The slowest run took 11.29 times longer than the fastest. This could mean that an intermediate result is being cached. 100000 loops, best of 3: 2.59 µs per loop

понедельник, 4 февраля 2019 г.

Как можно редактировать имена txt файлов в архиве zip

Есть zip архив. В нем 1000 txt файлов. Мне надо всех их редактировать(если можно то без распаковки, просто имя поменять им)
Пример: name-lord
первая замена ame-lord (Remove(0,1)) вторая замена ame-word (Replace("-l","-w")) и последняя same-word (Добавить букву в начале имени файла)
Как сделать через c# ?
В какой архив закинул там и будет выполнятся алгоритм....


Ответ

Используя библиотеку DotNetZip, можно сделать так:
Пример взять отсюда
using (ZipFile zip2 = ZipFile.Read(ExistingZipFile)) { foreach (ZipEntry e in zip2) { if (e.FileName.EndsWith(".txt")) { var newname = e.FileName + "rename"; e.FileName = newname; } } zip2.Save(); }
Переименовываем все файлы с расширением .txt, добавляю к существующему названию каждого файла суффикс rename
Для вашего случая замените соответствующую строку на следующий код:
var newname = e.FileName.Substring(1, s.Length - 1); // первая замена newname = newname.Replace("-l", "-w" ); // вторая замена newname = "s" + newname; // третья замена

вторник, 27 ноября 2018 г.

Как упаковать несколько файлов в zip,которые лежат в разных папках?

Есть List в котором содержатся пути(Path) всех файлов, которые я хочу упаковать.
Проблема в том что эти файлы в разных папках. Можно как то скопировать их в новую папку, а потом их упаковать, но количество этих файлов очень велико, так неудобно.
Есть ли какой нибудь способ?
Код создания архива:
using (ZipFile zip = new ZipFile()) { zip.CompressionLevel = Ionic.Zlib.CompressionLevel.BestCompression; zip.AddDirectory(@"C:\project\"); zip.AddFile(@"c:\Temp\Import.csv"); zip.Save(@"C:\Temp\PackedProject.zip"); }


Ответ

Приведенный вами код, к сожалению, не работоспособен. Класс ZipFile есть в библиотеке классов, но он статический и не рекомендован Microsoft для использования в приложениях для Windows Store, там же рекомендовано использовать класс ZipArchive. MSDN
Если полные имена (путь+имя) файлов уже содержатся в List fileNames, то не важно в каких папках они находятся, главное чтобы были права на чтение этих файлов. Если все условия выполнены, то дальше все довольно просто:
using System; using System.IO; using System.IO.Compression;
using (FileStream zipToOpen = new FileStream(@"newArchive.zip", FileMode.OpenOrCreate)) { using (ZipArchive archive = new ZipArchive(zipToOpen, ZipArchiveMode.Update)) { foreach (string fileName in fileNames) { FileInfo fi = new FileInfo(fileName) ZipArchiveEntry fileEntry = archive.CreateEntryFromFile(fi.FullName,fi.Name,CompressionLevel.Optimal); } } }
как-то так. Более подробно читать в MSDN
Можно улучшить результат если собирать файлы не в string, а сразу в FileInfo и List соответственно. Преимущество использования 'FileInfo' для хранения информации о файлах заключается в том, что есть ряд методов получения уже готовых коллекций этих объектов, например как дочерние узлы DirectoryInfo, и "из коробки" получаем легкие манипуляции с именами файлов. как то выделение пути из полного имени, получение только имени без пути плюс дополнительная функциональность, которая может внезапно понадобиться при работе с файлом. например уточнить права доступа.

пятница, 16 ноября 2018 г.

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

Здравствуйте! Уже несколько дней мучаюсь с проблемой: Мне нужно программно создать архив, и поместить в него файлы из массива. Использовал cледующий код:
private static final int BUFFER = 80000;
public void zip(String[] _files, String zipFileName) { try { BufferedInputStream origin = null; FileOutputStream dest = new FileOutputStream(zipFileName); ZipOutputStream out = new ZipOutputStream(new BufferedOutputStream( dest)); byte data[] = new byte[BUFFER];
for (int i = 0; i < _files.length; i++) { Log.v("Compress", "Adding: " + _files[i]); FileInputStream fi = new FileInputStream(_files[i]); origin = new BufferedInputStream(fi, BUFFER);
ZipEntry entry = new ZipEntry(_files[i].substring(_files[i].lastIndexOf("/") + 1)); out.putNextEntry(entry); int count;
while ((count = origin.read(data, 0, BUFFER)) != -1) { out.write(data, 0, count); } origin.close(); }
out.close(); } catch (Exception e) { e.printStackTrace(); } }
Вроде все идет хорошо, архив на месте, но: Сам архив должен весить порядка 15 МБ, а весит всего 10,56 МБ, и архиватор говорит: "Архив поврежден". Возможно, конечно, вес сокращен из-за сжатия, но почему архиватор отказывается открывать его, и как убрать сжатие? Подскажите, пожалуйста. Заранее спасибо!


Ответ

Проблема у вас в том, что вы обрабатываете не все исключения и закрываете выходной поток не в секции finally, вот так примерно должен выглядеть рабочий код
private static final int BUFFER = 80000;
public void zip(String[] files, String zipFileName) { ZipOutputStream out = null; try { out = new ZipOutputStream(new BufferedOutputStream(new FileOutputStream(zipFileName))); byte data[] = new byte[BUFFER]; for (int i = 0; i < files.length; i++) { processFile(out, data, files[i]); } } catch (IOException e) { e.printStackTrace(); } finally { close(out); } }
private void processFile(ZipOutputStream out, byte[] data, String file) { BufferedInputStream origin = null; try { origin = new BufferedInputStream(new FileInputStream(file), BUFFER); ZipEntry entry = new ZipEntry(file.substring(file.lastIndexOf("/") + 1)); out.putNextEntry(entry); int count; while ((count = origin.read(data, 0, BUFFER)) != -1) { out.write(data, 0, count); } } catch (IOException e) { e.printStackTrace(); } finally { close(origin); } }
private void close(Closeable closeable){ if (null != closeable){ try { closeable.close(); } catch (IOException ignored) { } } }