Запрос справки пакетного сценария: Как найти разрыв строки?
У меня есть несколько файлов RAR, содержащих JPG, и я пытаюсь получить имя первого файла каждого файла RAR.
Например, если я бегу 7z l -r abc.rar
Я хотел бы получить первый файл 01.jpg
path = xyz.rar
Type = zip
Physical Size = 15430338
Date Time Attr Size Compressed Name
------------------- ----- ------------ ------------ ------------------------
2003-03-06 13:32:44 ....A 330433 325405 01.jpg
2003-03-06 13:34:08 ....A 301098 291857 02.jpg
2003-03-06 13:34:14 ....A 257770 244619 03.jpg
2003-03-06 13:34:22 ....A 301220 292019 04.jpg
2003-03-06 13:34:30 ....A 326989 316380 05.jpg
Пока что с помощью следующего пакетного сценария я могу удалить метаданные команды 7z и получить список файлов в contents.txt
файл.
set PATH=%PATH%;"C:\Program Files\7-Zip"
for %%f in ("*.*") do (
echo "%%f" >> contents.txt
echo.
7z l -r "%%f" | FIND /V "ing " | FIND /V "Igor Pavlov" | FIND /V "--" | FIND /V "Path" | FIND /V "Type" | FIND /V "Solid" | FIND /V "Blocks" | FIND /V "Multivolume" | FIND /V "Volumes" | FIND /V "Date" | FIND /V "---" | FIND /V "Physical Size" | FINDSTR /R /E ".jpg" >> contents.txt
echo.
)
PAUSE
Пример вывода:
"abc.rar"
2003-03-26 01:18:50 ....A 331711 330648 01.jpg
2003-03-26 01:18:54 ....A 271173 270942 02.jpg
"xyz.rar"
2003-07-08 22:40:56 ....A 445799 430058 p00.jpg
2003-07-08 22:40:40 ....A 181324 142554 p01.jpg
2003-07-08 22:40:42 ....A 384901 370140 p02.jpg
"efg.rar"
2003-07-08 22:42:54 ....A 156436 115275 xy01abc.jpg
2003-07-08 22:42:58 ....A 456633 448240 xy02abc.jpg
2003-07-08 22:42:58 ....A 355114 339026 xy03abc.jpg
2003-07-08 22:42:58 ....A 355114 339026 xy04abc.jpg
Я думаю, что если я настрою свой сценарий, чтобы найти первый разрыв строки, за которым следует ".jpg" в выводе 7z, я могу получить имя первого файла в следующем формате:
"abc.rar"
2003-03-26 01:18:50 ....A 331711 330648 01.jpg
"xyz.rar"
2003-07-08 22:40:56 ....A 445799 430058 p00.jpg
"efg.rar"
2003-07-08 22:42:54 ....A 156436 115275 xy01abc.jpg
Но я не знаю, как искать разрыв строки в команде FINDSTR. Я пытался найти для ".jpg\n" в FINDSTR:
7z l -r "%%f" | FIND /V "ing " | FIND /V "Igor Pavlov" | FIND /V "--" | FIND /V "Path" | FIND /V "Type" | FIND /V "Solid" | FIND /V "Blocks" | FIND /V "Multivolume" | FIND /V "Volumes" | FIND /V "Date" | FIND /V "---" | FIND /V "Physical Size" | FINDSTR /R /E ".jpg\n" >> contents.txt
Но это не сработало.
Может кто-нибудь мне помочь?
Мой желаемый вывод - убрать всю информацию о дате и размере файла из вывода имени файла и добавить ее после имени файла RAR, например:
"abc.rar" 01.jpg
"xyz.rar" p00.jpg
"efg.rar" xy01abc.jpg
Не существует фиксированного шаблона первого файла jpg. Некоторые начинаются с 00, некоторые с 01, некоторые с текстом и номером (пример x00y.jpg). Я пробовал различные методы для поиска имен файлов, которые начинаются с 00 или 01 с текстом и без текста (например, в моей команде я использовал FINDSTR /R /E "[a-z][0-1]*.jpg"
искать имена файлов с текстом и номером, но есть некоторые файлы RAR без текста в именах файлов).
1 ответ
Выполнение в окне командной строки findstr /?
выводит справку для этого списка команд и объяснения /E
искать указанную строку в конце строк. Используя эту опцию намного проще, чем все остальное, найти строку в конце строки.
Одним из возможных пакетных решений для вашей задачи может быть:
@echo off
del contents.txt 2>nul
for %%A in ("*.*") do call :GetFirstFileName "%%~A"
exit /B
:GetFirstFileName
"%ProgramFiles%\7-Zip\7z.exe" l "%~1" | %SystemRoot%\System32\findstr.exe /E /I "/C:.jpg">"%TEMP%\FilesList.tmp"
for /F "usebackq eol=` tokens=5* delims= " %%B in ("%TEMP%\FilesList.tmp") do (
echo "%~1" %%C>>contents.txt
del "%TEMP%\FilesList.tmp"
exit /B
)
del "%TEMP%\FilesList.tmp"
exit /B
Этот пакетный файл вызывает 7-Zip для каждого файла в текущем каталоге, чтобы вывести содержимое архива, отфильтрованного с помощью findstr, чтобы попасть во временный файл списка только строк, заканчивающихся на .jpg
в любом случае.
Файл временного списка обрабатывается циклом FOR для получения только имени файла из первой строки, записанного вместе с именем файла архива в текстовый файл содержимого.
Другим решением было бы использование FOR напрямую для обработки вывода списка 7-Zip.
@echo off
setlocal EnableDelayedExpansion
del contents.txt 2>nul
for %%A in ("*.*") do call :GetFirstFileName "%%~A"
endlocal
exit /B
:GetFirstFileName
set "NextLine=0"
"%ProgramFiles%\7-Zip\7z.exe" l "%~1">"%TEMP%\FilesList.tmp"
for /F "usebackq eol=` tokens=1,5* delims= " %%B in ("%TEMP%\FilesList.tmp") do (
if "%%B" == "-------------------" (
set "NextLine=1"
) else if "!NextLine!" == "1" (
echo "%~1" %%D>>contents.txt
del "%TEMP%\FilesList.tmp"
exit /B
)
)
del "%TEMP%\FilesList.tmp"
exit /B
Этот пакетный файл вызывает 7-Zip для каждого файла в текущем каталоге, чтобы вывести содержимое архива, перенаправленного во временный файл списка.
Файл временного списка обрабатывается циклом FOR, чтобы получить только имя файла из первой строки после строки, содержащей -------------------
записывается вместе с именем файла архива в текстовый файл содержимого.
Число строк над списком не является постоянным, что является причиной, почему опция FOR skip=
не может быть использован здесь.
Не имеет значения, какое расширение имеет первый файл в архивном файле для этого пакетного решения.
Еще одним решением является использование бесплатного UnRAR для получения первого имени каждого файла архива RAR.
@echo off
del contents.txt 2>nul
for %%A in ("*.rar") do call :GetFirstFileName "%%~A"
exit /B
:GetFirstFileName
"%ProgramFiles%\WinRAR\UnRAR.exe" lb "%~1">"%TEMP%\FilesList.tmp"
for /F "usebackq eol=: delims=" %%B in ("%TEMP%\FilesList.tmp") do (
echo "%~1" %%B>>contents.txt
del "%TEMP%\FilesList.tmp"
exit /B
)
del "%TEMP%\FilesList.tmp"
exit /B
Преимущество состоит в том, что UnRAR поддерживает несколько опций для формата списка, включая пустой формат, используемый при использовании команды l
с b
прилагается. Это значительно упрощает получение первого имени файла.
Чтобы понять используемые команды и то, как они работают, откройте окно командной строки, выполните там следующие команды и полностью прочитайте все страницы справки, отображаемые для каждой команды.
call /?
del /?
echo /?
endlocal /?
exit /?
findstr /?
for /?
if /?
set /?
setlocal /?
"%ProgramFiles%\7-Zip\7z.exe" -?
"%ProgramFiles%\WinRAR\UnRAR.exe" /?