Имя пользователя:
Пароль:  
Помощь | Регистрация | Забыли пароль?  | Правила  

Компьютерный форум OSzone.net » Программирование, базы данных и автоматизация действий » Скриптовые языки администрирования Windows » CMD/BAT - Перенос каталогов и файлов

Ответить
Настройки темы
CMD/BAT - Перенос каталогов и файлов

Новый участник


Сообщения: 4
Благодарности: 0

Профиль | Отправить PM | Цитировать


Добрый день.

Друзья, необходимо выборочно перенести каталоги (и подкаталоги) и файлы в резервную папку.
Список выбранных каталогов сохранён в файле dir.txt, например:
Docs\!Каталог 1
Docs\Каталог 2
Docs\Каталог 3

Для выборочного переноса выполняется следующий код:
Код: Выделить весь код
@echo off
cls
setlocal enabledelayedexpansion
set curdisk=%~d0
 
for /f "usebackq delims=" %%A in ("dir.txt") do (
    Set "folder_from="%curdisk%\%%A""
    set "folder_where="%curdisk%\%date:~6,4%-%date:~3,2%-%date:~0,2% reserv\%%A""
 
    if not exist !folder_where! md !folder_where!
    
    move /Y !folder_from!\*.* !folder_where!
    FOR /F "delims=" %%I IN ('DIR /B /AD !folder_from!') DO (
        move /Y !folder_from!\"%%I" %1 !folder_where!
    )
if exist !folder_from! rd !folder_from! | echo !folder_from!
)
Но если в названии выбранного каталога или в названии его подкаталогов имеется "!" (восклицательный знак), код не работает. Из названия каталогов/подкаталогов исчезает "!".

Если в файле dir.txt знак ! экранировать ^, код работает только с этим каталогом.
Docs\^!Каталог 1

Структура этого каталога может быть такой:
Docs\!Каталог 1
Docs\!Каталог 1\Папка 1!
Docs\!Каталог 1\!Папка 2
Docs\!Каталог 1\Папка !3
Docs\!Каталог 1\Папка 4
Т.е. ! знак может оказаться в любом месте в названии подкаталога и/или файлов.
Каким образом экранировать ! знак в подкаталогах и файлах этой папки? Может у кого есть другое решение по переносу заданных списком каталогов со всеми файлами?

Отправлено: 19:48, 19-12-2018

 

Ветеран


Сообщения: 27449
Благодарности: 8086

Профиль | Отправить PM | Цитировать


Цитата RealDT:
Может у кого есть другое решение по переносу заданных списком каталогов со всеми файлами? »
Есть несколько вариантов. Например, не использовать отложенное раскрытие переменных окружения. Перейти на WSH/PoSH.

Зачем Вы используете здесь:
Цитата:
Код: Выделить весь код
if exist !folder_from! rd !folder_from! | echo !folder_from!
конвеер?!
Это сообщение посчитали полезным следующие участники:

Отправлено: 21:45, 19-12-2018 | #2



Для отключения данного рекламного блока вам необходимо зарегистрироваться или войти с учетной записью социальной сети.

Если же вы забыли свой пароль на форуме, то воспользуйтесь данной ссылкой для восстановления пароля.


Ветеран


Contributor


Сообщения: 2708
Благодарности: 1684

Профиль | Отправить PM | Цитировать


RealDT,
Цитата Iska:
не использовать отложенное раскрытие переменных окружения »
Попытался переделать Ваш код, не знаю, что получилось (корежить чужой код - нудное неблагодарное занятие), но васклицательного знака мой код не боится.
Код: Выделить весь код
@Echo Off
cls
	Set "curdisk=%~d0"
	For /f "usebackq delims=" %%A in ("dir.txt") Do (
		RoboCopy "%curdisk%\%%A" "%curdisk%\%date:~6,4%-%date:~3,2%-%date:~0,2% reserv\%%~nxA" "*.*" /S /IS /Move
	)
Pause
До меня совершенно не доходит строка:
Цитата RealDT:
move /Y !folder_from!\"%%I" %1 !folder_where! »
Если моё извращение Вашего кода Вас не устраивает, объясните подробнее, что Вам надо.

-------
Даже самая сложная проблема обязательно имеет простое, лёгкое для понимания, неправильное решение. Каждое решение плодит новые проблемы.


Последний раз редактировалось megaloman, 19-12-2018 в 23:26.


Отправлено: 22:51, 19-12-2018 | #3


Новый участник


Сообщения: 4
Благодарности: 0

Профиль | Отправить PM | Цитировать


Спасибо за отклики.
По порядку:

Цитата Iska:
Перейти на WSH/PoSH »
мне такое пока не ведомо, посмотрю. если есть ссылки, просьба черкануть...

это
Код: Выделить весь код
if exist !folder_from! rd !folder_from! | echo !folder_from!
нужно чтобы удалить выборочную папку (которая указана в dir.txt) c диска после переноса.

эта команда
Код: Выделить весь код
move /Y !folder_from!\"%%I" %1 !folder_where!
переносит и каталоги и файлы. %1 - лишнее, можно не указывать

Цитата:
Если моё извращение Вашего кода Вас не устраивает, объясните подробнее, что Вам надо.
Предложенный Вами код работает. Но, если move переносит файлы, то robocopy их копирует. Команда move (а не copy & rd или robocopy) на физическом уровне работает в разы быстрее, поскольку работает только в секторах HDD, где размещены ссылки на содержание файлов, а не данные этих файлов. Другими словами - copy/robocopy резервирует и создаёт на диске новый блок данных, а move - только меняет ссылки на расположение этих данных. Скорость работы move и copy/robocopy хорошо видна на больших файлах и незаметна если файлов много, но они небольшого размера.

Вот код, который переносит (не копирует) один заданный каталог и обрабатывает также каталоги/файлы с восклицательными знаками:
Код: Выделить весь код
set curdisk=%~d0
Set dir1=Docs\!КОНТАКТЫ
Set folder_from=%curdisk%\%dir1%
Set folder_where=%curdisk%\%date:~6,4%-%date:~3,2%-%date:~0,2% reserv\%dir1%
if not exist "%folder_where%" md "%folder_where%"
if exist "%folder_from%\*.*" move /Y "%folder_from%\*.*" "%folder_where%"
FOR /F "delims=" %%I IN ('DIR /B /AD "%folder_from%"') DO (move /Y "%folder_from%\%%I" %1 "%folder_where%")
if exist %folder_from% rd %folder_from%
Пока не разобрался, как в переменную dir1 в цикле вносить новое значение из файла dir.txt со списком выбранных каталогов.

Цитата:
объясните подробнее, что Вам надо.
Изначально решалось это:
Перенести избранные каталоги с их содержанием (подкаталоги и файлы) в резервную папку на текущем диске. Название диска не известно.

Отправлено: 12:36, 21-12-2018 | #4


Ветеран


Contributor


Сообщения: 2708
Благодарности: 1684

Профиль | Отправить PM | Цитировать


RealDT,
Цитата:
Но, если move переносит файлы, то robocopy их копирует.
Как говорил мой начальник, не надо ля-ля. Robocopy c ключом /mov переносит файлы с путями, а /move и директори, но при этом они будут удалены из источника, если только пустые. Я проверял, работает.
Проделайте robocopy /? >c:\robocopy.txt и читайте описание команды в файле c:\robocopy.txt
У меня ощущение, что Вы не проанализировали результат выполнения моего кода. Либо не точно его повторили, без всех ключей. Он полностью решает поставленную задачу, в том числе и чтение папок из списка в файле

-------
Даже самая сложная проблема обязательно имеет простое, лёгкое для понимания, неправильное решение. Каждое решение плодит новые проблемы.


Последний раз редактировалось megaloman, 21-12-2018 в 13:28.


Отправлено: 13:18, 21-12-2018 | #5


Новый участник


Сообщения: 4
Благодарности: 0

Профиль | Отправить PM | Цитировать


Код проверял в двух вариантах:
- на небольших файлах, которых много (код отлично справился за неск секунд) и
- на файлах > 1.5 ГБ - robocopy их начинает копировать, на экране светится прогресс копирования, после некоторого ожидания на середине одного из файлов - прервал работу кода...

Отправлено: 14:53, 21-12-2018 | #6


Ветеран


Contributor


Сообщения: 2708
Благодарности: 1684

Профиль | Отправить PM | Цитировать


RealDT, у меня нет большого опыта с RoboCopy, озвученные проблемы мне кажутся странными.
Тогда вот вариант для любого уровня вложенности подпапок на основе Move
Код: Выделить весь код
@Echo Off
cls
	Set "Disk=%~d0"
	Set "List=%Disk%\dir.txt"
	Set "Backup=%Disk%\%Date:~6,4%-%Date:~3,2%-%Date:~0,2% reserv"

	For /f "usebackq delims=" %%D in ("%List%") Do (
		For /F "usebackq delims=" %%F In (`Dir "%Disk%\%%D\" /B /S /A:D 2^>nul^|Sort /R`) Do (
			Call :MyMove "%%~dpD" "%Backup%\" "%%F" 
		)
		Call :MyMove "%%~dpD" "%Backup%\" "%Disk%\%%D" 
	)
pause
GoTo :Eof

:MyMove
	If Not Exist %3 Exit /B 1
	Set "Out=%~3"
	Call Set "Out=%%Out:%~1=%~2%%"
	If Not Exist "%Out%" Md "%Out%"
	2>nul Move /Y "%~3\*.*" "%Out%\"
	Rd %3
GoTo :Eof

-------
Даже самая сложная проблема обязательно имеет простое, лёгкое для понимания, неправильное решение. Каждое решение плодит новые проблемы.


Отправлено: 18:03, 21-12-2018 | #7


Новый участник


Сообщения: 4
Благодарности: 0

Профиль | Отправить PM | Цитировать


Спасибо за варианты решения.
Вот ещё один вариант решения:

Код: Выделить весь код
@echo off
set curdisk=%~d0
 
Set folder_where=%curdisk%\%date:~6,4%-%date:~3,2%-%date:~0,2% reserv
 
if not exist "%folder_where%" md "%folder_where%"
 
FOR /F "tokens=1,2* delims=;" %%I IN (dir.txt) DO (
    if not exist "%folder_where%\%%J" md "%folder_where%\%%J"
    move /Y "%curdisk%\%%I" "%folder_where%\%%J"
)
При этом структура файла dir.txt поменялась и должна быть такой:
Каталог1\!Папка11\!Папка111\Папка1111;Каталог1\!Папка11\!Папка111
Каталог1\!Папка12\!Папка121\Папка1121;Каталог1\!Папка12\!Папка121
Каталог2\Папка12\Папка!331;Каталог2\Папка12
Каталог3\Папка13\;Каталог3

Т.е.:
- в переменную %%I записывается каталог "что переносить";
- в переменную %%J записывается часть каталога "куда переносить", полный путь "куда переносить" будет таким %folder_where%\%%J

Отличия от начального варианта решения:
- убрал SETLOCAL enabledelayedexpansion, который удалял воскличательные знаки в именах каталогов и файлах;
- убрал внешний цикл FOR (оставил только один цикл);
- добавил неявную переменную %%J
- изменил структуру dir.txt, в котором каждая строка формирует значения для %%I и %%J.

Отправлено: 12:44, 27-12-2018 | #8


Ветеран


Сообщения: 27449
Благодарности: 8086

Профиль | Отправить PM | Цитировать


RealDT, только имейте в виду, что curdisk — не текущий диск, а диск, на котором находится пакетный файл.

Отправлено: 17:04, 27-12-2018 | #9



Компьютерный форум OSzone.net » Программирование, базы данных и автоматизация действий » Скриптовые языки администрирования Windows » CMD/BAT - Перенос каталогов и файлов

Участник сейчас на форуме Участник сейчас на форуме Участник вне форума Участник вне форума Автор темы Автор темы Шапка темы Сообщение прикреплено

Похожие темы
Название темы Автор Информация о форуме Ответов Последнее сообщение
Прочие - Программы для массового переименования каталогов и файлов Daiv Программное обеспечение Windows 39 17-06-2011 16:33
CMD/BAT - [решено] Конвертирование файлов с сохранением структуры каталогов Sarge81 Скриптовые языки администрирования Windows 3 17-09-2010 07:12
(solved) команда для копирования файлов / каталогов e9990638 Автоматическая установка Windows 2000/XP/2003 5 21-11-2006 14:52
Тормозит обзор файлов и каталогов в сети denbessonov Сетевые технологии 6 10-08-2005 14:09
Удаление неудаляемых файлов и каталогов Kasper Хочу все знать 52 14-05-2004 00:29




 
Переход