Форум программистов, компьютерный форум, киберфорум
Visual Basic
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
 
Рейтинг 5.00/1: Рейтинг темы: голосов - 1, средняя оценка - 5.00
1386 / 842 / 91
Регистрация: 08.02.2017
Сообщений: 3,588
Записей в блоге: 1

Работа с zip архивами

29.10.2024, 02:49. Показов 18480. Ответов 282
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Из всего, что попадалось по теме сжатия/распаковки ZIP наиболее интересные были примеры с использованием библиотеки Zlib. Оригинальная zlib использует cdecl экспорт функций, но есть реализация zlibwapi.dll, которую можно использовать в VB. Вот хороший пример использования. Там можно увидеть как сжть/распаковать массив байтов, но вот беда, очень сложно найти пример под VB с более обширным использованием, способной на большее, данной либы, которая не есть простая, там есть функции с использованием множества параметров констант и длинных структур, которые чтобы узнать наверное надо долго копатся в сишных заголочниках. Но HackerVlad в личной беседе говорил, что у него есть исходники с использованием данной библиотеки, поэтому любезно прошу его поделиться данной информацией.

Добавлено через 1 минуту
кстати словосочетание zip-архивами в названии форум блочит почему-то )

Добавлено через 6 минут
На одном форуме есть хороший пример испльзования функций zlib для извлечения/распаковки отдельных файлов, там
Кликните здесь для просмотра всего текста
обсуждался какой-то экзотический ЯП Clarion, но очень наглядно
Code
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
! Источнег: https://forum.clarionlife.net/viewtopic.php?t=2389
! Для добавления в архив PwlZip ваш пароль
ZipHandle = zipOpen(NEW_ZIPPACK, 0)
If EncryptFlag = 1
Res# = zipOpenNewFileInZip3(ZipHandle, PATH_CURZIP, Zinfo, 0, 0, 0, 0, Comment, Z_DEFLATED, CompressionFlag,0,-15,8,0,PwlZip,0)
Else
Res# = zipOpenNewFileInZip(ZipHandle, PATH_CURZIP, Zinfo, 0, 0, 0, 0, Comment, Z_DEFLATED, CompressionFlag)
.
 
!Для чтения из архива
ZipHandle = unzOpen(PATH_INFILE_PACK)
LocRes1=UnzGoToFirstFile(ZipHandle)
If unzGetCurrentFileInfo(ZipHandle,FinFo,PATH_NAMEUPD_TMP,Size(PATH_NAMEUPD_TMP),0,0,Comment,Size(Comment)).
If FinFo.Flag = 3 !признак шифрованного zip по крайней мере так я понял после мыкания с архивами
LocRes2 = unzOpenCurrentFilePassword(ZipHandle,PwlZip)
Else
LocRes2 = UnzOpenCurrentFile(ZipHandle)

Здесь подробное описание функций, структур и констант, однако я не нашел там unzGetCurrentFileInfo и т.п.
0
Programming
Эксперт
39485 / 9562 / 3019
Регистрация: 12.04.2006
Сообщений: 41,671
Блог
29.10.2024, 02:49
Ответы с готовыми решениями:

Работа с ZIP-архивами - распаковка файлов
Привет, уважаемый ALL! Подскажите, как можно работать с zip архивами из VBA? Стоит задача: 1) прочитать из архива...

Автоматизировать заполнение "Графика выполненных работ по месяцам"
Используя готовую рабочую книгу Blank1.xls, автоматизировать заполнение "Графика выполненных работ по месяцам". Из диапазона дат в...

Задания из лаб.работ
Надоедаю наверное уже всем...

282
Испарился
 Аватар для HackerVlad
1741 / 637 / 45
Регистрация: 10.09.2021
Сообщений: 2,769
17.02.2025, 20:24
Студворк — интернет-сервис помощи студентам
Ну да, если захотеть, можно придумать будет вообще без класса через SetFilePointer какой-нибудь читать нужный кусок)))) чтобы сэкономить эти 32 Кб, как ты говоришь)

Добавлено через 46 секунд
Цитата Сообщение от The trick Посмотреть сообщение
множество типов данных
да меня удивило как ты там объекты хранишь, вообще не врубился в это
0
Модератор
10048 / 3894 / 883
Регистрация: 22.02.2013
Сообщений: 5,847
Записей в блоге: 79
17.02.2025, 20:51
Цитата Сообщение от HackerVlad Посмотреть сообщение
чтобы сэкономить эти 32 Кб, как ты говоришь)
Ты скажи кого в 2025 году волнуют 32 кб?
0
Испарился
 Аватар для HackerVlad
1741 / 637 / 45
Регистрация: 10.09.2021
Сообщений: 2,769
18.02.2025, 03:51
The trick, меня, смотри, я уже придумал технологию для само-распаковывающегося SFX-архива:

1. Используем твой класс для того чтобы дописать в конец ZIP или CAB файл (только один файл!) но внутри он может содержать много файлов как бы
2. SFX программа не будет использовать класс вообще, чтобы сэкономить 32 Кб, а будет просто через SetFilePoiner всегда с одной и той же позиции и до конца файла считывать файл-архива и принимать решения о распаковки в какую-то папку

P. S. Скорее всего у тебя в твоей структуре есть 4 байта выделенные для размера файла (я не проверял но я бы лично так делал) и скорее всего их можно было бы тоже прочитать для того чтобы узнать длину вшитого файла (всегда из одной позиции) скорее всего но можно этого и не делать если читать до EOF всё равно же начинать чтение надо всегда с одного и тоже смещения, если файл будет всегда называться одинаково то и смещение по логике всегда будет одинаковым и если файл будет только один

Добавлено через 2 минуты
Кстати я УЖЕ написал SFX из ресурсов, но там наврное максимум мегабайтов 500-800 потянет, есть надежда что технология хвоста файла больше позволит мегабайтов для архива выделить.

Добавлено через 2 минуты
The trick, у Христиана Гислера самараспаковка около 40 Кб занимает, мне нужно сделать меньше, чтобы быть круче

Добавлено через 4 часа 41 минуту
Я тут так подумал, я думаю, что класс вообще не нужен, просто берешь дописываешь сам в EXE буфер файла и всё. И не нужно ничего знать вообще ни имя файла, ни его размер, ничего не нужно, ни класс не нужен вообще для SFX реализации.

Добавлено через 1 минуту
У меня вот болванка (программа для самораспаковки) занимает 24576 EXE. Это меньше чем где-либо у кого-либо.

Добавлено через 6 секунд
У меня вот болванка (программа для самораспаковки) занимает 24576 EXE. Это меньше чем где-либо у кого-либо.

Добавлено через 1 минуту
И я думаю можно подписать в конец EXE файла начиная с 24577 байта этот свой добавочный CAB файл и всё.

Добавлено через 30 секунд
У меня была даже мысль удалить лишние нули в конце EXE чтобы сэкономить ещё чуть-чуть, но пока не буду...

Добавлено через 10 минут
Только что провернул интересный финт:

Решил дописать в конец EXE и присоединить туда CAB файл, сначала думал писать скрипт для этого, но поленился и решил это сделать с помощью Total Commander, просто так этого и в TC не сделать, погуглил и понял как это сделать взял EXE переименовал в file01.txt потом взял CAB и переименовал в file02.txt потом в TC выбрал пункт в меню Собрать/Склеить файлы и вуаля! Магия! Готово! Получился на выходе новый файл уже с подписанным в хвост EXE архивом! Далее проверяем - нажимает комбинацию клавиш Ctrl+PageDown и TC входит успешно в EXE как в архив! Вуаля! Всё вручную через Total Commander! Просто магия! Даже класс от The trick не понадобился)))

Добавлено через 1 час 40 минут
The trick, но я тут выяснил что просто подписанные в хвост EXE большие объёмы тоже занимают Virtual Size Memory так что ни факт что будет чем-то лучше чем из ресурсов конечно, тоже много ест виртуалки... Просто запускаешь EXE где в хвосте что-то огромное записано и смотришь на этот процесс и видишь как отъело просто так без причины много виртуалки.
0
Модератор
10048 / 3894 / 883
Регистрация: 22.02.2013
Сообщений: 5,847
Записей в блоге: 79
18.02.2025, 12:56
Цитата Сообщение от HackerVlad Посмотреть сообщение
The trick, но я тут выяснил что просто подписанные в хвост EXE большие объёмы тоже занимают Virtual Size Memory так что ни факт что будет чем-то лучше чем из ресурсов конечно, тоже много ест виртуалки...
Ничего подобного.Вложение 1502149
0
Модератор
10048 / 3894 / 883
Регистрация: 22.02.2013
Сообщений: 5,847
Записей в блоге: 79
18.02.2025, 12:56
Цитата Сообщение от HackerVlad Посмотреть сообщение
The trick, но я тут выяснил что просто подписанные в хвост EXE большие объёмы тоже занимают Virtual Size Memory так что ни факт что будет чем-то лучше чем из ресурсов конечно, тоже много ест виртуалки...
Ничего подобного.
0
Испарился
 Аватар для HackerVlad
1741 / 637 / 45
Регистрация: 10.09.2021
Сообщений: 2,769
18.02.2025, 15:29
The trick, а теперь посмотри с помощью программы Process Hacker или Process Explorer, ровно как на этой картинке: https://www.cyberforum.ru/atta... 1613154219

Добавлено через 3 минуты
Я только что провёл эксперимент создал пустой EXE на VB6 откомпилировал новый стандартный EXE он оказался 16 Кб всего.
Потом я просто внедрил в этот новый EXE в хвост файл на 25 Мб (провбовал как с помощью класса The Trick так и через ручную склейку через Total Commander)
Потом просто запускаешь Process Hacker открываешь этот запущенный процесс и видишь как виртуальная память уже 75 Мб почему-то (в три раза превышает вложение в 25 Мб)! Как это объяснить?
0
Испарился
 Аватар для HackerVlad
1741 / 637 / 45
Регистрация: 10.09.2021
Сообщений: 2,769
18.02.2025, 15:31
EXE на 25 Мб а Process Hacker выдаёт пик виртуалки вообще на 75 Мб. Почему?
Миниатюры
Работа с zip архивами  
0
Модератор
10048 / 3894 / 883
Регистрация: 22.02.2013
Сообщений: 5,847
Записей в блоге: 79
18.02.2025, 15:37
Цитата Сообщение от HackerVlad Посмотреть сообщение
Я только что провёл эксперимент создал пустой EXE на VB6 откомпилировал новый стандартный EXE он оказался 16 Кб всего.
Нет. Процесс со стандартным EXE с пустой формой никак 16КБ не может занимать виртуальной памяти. Как минимум сам EXE получается 16КБ, а там еще куча системных DLLок лежит. Короче думай как хочешь, достал ты уже фигню нести какую-то. Отписываюсь от темы.
0
Испарился
 Аватар для HackerVlad
1741 / 637 / 45
Регистрация: 10.09.2021
Сообщений: 2,769
18.02.2025, 15:57
Так и не объяснил почему 75 Мб. Решил свалить, чтобы не оправдываться.

Добавлено через 49 секунд
Цитата Сообщение от The trick Посмотреть сообщение
Процесс со стандартным EXE с пустой формой никак 16КБ не может занимать виртуальной памяти.
Ну пускай занимало бы несколько мегабайтов (в пределах 10) но не 75 же!

Добавлено через 2 минуты
Цитата Сообщение от The trick Посмотреть сообщение
достал ты уже фигню нести какую-то
Когда понял что никак не может объяснить это)))))))))))

Добавлено через 4 минуты
The trick, ну VMMap у меня тоже показывает, как и у тебя кстати
0
Испарился
 Аватар для HackerVlad
1741 / 637 / 45
Регистрация: 10.09.2021
Сообщений: 2,769
23.02.2025, 16:35
Тема неожиданно получила дальнейшее развитие. Так как я узнал о новом коде с помощью API как извлечь все файлы из ZIP-архива. Поэтому я по быстрому состряпал новый пример-программу для этой цели.

Как распаковать ZIP с помощью Win32 API на VB6

Visual Basic
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
Option Explicit
Private Declare Function SHFileOperation Lib "shell32" Alias "SHFileOperationW" (ByVal lpFileOp As Long) As Long
 
Private Const FO_COPY = &H2
Private Const FOF_SILENT = &H4
Private Const FOF_NOCONFIRMATION = &H10
 
Private Type SHFILEOPSTRUCT
   hwnd        As Long
   wFunc       As Long
   pFrom       As String
   pTo         As String
   fFlags      As Integer
   fAborted    As Boolean
   hNameMaps   As Long
   sProgress   As String
 End Type
 
Public Function UnpackingZIP(ByVal Source As String, ByVal DestinationFolder As String, Optional ShowProgress As Boolean) As Boolean
    Dim SHF As SHFILEOPSTRUCT
    Dim pFrom As String
    
    pFrom = Source & "\*.*" & vbNullChar
    
    SHF.hwnd = hwnd
    SHF.wFunc = FO_COPY
    If Not ShowProgress Then
        SHF.fFlags = FOF_SILENT Or FOF_NOCONFIRMATION
    Else
        SHF.fFlags = FOF_NOCONFIRMATION
    End If
    SHF.pFrom = pFrom & vbNullChar
    SHF.pTo = DestinationFolder
    
    If SHFileOperation(VarPtr(SHF)) = 0 Then UnpackingZIP = True
End Function
 
Private Sub Command1_Click()
    Screen.MousePointer = 13
    
    If UnpackingZIP(Text1.Text, Text2.Text) = True Then
        Screen.MousePointer = 0
        MsgBox "All files have been successfully copied!", vbInformation
    Else
        Screen.MousePointer = 0
        MsgBox "File copying error, 0 files were copied.", vbCritical
    End If
End Sub
 
Private Sub Form_Load()
    Text1.Text = AppPath & "\TestSource.zip"
    Text2.Text = AppPath & "\TestDestination"
End Sub
Данный пример распаковывает все файлы, даже со всеми вложенными подпапками. Устанавливает правильные атрибуты и дату и время файлов.
Но этот пример работает только начиная от Windows 7, у меня лично на моём компьютере в XP это не работает.
Вложения
Тип файла: zip Unpacking ZIP on API.zip (2.33 Мб, 8 просмотров)
1
1386 / 842 / 91
Регистрация: 08.02.2017
Сообщений: 3,588
Записей в блоге: 1
23.02.2025, 16:46  [ТС]
Цитата Сообщение от HackerVlad Посмотреть сообщение
If Not ShowProgress Then
Типо можно с отображением прогресса в проводнике или без?
0
Испарился
 Аватар для HackerVlad
1741 / 637 / 45
Регистрация: 10.09.2021
Сообщений: 2,769
23.02.2025, 16:55
testuser2, ну да, а ты что не знал? эти флаги давно имеются

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

Visual Basic
1
2
3
4
5
6
7
8
9
Dim oShell As Object
    Dim oFile As Object
    Dim Ret As Long
    
    Set oShell = CreateObject("Shell.Application")
    
    For Each oFile In oShell.NameSpace("D:\Temp\temp.zip").Items
        Ret = (oShell.NameSpace("D:\temp\Testzip\").CopyHere(oFile))
    Next
0
1386 / 842 / 91
Регистрация: 08.02.2017
Сообщений: 3,588
Записей в блоге: 1
23.02.2025, 17:07  [ТС]
В комовской версии не все флаги работают из msdn
Лучше так, иначе в каждой итерации создается и уничтожается объект папки
Visual Basic
1
2
3
4
5
        Wiht oShell.NameSpace("D:\temp\Testzip\")
            For Each oFile In oShell.NameSpace("D:\Temp\temp.zip").Items
                .CopyHere oFile
            Next
        End With
1
Испарился
 Аватар для HackerVlad
1741 / 637 / 45
Регистрация: 10.09.2021
Сообщений: 2,769
23.02.2025, 17:13
testuser2, хорошо, спасибо за это замечание, буду знать. А теперь вопрос на засыпку: как сюда присобачить флаги для скрытия прогресса?
0
1386 / 842 / 91
Регистрация: 08.02.2017
Сообщений: 3,588
Записей в блоге: 1
23.02.2025, 17:41  [ТС]
HackerVlad, сдесь описание параметров
https://learn.microsoft.com/ru... r-copyhere

Добавлено через 3 минуты
Если подключить C:\Windows\SysWOW64\shell32.dll, то можно использовать раннее связывание
Visual Basic
1
2
3
4
    Dim oShell As New Shell32.shell
    Dim folder As Shell32.Folder3
    Set folder = oShell.Namespace("C:\")
    'folder.CopyHere(
1
Испарился
 Аватар для HackerVlad
1741 / 637 / 45
Регистрация: 10.09.2021
Сообщений: 2,769
23.02.2025, 17:59
Цитата Сообщение от testuser2 Посмотреть сообщение
Типо можно с отображением прогресса в проводнике или без?
Единственный минус этого кода в том что можно закрыть форму свою программу до того как завершится извлечение. Тут какая-то странная хрень что во время долгого прогресса передаётся управление форме и всё-всё спокойно можно соверщать.
0
Испарился
 Аватар для HackerVlad
1741 / 637 / 45
Регистрация: 10.09.2021
Сообщений: 2,769
24.02.2025, 16:18
И ещё один минус этого кода в том, что он не работает с файлами docx в отличии от кода The trick

Добавлено через 13 минут
Даже класс от wqweto просто так не читает файлы docx как нам надо - структуру показывает а файлы сами по себе не извлекает. Единственный код который это реально делает это код от The trick.
0
Испарился
 Аватар для HackerVlad
1741 / 637 / 45
Регистрация: 10.09.2021
Сообщений: 2,769
27.02.2025, 20:33
Итак, недавно мне дали очень интересную ссылку на Excel-ZIP класс: https://github.com/cristianbus... ree/master
Этот класс недавно пару лет назад написали какие-то умные люди из Массачусетского университета.
Скачав этот очень хороший примерчик я понял что он работает ещё и в VB6 ни только в VBA-Excel. Итак достоинства и недостатки этого кода:
Достоинства:
- Маленький размер EXE (всего 40Кб, по сравнению со 100 - 120 Кб класса от известного болгарина wqweto)
- Относительно быстрая скорость (особенно в EXE)
- Работает в P-коде

Недостатки:
- Не работает на больших файлах 500Мб уже фатальный вылет
- Не работает в EXE со всеми галочками оптимизации
- Не распаковывает файлы из DOCX нормально

Но зато теперь в мини-программе по чтению картинок из ZIP картинки теперь загружаются со скоростью 15-16 мс всего! При этом довольно маленький размер EXE! Не требует никаких DLL!
Миниатюры
Работа с zip архивами  
Вложения
Тип файла: zip Чтение картинок из ZIP новым кодом класса ExcelUnZip.zip (912.9 Кб, 4 просмотров)
1
1386 / 842 / 91
Регистрация: 08.02.2017
Сообщений: 3,588
Записей в блоге: 1
04.03.2025, 15:04  [ТС]
Уже многое было в этой теме, и я если честно путаюсь где что искать. Но, поскольку, HackerVlad, недавно выяснил кое-что про cabinet.dll, выложу сохраненный у меня пример использования современных функций (работающих, начиная с win8.1) cabinet.dll (компрессия/декомпрессия) там в примере сравнение с NT-компрессией, чтобы освежить память в данном вопросе. Там я еще добавил кое-какие константы.
Кликните здесь для просмотра всего текста
Visual Basic
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
Option Explicit
Enum apiBOOL
    apiFalse
    apiTrue
End Enum
Enum CabCompressAlgorithm
    COMPRESS_ALGORITHM_MSZIP = 2 
    COMPRESS_ALGORITHM_XPRESS = 3
    COMPRESS_ALGORITHM_XPRESS_HUFF = 4
    COMPRESS_ALGORITHM_LZMS = 5
End Enum
'#If VBA7 Then
'    Private Declare PtrSafe Function Compress& Lib "cabinet" (ByVal hCompressor&, pUncompressedData As Any, ByVal sizeUncompressedData&, pCompressedDataBuffer As Any, ByVal sizeCompressedBuffer&, bytesOut&)
'    Private Declare PtrSafe Function Decompress& Lib "cabinet" (ByVal hCompressor&, pCompressedData As Any, ByVal sizeCompressedData&, pUncompressedDataBuffer As Any, ByVal sizeOfUncompressedBuffer&, bytesOut&)
'    Private Declare PtrSafe Function CreateCompressor& Lib "cabinet" (ByVal CompressAlgorithm As CabCompressAlgorithm, ByVal pAllocationRoutines&, hCompressor&)
'    Private Declare PtrSafe Function CreateDecompressor& Lib "cabinet" (ByVal CompressAlgorithm As CabCompressAlgorithm, ByVal pAllocationRoutines&, hDecompressor&)
'    Private Declare PtrSafe Function CloseCompressor& Lib "cabinet" (ByVal hCompressor&)
'    Private Declare PtrSafe Function CloseDecompressor& Lib "cabinet" (ByVal hDecompressor&)
'#Else
    Private Declare Function Compress Lib "cabinet" (ByVal hCompressor As Long, pUncompressedData As Any, ByVal sizeUncompressedData As Long, pCompressedDataBuffer As Any, ByVal sizeCompressedBuffer As Long, bytesOut As Long) As apiBOOL
    Private Declare Function Decompress Lib "cabinet" (ByVal hCompressor As Long, pCompressedData As Any, ByVal sizeCompressedData As Long, pUncompressedDataBuffer As Any, ByVal sizeOfUncompressedBuffer&, bytesOut As Long) As apiBOOL
    Private Declare Function CreateCompressor Lib "cabinet" (ByVal CompressAlgorithm As CabCompressAlgorithm, ByVal pAllocationRoutines As Long, hCompressor As Long) As apiBOOL
    Private Declare Function CreateDecompressor Lib "cabinet" (ByVal CompressAlgorithm As CabCompressAlgorithm, ByVal pAllocationRoutines As Long, hDecompressor As Long) As apiBOOL
    Private Declare Function CloseCompressor Lib "cabinet" (ByVal hCompressor As Long) As apiBOOL
    Private Declare Function CloseDecompressor Lib "cabinet" (ByVal hDecompressor As Long) As apiBOOL
'#End If
'ntifs.h:
'#define COMPRESSION_FORMAT_NONE         (0x0000)
'#define COMPRESSION_FORMAT_DEFAULT      (0x0001)
'#define COMPRESSION_FORMAT_LZNT1        (0x0002)
'#define COMPRESSION_ENGINE_STANDARD     (0x0000)
'#define COMPRESSION_ENGINE_MAXIMUM      (0x0100)
'#define COMPRESSION_ENGINE_HIBER        (0x0200)
Enum NtCompressionFormat
    COMPRESSION_FORMAT_DEFAULT = &H1
    COMPRESSION_FORMAT_LZNT1 = &H2
    COMPRESSION_FORMAT_XPRESS = &H3
    COMPRESSION_FORMAT_XPRESS_HUFF = &H4
    COMPRESSION_ENGINE_STANDARD = &H0
    COMPRESSION_ENGINE_MAXIMUM = &H100
    COMPRESSION_ENGINE_HIBER = &H200
End Enum
Enum NtCompressionStatus
    STATUS_SUCCESS& = 0
    STATUS_BAD_COMPRESSION_BUFFER& = &HC0000242   '-1073741246
    STATUS_UNSUPPORTED_COMPRESSION& = &HC000025F  '-1073741217
    STATUS_INVALID_PARAMETER& = &HC000000D        '-1073741811
    STATUS_BUFFER_ALL_ZEROS = &H117               '279
    STATUS_NOT_SUPPORTED = &HC00000BB             '-1073741637
    STATUS_BUFFER_TOO_SMALL = &HC0000023          '-1073741789
End Enum
Private Declare Function RtlGetCompressionWorkSpaceSize Lib "ntdll" (ByVal CompressionFormatAndEngine As NtCompressionFormat, ByRef CompressBufferWorkSpaceSize As Long, ByRef CompressFragmentWorkSpaceSize As Long) As NtCompressionStatus
Private Declare Function RtlCompressBuffer Lib "ntdll" (ByVal CompressionFormatAndEngine As Integer, ByRef UncompressedBuffer As Any, ByVal UncompressedBufferSize As Long, ByRef CompressedBuffer As Any, ByVal CompressedBufferSize As Long, ByVal UncompressedChunkSize As Long, ByRef FinalCompressedSize As Long, ByRef WorkSpace As Any) As NtCompressionStatus
Private Declare Function RtlDecompressBuffer Lib "ntdll" (ByVal CompressionFormat As Integer, ByRef ptrDestBuffer As Any, ByVal DestBufferSize As Long, ByRef ptrSrceBuffer As Any, ByVal SceBufferSize As Long, ByRef pDestinationSize As Long) As NtCompressionStatus
 
Private Const NullPtr As LongPtr = 0
 
Function Compress_NT(bInp() As Byte, bOut() As Byte, CmpFormat As NtCompressionFormat) As NtCompressionStatus
    On Error GoTo Quit
    Dim WorkSpace() As Byte
    Dim szWorkSpace As Long
    Dim bInpSize As Long
    Dim bOutSize As Long
    
    Compress_NT = RtlGetCompressionWorkSpaceSize(CmpFormat, szWorkSpace, 0)
    If Compress_NT = STATUS_SUCCESS Then
        bInpSize = UBound(bInp) + 1
        ReDim WorkSpace(szWorkSpace - 1)
        ReDim bOut(bInpSize - 1)
        
        Compress_NT = RtlCompressBuffer(CmpFormat, bInp(0), bInpSize, bOut(0), bInpSize, 4096, bOutSize, WorkSpace(0))
        If Compress_NT = STATUS_SUCCESS Then ReDim Preserve bOut(bOutSize - 1)
    End If
Quit:
End Function
Function DeCompress_NT(bInp() As Byte, bOut() As Byte, Optional ByVal bOutSize As Long) As NtCompressionStatus
    On Error GoTo Quit
    Dim bInpSize As Long
    Dim returnedSize As Long
    
    bInpSize = UBound(bInp) + 1
    If bOutSize = 0 Then bOutSize = bInpSize * 2
    ReDim bOut(bOutSize - 1)
    
    Do
        DeCompress_NT = RtlDecompressBuffer(COMPRESSION_FORMAT_LZNT1, bOut(0), bOutSize, bInp(0), bInpSize, returnedSize)
        Select Case DeCompress_NT
        Case STATUS_SUCCESS
            ReDim Preserve bOut(returnedSize - 1)
            Exit Do
        Case STATUS_BAD_COMPRESSION_BUFFER
            bOutSize = bOutSize + bInpSize
            ReDim Preserve bOut(bOutSize - 1)
        Case Else 'STATUS_UNSUPPORTED_COMPRESSION
            Exit Do
        End Select
    Loop
Quit:
End Function
Function CabCompress(bInp() As Byte, Optional ByVal algorithm As CabCompressAlgorithm = COMPRESS_ALGORITHM_LZMS) As Byte()
    Dim h&, Max&, bytesOut&, bOut() As Byte
    
    If CreateCompressor(algorithm, 0, h) Then
        Max = UBound(bInp) + 1: ReDim bOut(Max - 1)
        If Compress(h, bInp(0), Max, bOut(0), Max, bytesOut) Then
            If bytesOut Then ReDim Preserve bOut(bytesOut - 1)
        End If
        CloseCompressor h
    End If
    
    CabCompress = bOut
End Function
Function CabDecompress(bInp() As Byte, Optional ByVal algorithm As CabCompressAlgorithm = COMPRESS_ALGORITHM_LZMS) As Byte()
    Dim h&, bytesOut&, bOut() As Byte
    
    If CreateDecompressor(algorithm, 0, h) Then
        Decompress h, bInp(0), UBound(bInp) + 1, ByVal StrPtr(vbNullString), 0, bytesOut
        If bytesOut Then
            ReDim bOut(bytesOut - 1)
            Decompress h, bInp(0), UBound(bInp) + 1, bOut(0), bytesOut, ByVal StrPtr(vbNullString)
        End If
        CloseDecompressor h
    End If
    
    CabDecompress = bOut
End Function
 
Function CompressString(s$, Optional ByVal algorithm As CabCompressAlgorithm = 5) As String
    Dim h&, Max&, bytesOut&, b$
    If Len(s) Then
        If CreateCompressor(algorithm, 0&, h) Then
            Max = LenB(s): b = Space$(Max)
            If Compress(h, ByVal StrPtr(s), Max, ByVal StrPtr(b), Max, bytesOut) Then
                If bytesOut Then CompressString = Left$(b, bytesOut \ 2)
            End If
            CloseCompressor h
        End If
    End If
End Function
 
Function DecompressString(s$, Optional ByVal algorithm As CabCompressAlgorithm = 5) As String
    Dim h&, bytesOut&, b$
    If Len(s) Then
        If CreateDecompressor(algorithm, 0&, h) Then
            b = Space$(LenB(s) * 50)
            If Decompress(h, ByVal StrPtr(s), LenB(s), ByVal StrPtr(b), LenB(b), bytesOut) Then
                If bytesOut Then DecompressString = Left$(b, bytesOut \ 2)
            End If
            CloseDecompressor h
        End If
    End If
End Function
 
Private Function GetFileBytes(sFlPt As String) As Byte()
    Dim fNum&, fLen&, bBuf() As Byte
    fNum = FreeFile
    Open sFlPt For Binary Access Read As #fNum
    fLen = LOF(fNum)
    If fLen Then
        ReDim bBuf(fLen - 1)
        Get fNum, , bBuf
    End If
    Close fNum
    GetFileBytes = bBuf
End Function
 
Private Sub Example2()
    Dim bBuf() As Byte, bCompNt() As Byte, bCompCab() As Byte
    
'    bBuf = "I do not like them in a box. I do not like them with a fox. I will not eat them in a house. I do not like them with a mouse. I do not like them here or there. I do not like them ANYWHERE!"
    bBuf = GetFileBytes("D:\tmp\Zip\Diletant\Simpler Zipper Demo_\Subfolder\zlibwapi.dll")
    
    Compress_NT bBuf, bCompNt, COMPRESSION_FORMAT_XPRESS_HUFF Or COMPRESSION_ENGINE_MAXIMUM
    bCompCab = CabCompress(bBuf, COMPRESS_ALGORITHM_MSZIP)
    Debug.Print "Размер данных:  "; UBound(bBuf) + 1
    Debug.Print "NT-кмопрессия:  "; UBound(bCompNt) + 1
    Debug.Print "Cab-компрессия: "; UBound(bCompCab) + 1
    Debug.Print
End Sub
2
Испарился
 Аватар для HackerVlad
1741 / 637 / 45
Регистрация: 10.09.2021
Сообщений: 2,769
04.03.2025, 15:59
testuser2, у меня класс есть, который я когда-то скачал с иностранного форума, но твой пример тоже очень хороший

Добавлено через 1 минуту
Цитата Сообщение от testuser2 Посмотреть сообщение
и я если честно путаюсь где что искать.
да надо было разделить эту тему на несколько тем, неудобно конечно когда одна тема огромная

Добавлено через 21 минуту
Цитата Сообщение от testuser2 Посмотреть сообщение
пример использования современных функций (работающих, начиная с win8.1)
функции кстати не такие уж и современные, на самом деле распаковка ZIP доступна в cabinet.dll начиная с Windows 95, просто никто об этом не знает толком. И там сложнее будет всё это реализовать, но возможно тоже распаковывать простые ZIP файлы функцией FDICopy, просто сложно будет разобраться со структурами и как их переделать, но это возможно.
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
inter-admin
Эксперт
29715 / 6470 / 2152
Регистрация: 06.03.2009
Сообщений: 28,500
Блог
04.03.2025, 15:59
Помогаю со студенческими работами здесь

access и zip архив
Привет всем! Подскажите... если есть возможность сохранение файла в zip архив Dim FileHeder As String Dim filePath As String ...

Как распаковать ZIP-файл в 7z?
'При помощи VBA WinRAR распаковывает архив в папку … q = Адрес_сохранения_файла 'путь к каталогу, то есть к папке, в конце пути для...

ребята!завтра надо сдать работу,а без этих работ никак((
алгоритмы линейной структуры 1) СОСТАВИТЬ ПРОГРАММУ ВЫЧИСЛЕНИЯ СРЕДНЕГО ЗНАЧЕНИЯ ТРЕХ ВЕЛИЧИН 2) ПОДСЧИТАТЬ И ВЫВЕСТИ НА ЭКРАН СУММУ И...

Замена файла в zip архиве при совпадении имени
Есть несколько excel файлов. например, 1.xls, 2.xls, 3.xls Есть куча zip архивов. например, A (1.xls), B (1.xls,5.doc,3.doc), C (3.xls),...

Как сделать архив zip?
Как сделать архив zip? Какие нужны библиотеки и где их взять? заранее спасибо.


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
280
Ответ Создать тему
Новые блоги и статьи
SDL3 для Web (WebAssembly): Реализация движения на Box2D v3 - трение и коллизии с повёрнутыми стенами
8Observer8 20.02.2026
Содержание блога Box2D позволяет легко создать главного героя, который не проходит сквозь стены и перемещается с заданным трением о препятствия, которые можно располагать под углом, как верхнее. . .
Конвертировать закладки radiotray-ng в m3u-плейлист
damix 19.02.2026
Это можно сделать скриптом для PowerShell. Использование . \СonvertRadiotrayToM3U. ps1 <path_to_bookmarks. json> Рядом с файлом bookmarks. json появится файл bookmarks. m3u с результатом. # Check if. . .
Семь CDC на одном интерфейсе: 5 U[S]ARTов, 1 CAN и 1 SSI
Eddy_Em 18.02.2026
Постепенно допиливаю свою "многоинтерфейсную плату". Выглядит вот так: https:/ / www. cyberforum. ru/ blog_attachment. php?attachmentid=11617&stc=1&d=1771445347 Основана на STM32F303RBT6. На борту пять. . .
Камера Toupcam IUA500KMA
Eddy_Em 12.02.2026
Т. к. у всяких "хикроботов" слишком уж мелкий пиксель, для подсмотра в ESPriF они вообще плохо годятся: уже 14 величину можно рассмотреть еле-еле лишь на экспозициях под 3 секунды (а то и больше),. . .
И ясному Солнцу
zbw 12.02.2026
И ясному Солнцу, и светлой Луне. В мире покоя нет и люди не могут жить в тишине. А жить им немного лет.
«Знание-Сила»
zbw 12.02.2026
«Знание-Сила» «Время-Деньги» «Деньги -Пуля»
SDL3 для Web (WebAssembly): Подключение Box2D v3, физика и отрисовка коллайдеров
8Observer8 12.02.2026
Содержание блога Box2D - это библиотека для 2D физики для анимаций и игр. С её помощью можно определять были ли коллизии между конкретными объектами и вызывать обработчики событий столкновения. . . .
SDL3 для Web (WebAssembly): Загрузка PNG с прозрачным фоном с помощью SDL_LoadPNG (без SDL3_image)
8Observer8 11.02.2026
Содержание блога Библиотека SDL3 содержит встроенные инструменты для базовой работы с изображениями - без использования библиотеки SDL3_image. Пошагово создадим проект для загрузки изображения. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru