Компьютерный форум OSzone.net  

Компьютерный форум OSzone.net (http://forum.oszone.net/index.php)
-   Скриптовые языки администрирования Windows (http://forum.oszone.net/forumdisplay.php?f=102)
-   -   [решено] Нужна помощь в написании скрипта работы с файлами. (http://forum.oszone.net/showthread.php?t=341884)

nik123456654321 20-08-2019 09:28 2884813

Нужна помощь в написании скрипта работы с файлами.
 
Доброго времени суток господа форумчане! Требуется помощь в написании скрипта. Имеем следующее : программа 3D съемки дает на выходе 32 .jpg файла в папку с рандомным названием (эта папка создается всегда в одном месте скажем в D:/Photo) . Задача состоит в том , что бы переименовать эти .jpg фалы по очереди , начиная с 0 до 31(тоесть должно получиться 0.jpg.....31.jpg) и запаковать их в архив с помощью 7zip под названием photo.zip . Заранее спасибо за помощь.

megaloman 20-08-2019 09:47 2884815

nik123456654321, в D:/Photo папка с рандомным названием единственная? Или надо обработать все папки? Что делать с файлами после упаковки? В каком порядке присваиваются номера (по дате/времени изменения?) Не лучше ли именовать файлы 00.jpg 01.jpg ...09.jpg 10.jpg 11.jpg... 31.jpg Куда девать файл photo.zip?

nik123456654321 20-08-2019 10:52 2884818

megaloman, Здравствуйте,спасибо , что откликнулись ! Да папка будет единственная . После упаковки файлы будут загружаться на ftp сайта (но это уже другая история :)). Номера присваиваются по дате создания я думаю (т.е. делаются последовательно 32 фото и их так же по порядку создания надо переименовывать начиная с 0 и до 31 ). С названием файлов ,к сожалению, они должны именоваться именно с 0.jpg и т.д. (это требования скрипта , который потом из них разворачивает 3D модель на сайте ). Photo.zip можно положить в туже корневую папку рядом (вместо ) папки с рандомным названием.

megaloman 20-08-2019 13:58 2884828

nik123456654321,
Код:

@Echo Off
cls
        Set "BoxIn=D:\Photo"
        Set "Mask=*.jpg"
        Set "FileOut=D:\Photo\Photo.zip"

        Set "Arc="C:\Program Files\7-Zip\7z.exe" a -mx5 -sdel --"

        Set /A NContr=32

        If Not Exist "%BoxIn%\" (Echo !!! Folder "%BoxIn%\" not exists. Script Exit. &Pause &Exit /B 2)
        If Exist "%FileOut%" (Echo !!! File "%FileOut%" already exists. Script Exit. &Pause &Exit /B 2)

        Set /A N=0
        FOR /F "usebackq delims=" %%d IN (`2^>nul Dir "%BoxIn%\" /B /A:D /O:-D`) DO (
                FOR /F "usebackq delims=" %%f IN (`2^>nul Dir "%BoxIn%\%%d\%Mask%" /B /A:-D /O:D`) DO (
                        Call Ren "%BoxIn%\%%d\%%f" %%N%%%%~xf
                        Set /A N+=1
                )
                Call :Pack "%BoxIn%\%%d\%Mask%" "%FileOut%" %%N%% %NContr% &&Exit /B
        )
        If "%N%"=="0" (Echo !!! In Subfolders of Folder "%BoxIn%\" files %Mask% not found. Script Exit. &Pause &Exit /B 2)
Exit /B

:Pack
        If "%3"=="0" Exit /B 1
        %Arc% %2 %1 &&Rd /S /Q "%~dp1"

        If Not "%3"=="%4" Echo. &Echo Found In %1 files N=%3^<^>%4 files &Echo. &Pause
Exit /B 0

Если хочется, чтобы процесс исполнялся многократно быстрее, замените -mx5 на -mx0
Конечно, размер архивного файла будет больше, но, для jpg не намного (менее процента).

nik123456654321 20-08-2019 16:06 2884834

megaloman, Огромное спасибо ! Завтра буду тестировать.

Iska 20-08-2019 17:10 2884842

Добавлю сюда же код на PowerShell:
Скрытый текст
Код:

$sRootFolder  = 'C:\Мои проекты\0273\Photo'
$sArchiveFile = "$sRootFolder\Photo.zip"

if([System.IO.Directory]::Exists($sRootFolder)) {
    $oDirectoryInfo = Get-ChildItem -Path $sRootFolder -Directory
   
    if($oDirectoryInfo -is [System.IO.DirectoryInfo]) {
        $aFileInfo = @(Get-ChildItem -Path "$($oDirectoryInfo.FullName)\*" -Include '*.jpg' -File)

        if($aFileInfo.Count -eq 32) {
            try {
                Compress-Archive -Path $aFileInfo -DestinationPath $sArchiveFile -CompressionLevel NoCompression -Force -ErrorAction SilentlyContinue
                Write-Host "Archive file [$sArchiveFile] created." -ForegroundColor Green
            } catch {
                Write-Host "Can't create archive file [$sArchiveFile]." -ForegroundColor Red
            }
        } else {
            Write-Host "Need exactly 32 jpg files in subfolder [$($oDirectoryInfo.FullName)]." -ForegroundColor Red
        }
    } else {
        Write-Host "Need at least one (and no more) subfolder in root folder [$sRootFolder]." -ForegroundColor Red
    }
} else {
    Write-Host "Can't find root folder [$sRootFolder]." -ForegroundColor Red
}


nik123456654321 21-08-2019 08:42 2884891

Iska, Спасибо !

nik123456654321 21-08-2019 10:24 2884906

Еще раз всем спасибо! Работает так , как надо.

Iska 21-08-2019 21:48 2885020

К сожалению, на радостях я тупо забыл про:
Цитата:

Цитата nik123456654321
переименовать эти .jpg фалы по очереди , начиная с 0 до 31 »

Исправленная версия:
Скрытый текст
Код:

$sRootFolder  = 'C:\Мои проекты\0273\Photo'
$sArchiveFile = "$sRootFolder\Photo.zip"
$sExtension  = 'jpg'

if([System.IO.Directory]::Exists($sRootFolder)) {
    $oDirectoryInfo = Get-ChildItem -Path $sRootFolder -Directory
   
    if($oDirectoryInfo -is [System.IO.DirectoryInfo]) {
        $aFileInfo = @(Get-ChildItem -Path "$($oDirectoryInfo.FullName)\*" -Include "*.$sExtension" -File)

        if($aFileInfo.Count -eq 32) {
            $aFileInfo | ForEach-Object -Process {
                do {
                    $sNewFileName = "$($oDirectoryInfo.FullName)\$([System.IO.Path]::GetRandomFileName())$($_.Extension)"
                } until (-not [System.IO.File]::Exists($sNewFileName))

                [System.IO.File]::Move($_.FullName, $sNewFileName)
            }

            $aFileInfo = @(Get-ChildItem -Path "$($oDirectoryInfo.FullName)\*" -Include "*.$sExtension" -File) | Sort-Object -Property 'CreationTime'
            $aFileInfo | ForEach-Object -Begin {
                $iCount = 0
            } -Process {
                [System.IO.File]::Move($_.FullName, "$($oDirectoryInfo.FullName)\$(($iCount++).ToString())$($_.Extension)")
            }

            $aFileInfo = @(Get-ChildItem -Path "$($oDirectoryInfo.FullName)\*" -Include "*.$sExtension" -File)
            try {
                Compress-Archive -Path $aFileInfo -DestinationPath $sArchiveFile -CompressionLevel NoCompression -Force -ErrorAction SilentlyContinue
                Write-Host "Archive file [$sArchiveFile] created." -ForegroundColor Green
            } catch {
                Write-Host "Can't create archive file [$sArchiveFile]." -ForegroundColor Red
            }
        } else {
            Write-Host "Need exactly 32 $sExtension files in subfolder [$($oDirectoryInfo.FullName)]." -ForegroundColor Red
        }
    } else {
        Write-Host "Need at least one (and no more) subfolder in root folder [$sRootFolder]." -ForegroundColor Red
    }
} else {
    Write-Host "Can't find root folder [$sRootFolder]." -ForegroundColor Red
}


P.S. Надо же было столько возиться, чтобы сохранить оригинальные даты файлов, а потом открыть новосозданный архив в 7-Zip и внезапно обнаружить, что командлет Compress-Archive не сохраняет в архиве даты создания файлов :shocked:.

YuS_2 21-08-2019 21:57 2885022

Цитата:

Цитата Iska
не сохраняет в архиве даты создания файлов »

всё равно, при любом копировании, эти даты изменяются... да и если мне не изменяет мой склероз, они не сохраняются при извлечении из любого архива, то бишь это не Compress-Archive так работает, а файловая система...

Iska 21-08-2019 22:38 2885024

Цитата:

Цитата YuS_2
всё равно, при любом копировании, эти даты изменяются... »

Ага. Я сначала для простоты создавал каталог в %Temp% и туда копировал по одному файлу с одновременным переименованием, потом обнаружил, что дата создания при этом меняется, стал делать по месту — аж в три прохода.

Цитата:

Цитата YuS_2
да и если мне не изменяет мой склероз, они не сохраняются при извлечении из любого архива, то бишь это не Compress-Archive так работает, а файловая система... »

По умолчанию — так. Но 7-Zip умеет сохранять атрибуты дат файлов в архив (для 7z отчасти по запросу, для Zip — безусловно) и восстанавливать (безусловно), а WinRAR — как сохранять, так и восстанавливать (там более сложная логика умолчаний, приведена в справке).
7-Zip
Цитата:

-m (Set compression Method) switch

Zip

tc=[off | on] on Stores NTFS timestamps for files: Modification time, Creation time, Last access time.

7z

tm=[off | on] on Stores last Modified timestamps for files.
tc=[off | on] off Stores Creation timestamps for files.
ta=[off | on] off Stores last Access timestamps for files.

WinRAR
Цитата:

-ts[m,c,a][+,-,1] Сохранять или восстанавливать время файлов (изменения, создания, доступа)

megaloman 21-08-2019 23:09 2885029

Iska, Дата последнего изменения сохраняются после упаковки-восстановления 7Z, WinRar по умолчанию
При копировании меняется дата создания, дата последнего изменения сохраняется.
Отсюда парадокс: дата изменения может быть меньше даты создания.
Дата создания - очень ненадёжная дата.

Iska 22-08-2019 02:26 2885039

megaloman, всё так.

YuS_2 22-08-2019 09:26 2885058

Цитата:

Цитата Iska
Но 7-Zip умеет сохранять атрибуты дат файлов в архив (для 7z отчасти по запросу, для Zip — безусловно) и восстанавливать (безусловно), а WinRAR — как сохранять, так и восстанавливать (там более сложная логика умолчаний, приведена в справке). »

Да, это так. Архиваторы умеют сохранять/восстанавливать и дату создания, и дату доступа, при включении соответствующих опций, т.е. они сохраняют их в виде служебной информации в самих архивах и восстанавливают тоже при включении соответствующей опции и из этой именно, служебной информации... это можно проверить, сохранив одинаковый файл в два архива: один с доп.информацией по датам, другой без этой информации, при прочих равных условиях - размер у таких архивов, естественно, будет отличаться.
Comress-Archive этому не обучен (уже хорошо, что вообще появился такой командлет :) ), но при желании, можно состряпать функцию сохранения таких дат в доп.файл и при необходимости, аналогично восстанавливать эти даты...
Но, честно говоря, не вижу в этих действиях большого смысла, по причинам озвученным выше, т.е. эти даты абсолютно ненадежны.

nik123456654321 22-08-2019 10:29 2885064

Добрый день ! Обнаружился глюк в работе программы 3d съемки(с какого то момента она начала делать фото у которых не совпадает дата создания и порядковый номер фото), к счастью она присваивает имена файлов по порядку. Можно переделать скрипт , что бы он основывался не на дате создания , а переименовывал файлы с именами вида : 001_001.jpg,002_001.jpg,003_001.jpg ... 032_001.jpg в 0.jpg...31.jpg. Заранее спасибо !

megaloman 22-08-2019 11:08 2885074

Код:

@Echo Off
        Set "FileIn=Z:\Box_In\0??_001.jpg"

        FOR %%f IN ("%FileIn%") DO (
                Set "Name=%%~nf"
                Call Set /A N=1%%Name:~0,3%%-1001
                Call Ren "%%f" "%%N%%%%~xf"
        )
Exit /B


Iska 22-08-2019 11:21 2885077

Цитата:

Цитата YuS_2
(уже хорошо, что вообще появился такой командлет »

Ну, да, не прошло и десяти лет :lol:. Или прошло?

Цитата:

Цитата YuS_2
Но, честно говоря, не вижу в этих действиях большого смысла, по причинам озвученным выше, т.е. эти даты абсолютно ненадежны. »

Угу. Exif наше всё (или иной аналог).

Цитата:

Цитата nik123456654321
Обнаружился глюк в работе программы 3d съемки(с какого то момента она начала делать фото у которых не совпадает дата создания и порядковый номер фото), к счастью она присваивает имена файлов по порядку. Можно переделать скрипт , что бы он основывался не на дате создания , а переименовывал файлы с именами вида : 001_001.jpg,002_001.jpg,003_001.jpg ... 032_001.jpg в 0.jpg...31.jpg. »

[Iska бьётся головой о стену]:lol:.

megaloman 22-08-2019 11:27 2885080

Развлекаюсь:
Код:

@Echo Off
        Set "BoxIn=Z:\Box_In"

        FOR /L %%i IN (1001,1,1032) DO (
                Set /A N=%%i
                Set /A M=%%i-1001
                Call Ren "%BoxIn%\%%N:~1,3%%_001.jpg" "%%M%%.jpg"||Call Echo "%BoxIn%\%%N:~1,3%%_001.jpg"
        )
Exit /B

Цитата:

Цитата nik123456654321
переименовывал файлы с именами вида : 001_001.jpg,002_001.jpg,003_001.jpg ... 032_001.jpg в 0.jpg...31.jpg »

Имхо, затем последует
Цитата:

Цитата nik123456654321
программа 3D съемки дает на выходе 32 .jpg файла в папку с рандомным название »

и надо будет придумать, как это сделать.
Как бы до мерзости упростилась жизнь и сократились бы возможности поразвлечься, если бы сразу нам четко рассказывали задачу :)
Цитата:

Цитата Iska
[Iska бьётся головой о стену]. »

Цитата:

И тогда главврач Маргулис тиливизер запретил
:biggrin:

nik123456654321 22-08-2019 11:54 2885087

megaloman, Да , к сожалению это именно так :( Простите меня грешного я первый раз прошу помощи на форуме (на моей памяти). Задача : программа 3D съемки дает на выходе 32 .jpg файла в D:\Pfoto\папка с рандомным названием , файлы имеют название вида 001_001.jpg,002_001.jpg,003_001.jpg ... 032_001.jpg , требуется переименовать файлы по порядку 0.jpg , 1.jpg....31.jpg (т.е. 001_001.jpg в 0.jpg , 002_001.jpg в 1.jpg....032_001.jpg в 31.jpg) и сжать их в архив (с 0 сжатием т.е. -mx0)под названием photo.zip ,который должен размещаться в D:\Photo. Папку с рандомным названием после манипуляций удалить. Надеюсь я исправился :) На будущее учту свои промахи . Спасибо !

YuS_2 22-08-2019 12:41 2885091

Цитата:

Цитата Iska
Или прошло? »

Даже больше...
Цитата:

Впервые публично язык был продемонстрирован на Профессиональной конференции разработчиков (англ. Professional Developers Conference, PDC) в сентябре 2003 года под кодовым названием Monad.
:yes:
Цитата:

Цитата Iska
Exif наше всё (или иной аналог). »

С EXIF тоже не всё так радужно, остались ещё устройства, которые и не думают писать эту инфу, а именно дату... да и пользователи не всегда настраивают её так, чтобы она не показывала начало прошлого века, например. :)

megaloman 22-08-2019 12:46 2885092

Код:

@Echo Off
cls
        Set "BoxIn=D:\Photo"
        Set "FileOut=D:\Photo\Photo.zip"

        Set "Arc="C:\Program Files\7-Zip\7z.exe" a -mx0 -sdel --"

        If Not Exist "%BoxIn%\" (Echo !!! Folder "%BoxIn%\" not exists. Script Exit. &Pause &Exit /B 2)
        If Exist "%FileOut%" (Echo !!! File "%FileOut%" already exists. Script Exit. &Pause &Exit /B 2)

        FOR /F "usebackq delims=" %%d IN (`2^>nul Dir "%BoxIn%\" /B /A:D /O:-D`) DO (
                If Exist "%BoxIn%\%%d\0??_001.jpg" (
                        2>nul Md "%BoxIn%\%%d\%~n0.tmp"

                        FOR /L %%i IN (1001,1,1032) DO (
                                Set /A N=%%i
                                Set /A M=%%i-1001
                                >nul Call Move /Y "%BoxIn%\%%d\%%N:~1,3%%_001.jpg" "%BoxIn%\%%d\%~n0.tmp\%%M%%.jpg"||Call Echo "%BoxIn%\%%N:~1,3%%_001.jpg"
                        )
                        If Exist "%BoxIn%\%%d\%~n0.tmp\*.jpg" %Arc% "%FileOut%" "%BoxIn%\%%d\%~n0.tmp\*.*" &&(Rd /S /Q "%BoxIn%\%%d" &Exit /B)
                )
        )
        Echo !!! In Subfolders of Folder "%BoxIn%\" files 0??_001.jpg not found. Script Exit. &Pause &Exit /B 2)
Exit /B


Iska 22-08-2019 12:50 2885094

Тогда примерно так:
Скрытый текст
Код:

$sRootFolder  = 'C:\Мои проекты\0273\Photo'
$sArchiveFile = "$sRootFolder\Photo.zip"
$sExtension  = 'jpg'

if([System.IO.Directory]::Exists($sRootFolder)) {
    $oDirectoryInfo = Get-ChildItem -Path $sRootFolder -Directory
   
    if($oDirectoryInfo -is [System.IO.DirectoryInfo]) {
        $aFileInfo = @(Get-ChildItem -Path "$($oDirectoryInfo.FullName)\*" -Include "*.$sExtension" -File) | Sort-Object -Property 'Name'

        if($aFileInfo.Count -eq 32) {
            $aFileInfo | ForEach-Object -Begin {
                $iCount = 0
            } -Process {
                [System.IO.File]::Move($_.FullName, "$($oDirectoryInfo.FullName)\$(($iCount++).ToString())$($_.Extension)")
            }

            $aFileInfo = @(Get-ChildItem -Path "$($oDirectoryInfo.FullName)\*" -Include "*.$sExtension" -File) | Sort-Object -Property 'Name'
            try {
                Compress-Archive -Path $aFileInfo -DestinationPath $sArchiveFile -CompressionLevel NoCompression -Force -ErrorAction SilentlyContinue
                Write-Host "Archive file [$sArchiveFile] created." -ForegroundColor Green
                $oDirectoryInfo.Delete($true)
                Write-Host "Folder [$($oDirectoryInfo.FullName)] deleted." -ForegroundColor Green
            } catch {
                Write-Host "Can't create archive file [$sArchiveFile]." -ForegroundColor Red
            }
        } else {
            Write-Host "Need exactly 32 $sExtension files in subfolder [$($oDirectoryInfo.FullName)]." -ForegroundColor Red
        }
    } else {
        Write-Host "Need at least one (and no more) subfolder in root folder [$sRootFolder]." -ForegroundColor Red
    }
} else {
    Write-Host "Can't find root folder [$sRootFolder]." -ForegroundColor Red
}



Цитата:

Цитата YuS_2
С EXIF тоже не всё так радужно, остались ещё устройства, которые и не думают писать эту инфу, а именно дату... да и пользователи не всегда настраивают её так, чтобы она не показывала начало прошлого века, например. »

Это да :).

nik123456654321 22-08-2019 13:11 2885096

megaloman, Огромное Вам спасибо за помощь и терпение ! Все работает , надеюсь больше никаких неполадок со стороны программы 3d съемки не будет .

DJ Mogarych 22-08-2019 15:20 2885111

Код:

$folder = gci "D:\Photo"
$zip = $folder.BaseName + '.zip'
$count = 0

cd $folder.FullName

gci |sort |% {
Rename-Item $_.FullName -NewName "$count.jpg"
$count++
}

gci |Compress-Archive -DestinationPath ..\$zip
cd ..
rm $folder.FullName -Recurse -Force -Confirm:$false



Время: 18:03.

Время: 18:03.
© OSzone.net 2001-