Форум программистов, компьютерный форум, киберфорум
Batch (CMD/BAT)
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.77/13: Рейтинг темы: голосов - 13, средняя оценка - 4.77
9 / 9 / 0
Регистрация: 14.10.2014
Сообщений: 69

Создание списка файлов на диске (рекурсия). Оптимизируем?

14.10.2014, 10:02. Показов 2543. Ответов 11
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Добрый день.
Есть скрипт на batch, который рекурсивно обходит список сетевых дисков и записывает найденные файлы в формируемый XML файл. Оно работает.
Но есть очень серьёзная проблема. К сожалению этот скрипт очень сильно нагружает сервер и приводит к его зависанию. На сервере находится около 10млн файлов.
Как я понял суть процесса заключается в том, что он сначала грузит найденный результат в память ПК, а затем начинает писать результат в файл.
Прошу помочь в ускорении и оптимизации данной утилиты.


Windows Batch file
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
: устанавливаем кодировку UTF-8. 
: Кодировка необходима для корректного открывания и импорта полученного *.XML в программу Excel
chcp 65001
 
: Тут формируется правильный заголовок для *.XML файла. 
: Обратите внимание на символ ^. Этот символпозволяет нам выводить в echo специальные символы.
: Символ ^ делает "экранирование" специальных символов, и они печатаются к нормальный текст.
echo ^<?xml version="1.0" encoding="UTF-8" standalone="yes"?^> > c:\temp\dir\%date%.xml.bak
echo ^<title xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"^> >> c:\temp\dir\%date%.xml.bak
echo ^<Meta FileSpace="\\sonas.gis.prom.int\"^>^<^/Meta^> >> c:\temp\dir\%date%.xml.bak
 
: В этой части начинается магия.
: Для понимания того, что тут написано используйте help для команды for
: В скобках мы кладем команду dir, которая запускается с s-рекурсие по всем подпапкам, b-вывод полных ппутей до файлов с именами файлов, x-позволяет нам без ошибок, если мена файло очень длинные, продолжитьь выполнение скрипта. Х-сократит слишком длинные имена, без потери свяинка.
: после do выполняем echo, которое выводит нам необходимую информацию из DIR, разбивая её по ключам из команды FOR, записывая вывод в файл.
: Двойная >> необходимо, чтобы дозаписывалась\писалась каждая прошенная строка
for /f "delims=" %%a in ('dir %1 /S /B /A:-D') do @echo ^<LINK DISK="%%~da" HL="%%~pa" LL="%%~na" EXTENSION="%%~xa" DATE="%%~ta" SIZE="%%~za bytes"^>%%~aa^<^/LINK^> >> c:\temp\dir\%date%.xml.bak
for /f "delims=" %%a in ('dir %2 /S /B /A:-D') do @echo ^<LINK DISK="%%~da" HL="%%~pa" LL="%%~na" EXTENSION="%%~xa" DATE="%%~ta" SIZE="%%~za bytes"^>%%~aa^<^/LINK^> >> c:\temp\dir\%date%.xml.bak
for /f "delims=" %%a in ('dir %3 /S /B /A:-D') do @echo ^<LINK DISK="%%~da" HL="%%~pa" LL="%%~na" EXTENSION="%%~xa" DATE="%%~ta" SIZE="%%~za bytes"^>%%~aa^<^/LINK^> >> c:\temp\dir\%date%.xml.bak
for /f "delims=" %%a in ('dir %4 /S /B /A:-D') do @echo ^<LINK DISK="%%~da" HL="%%~pa" LL="%%~na" EXTENSION="%%~xa" DATE="%%~ta" SIZE="%%~za bytes"^>%%~aa^<^/LINK^> >> c:\temp\dir\%date%.xml.bak
for /f "delims=" %%a in ('dir %5 /S /B /A:-D') do @echo ^<LINK DISK="%%~da" HL="%%~pa" LL="%%~na" EXTENSION="%%~xa" DATE="%%~ta" SIZE="%%~za bytes"^>%%~aa^<^/LINK^> >> c:\temp\dir\%date%.xml.bak
for /f "delims=" %%a in ('dir %6 /S /B /A:-D') do @echo ^<LINK DISK="%%~da" HL="%%~pa" LL="%%~na" EXTENSION="%%~xa" DATE="%%~ta" SIZE="%%~za bytes"^>%%~aa^<^/LINK^> >> c:\temp\dir\%date%.xml.bak
for /f "delims=" %%a in ('dir %7 /S /B /A:-D') do @echo ^<LINK DISK="%%~da" HL="%%~pa" LL="%%~na" EXTENSION="%%~xa" DATE="%%~ta" SIZE="%%~za bytes"^>%%~aa^<^/LINK^> >> c:\temp\dir\%date%.xml.bak
for /f "delims=" %%a in ('dir %8 /S /B /A:-D') do @echo ^<LINK DISK="%%~da" HL="%%~pa" LL="%%~na" EXTENSION="%%~xa" DATE="%%~ta" SIZE="%%~za bytes"^>%%~aa^<^/LINK^> >> c:\temp\dir\%date%.xml.bak
for /f "delims=" %%a in ('dir %9 /S /B /A:-D') do @echo ^<LINK DISK="%%~da" HL="%%~pa" LL="%%~na" EXTENSION="%%~xa" DATE="%%~ta" SIZE="%%~za bytes"^>%%~aa^<^/LINK^> >> c:\temp\dir\%date%.xml.bak
for /f "delims=" %%a in ('dir %10 /S /B /A:-D') do @echo ^<LINK DISK="%%~da" HL="%%~pa" LL="%%~na" EXTENSION="%%~xa" DATE="%%~ta" SIZE="%%~za bytes"^>%%~aa^<^/LINK^> >> c:\temp\dir\%date%.xml.bak
 
: делаем гудок динамиком ПК, указывая на конец сбора информации.
echo 
: закрываем формирование xml файла
echo ^<^/title^> >> c:\temp\dir\%date%.xml.bak
 
:данный процесс помогает нам избавиться от аперсанда
:если быть точнее, то сделать его читаемым в файлах XML
:мы просто подменим  аперсанд & приемлемой для XML формой &amp;
:для этого первоначально расширяем локаль
setlocal enabledelayedexpansion
:указываем в каком именно файле мы будем заниматься изменениями
set FileToChange=c:\temp\dir\%date%.xml.bak
:указываем что будем менять
set "mask=&"
 данной строке указываем на что будем менять
set "mask2=&amp;"
:запускаем циклический поиск по файлу
for /f "delims=" %%i in (%FileToChange%) do (
:обявляем переменную с найденным значением
set out=%%i
:именно в этой строке меняем первое на второе
set "out=!out:%mask%=%mask2%!"
:выводим в готовый файл, который уже можно полноценно использовать
echo !out! >> c:\temp\dir\%date%_%random%.xml
)
Может кто-то поможет написать аналог на С++? Имеет это смысл?
0
Лучшие ответы (1)
IT_Exp
Эксперт
34794 / 4073 / 2104
Регистрация: 17.06.2006
Сообщений: 32,602
Блог
14.10.2014, 10:02
Ответы с готовыми решениями:

Поиск на диске файлов с расширениями .txt и .docx и создание списка имён найденных файлов
Помогите, нужно создать bat файл, который ищет на диске файлы *.txt *docx а потом создаёт список с их именами.

Вывод списка файлов на диске
Помогите пожалуйста! Уже очень долгое время бьюсь над кодом и все не работает! РУгается на done = _findfirst(&quot;I:\\*.*&quot;, &amp;f,...

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

11
Эксперт WindowsАвтор FAQ
 Аватар для Dragokas
18033 / 7736 / 892
Регистрация: 25.12.2011
Сообщений: 11,502
Записей в блоге: 16
14.10.2014, 13:18
Имеет смысл.
0
9 / 9 / 0
Регистрация: 14.10.2014
Сообщений: 69
15.10.2014, 09:19  [ТС]
Есть идеи, помимо?
0
Эксперт WindowsАвтор FAQ
 Аватар для Dragokas
18033 / 7736 / 892
Регистрация: 25.12.2011
Сообщений: 11,502
Записей в блоге: 16
15.10.2014, 10:42
Отключите временно защитное Антивирусное ПО.
Проверить SMART диска. Возможно микротормоза происходят при попытке чтения "сомнительных" кластеров.
Через диспетчер задач понизьте приоритет выполнения процесса cmd.exe до уровня "низкий".
Задайте маску сходства процесса только с одним из доступных на сервере процессором (желательно не нулевым). Смотрите по общей нагрузке.
Добавьте к DIR ключ /A-L (/A-D-L), чтобы не включать в поиск симлинки и точки повторной обработки.
Воспользуйтесь специализированным ПО для осуществления быстрой выборки файлов,
например Microsoft Log Parser. Пример использования.
Переписать программу на язык Visual Basic 6 с добавлением оператора DoEvents в цикл для разгрузки процессора.
1
9 / 9 / 0
Регистрация: 14.10.2014
Сообщений: 69
15.10.2014, 16:19  [ТС]
Спасибо! Действительно дельно.
0
9 / 9 / 0
Регистрация: 14.10.2014
Сообщений: 69
07.08.2015, 12:22  [ТС]
Windows Batch file
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
chcp 65001
 
echo ^<?xml version="1.0" standalone="yes"?^> > C:\Users\admin\Documents\filemonsql\dir\%date%.xml
echo ^<RECORDS^> >> C:\Users\admin\Documents\filemonsql\dir\%date%.xml
 
for /f "delims=" %%a in ('dir %1 /S /B /A:-D-L') do @echo ^<RECORD^>^<disk^>%%~da^<^/disk^>^<hl^>%%~pa^<^/hl^>^<ll^>%%~na^<^/ll^>^<extensions^>%%~xa^<^/extensions^>^<date^>%%~ta^<^/date^>^<size^>%%~za^<^/size^>^<^/RECORD^> >> C:\Users\admin\Documents\filemonsql\dir\%date%.xml
echo ^<^/RECORDS^> >> C:\Users\admin\Documents\filemonsql\dir\%date%.xml
 
setlocal enabledelayedexpansion
set FileToChange=C:\Users\admin\Documents\filemonsql\dir\%date%.xml.bak
set "mask=&"
set "mask2=&amp;"
for /f "delims=" %%i in (%FileToChange%) do (
set out=%%i
set "out=!out:%mask%=%mask2%!"
echo !out! >> C:\Users\admin\Documents\filemonsql\dir\%date%_%random%.xml
)
Можно как-то в цикл for воткнуть паузу в 1мс? Смысл в том, чтобы за 1мс обрабатывался всего 1 файл.
Имеет смысл воткнуть sleep вот так?

Windows Batch file
1
for /f "delims=" %%a in ('dir %1 /S /B /A:-D-L') do (sleep 1) @echo ^<RECORD^>^<disk^>%%~da^<^/disk^>^<hl^>%%~pa^<^/hl^>^<ll^>%%~na^<^/ll^>^<extensions^>%%~xa^<^/extensions^>^<date^>%%~ta^<^/date^>^<size^>%%~za^<^/size^>^<^/RECORD^> >> C:\Users\admin\Documents\filemonsql\dir\%date%.xml
0
 Аватар для ComSpec
3463 / 2001 / 635
Регистрация: 26.02.2014
Сообщений: 1,457
10.08.2015, 10:30
Лучший ответ Сообщение было отмечено ComSpec как решение

Решение

Цитата Сообщение от inzaim Посмотреть сообщение
Можно как-то в цикл for воткнуть паузу в 1мс? Смысл в том, чтобы за 1мс обрабатывался всего 1 файл.




Код для пакетного файла:

Windows Batch file
1
2
3
4
for /f "delims=" %%a in ('dir %1 /S /B /A:-D-L') do @(
 >nul ping -n 1 -w 1 ""
 >>"C:\Users\admin\Documents\filemonsql\dir\%date%.xml" echo ^<RECORD^>^<disk^>%%~da^</disk^>^<hl^>%%~pa^</hl^>^<ll^>%%~na^</ll^>^<extensions^>%%~xa^</extensions^>^<date^>%%~ta^</date^>^<size^>%%~za^</size^>^</RECORD^>
)
.


Пояснение:

1)
Windows Batch file
 >nul ping -n 1 -w 1 ""
-- пауза в 1 мс;

2) символ
/
экранировать (
^/
)
не нужно.
1
9 / 9 / 0
Регистрация: 14.10.2014
Сообщений: 69
10.08.2015, 14:20  [ТС]
Интересный вариант через ping проделать данную операцию ))) Спасибо )))
0
9 / 9 / 0
Регистрация: 14.10.2014
Сообщений: 69
08.09.2015, 16:38  [ТС]
Решил сделать небольшой апгрейд скрипту. Чтобы свои результаты он добавлял в бд mysql. Я посчитал, что так будет оптимально и в дальнейшем смогу оперативнее обрабатывать данный в самой БД. Для обработки файлов в количестве от 6.000.000 это гораздо удобнее, чем раскать по текстовому файлу.

Содержимое файла start.bat
Windows Batch file
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
@echo off
@cls
 
@color 72
 
: устанавливаем кодировку UTF-8. 
: Кодировка необходима для корректного открывания и импорта полученного *.sql в mysql
chcp 65001
 
del /f /q %~dp0dir_output\%date%.bat
 
: Пропускать корректировку во времени, которое раньше 10:00 - тот момент что убирал ноль перед числом '0'
set now=%DATE: =0% %TIME: =0%
: Разбираем дату и время на части
for /f "tokens=1-7 delims=/-:., " %%a in ( "%now%" ) do (
: Определяем в каком порядке будут идти день, месяц, год, часы и минуты
: set now=%%a%%b%%c_%%d%%e
set now=%%a_%%b_%%c
)
 
: Формируем заголовок таблицы для БД "SONAS" в MySQL
echo SET SQL_MODE="NO_AUTO_VALUE_ON_ZERO"; > %~dp0dir_output\%date%.bat
echo DROP TABLE IF EXISTS `%now%`; >> %~dp0dir_output\%date%.bat
echo CREATE TABLE IF NOT EXISTS `%now%` ( >> %~dp0dir_output\%date%.bat
echo   `disk` char(255) character set utf8 default NULL, >> %~dp0dir_output\%date%.bat
echo   `hl` longtext character set utf8, >> %~dp0dir_output\%date%.bat
echo   `date` varchar(255) default NULL, >> %~dp0dir_output\%date%.bat
echo   `size` int(11) default NULL, >> %~dp0dir_output\%date%.bat
echo   `attributes` text character set utf8, >> %~dp0dir_output\%date%.bat
echo   `ll` text character set utf8, >> %~dp0dir_output\%date%.bat
echo   `extension` text character set utf8 >> %~dp0dir_output\%date%.bat
echo ) ENGINE=MyISAM DEFAULT CHARSET=utf8 COLLATE=utf8_bin; >> %~dp0dir_output\%date%.bat
 
: В этой части начинается магия.
: Для понимания того, что тут написано используйте help для команды for
: В скобках мы кладем команду dir, которая запускается с s-рекурсией по всем подпапкам, b-вывод полных путей до файлов с именами файлов, x-позволяет нам без ошибок, если мена файлов очень длинные, продолжить выполнение скрипта. Х-сократит слишком длинные имена, без потери свяинка.
: после do выполняем echo, которое выводит нам необходимую информацию из DIR, разбивая её по ключам из команды FOR, записывая вывод в файл.
: Двойная >> необходимо, чтобы дозаписывалась\писалась каждая прошенная строка
 
for /f "delims=" %%a in ('dir %1 /S /B /X /A:-D-L') do @(
>nul ping -n 1 -w 1 ""
>> "%~dp0dir_output\%date%.bat" echo INSERT INTO `%now%` VALUES ^("%%~da", "%%~pa", "%%~ta", "%%~za", "%%~aa", "%%~na", "%%~xa"^)^;
)
 
 setlocal enabledelayedexpansion
 set FileToChange=%~dp0dir_output\%date%.bat
 set "mask=\"
 set "mask2=\\"
 for /f "delims=" %%i in (%FileToChange%) do (
 set out=%%i
 set "out=!out:%mask%=%mask2%!"
 echo !out! >> %~dp0dir_output\%date%.go.bat
 )
 
: Вызываем импорт sql в базу данных через mysql.exe
%~dp0mysql.bat
Содержимое mysql.bat
Windows Batch file
1
2
chcp 65001
C:\AppServ\MySQL\bin\mysql.exe -uroot -pPASSWORD DataBase < %~dp0dir_output\%date%.go.bat
Для корректной работы скрипта необходимо в папке со скриптом создать папку с названием dir_output
0
4340 / 2130 / 661
Регистрация: 26.04.2015
Сообщений: 6,823
08.09.2015, 23:09
Не совсем, а может и нет в тему: inzaim, Если http://www.w3.org/2001/XMLSchema-instance это Ваши проекты и разработки, извините, но совсем не интересно и ужасно нечитабельно.
0
9 / 9 / 0
Регистрация: 14.10.2014
Сообщений: 69
09.09.2015, 10:26  [ТС]
alpap
Не мое, да и ссылка не открывается.
0
4340 / 2130 / 661
Регистрация: 26.04.2015
Сообщений: 6,823
09.09.2015, 11:46
inzaim, Значит не обижаетесь, а ссылка действительно не открывается, а вчера открывалась, я же на основании чего-то оставил комментарий.
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
BasicMan
Эксперт
29316 / 5623 / 2384
Регистрация: 17.02.2009
Сообщений: 30,364
Блог
09.09.2015, 11:46
Помогаю со студенческими работами здесь

Создание списка файлов текущей директории
написать фаил lab.bat создающий список файлов текущей дериктории ,торый записыва т в файл 1.txt каталога c:/temp Так не работает...

Создание списка файлов в папке и подпапках
Здравствуйте. Есть папка с подпапками, названия могут быть разные. Нужно получить список всех файлов и путь к ним. Чтобы в...

Создание списка всех файлов каталога
Доброе время всем! Прошу помочь советом: Как сделать макрос, который бы создавал список всех файлов каталога...

Создание списка файлов и перенос его в БД
Помогите, люди! Нужно создать список файлов в папке и перенести его в таблицу. Мой адрес: leyftd@mail.ru Serj

Создание списка, печать списка на экран, добавления элемента в начало списка, конец списка
Построить динамическую структуру типа список . Необходимо реализовать следующие процедуры: 1. создание списка. 2. печать списка на...


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

Или воспользуйтесь поиском по форуму:
12
Ответ Создать тему
Новые блоги и статьи
Автоматическое создание документа при проведении другого документа
Maks 29.03.2026
Реализация из решения ниже выполнена на нетиповых документах, разработанных в конфигурации КА2. Есть нетиповой документ "ЗаявкаНаРемонтСпецтехники" и нетиповой документ "ПланированиеСпецтехники". В. . .
Настройка движения справочника по регистру сведений
Maks 29.03.2026
Решение ниже реализовано на примере нетипового справочника "ТарифыМобильнойСвязи" разработанного в конфигурации КА2, с целью учета корпоративной мобильной связи в коммерческом предприятии. . . .
Автозаполнение реквизита при выборе элемента справочника
Maks 27.03.2026
Программный код из решения ниже на примере нетипового документа "ЗаявкаНаРемонтСпецтехники" разработанного в конфигурации КА2. При выборе "Спецтехники" (Тип Справочник. Спецтехника), заполняется. . .
Сумматор с применением элементов трёх состояний.
Hrethgir 26.03.2026
Тут. https:/ / fips. ru/ EGD/ ab3c85c8-836d-4866-871b-c2f0c5d77fbc Первый документ красиво выглядит, но без схемы. Это конечно не даёт никаких плюсов автору, но тем не менее. . . всё может быть. . .
Автозаполнение реквизитов при создании документа
Maks 26.03.2026
Программный код из решения ниже размещается в модуле объекта документа, в процедуре "ПриСозданииНаСервере". Алгоритм проверки заполнения реализован для исключения перезаписи значения реквизита,. . .
Команды формы и диалоговое окно
Maks 26.03.2026
1. Команда формы "ЗаполнитьЗапчасти". Программный код из решения ниже на примере нетипового документа "ЗаявкаНаРемонтСпецтехники" разработанного в конфигурации КА2. В качестве источника данных. . .
Кому нужен AOT?
DevAlt 26.03.2026
Решил сделать простой ланчер Написал заготовку: dotnet new console --aot -o UrlHandler var items = args. Split(":"); var tag = items; var id = items; var executable = args;. . .
Отправка уведомления на почту при создании или изменении элементов справочника
Maks 24.03.2026
Программная отправка письма электронной почты на примере типового справочника "Склады" в конфигурации БП3. Перед реализацией необходимо выполнить настройку системной учетной записи электронной. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru