PDA

Показать полную графическую версию : Как каталогизировать папки средствами JS ?


ruslaw
01-05-2018, 13:52
Имеется папка с множеством вложенных папок разных уровней вложения и файлы в каждой из них.
Необходимо методами JS разместить в каждой папке текстовый файл со списком содержащихся в ней файлов (но не папок) и именем папки в кодировке 1251.
Прошу помощи.

Iska
01-05-2018, 14:03
ruslaw, VBScript устроит?

ruslaw
01-05-2018, 15:20
я в нем не разбираюсь совсем, а JS я смог бы потом модифицировать

Busla
01-05-2018, 15:22
ruslaw, в таком виде задача выглядит бессмысленной деятельностью, т.к. содержимое директории на нижнем уровне практически и есть "текстовый файл со списком содержащихся в ней файлов"

Iska, с вашим опытом перенести перенести простой скрипт из VB в JS - всё равно, что почесаться. А вы продолжаете некромантию пропагандировать.

megaloman
01-05-2018, 20:22
var AllDir = "D:\\CMD_Forum\\Муз"; // --------- Полное имя рабочего каталога (без слэжа \ на конце)

var Maska = "^.*\\..*$";

var FSO = WScript.CreateObject("Scripting.FileSystemObject");

var RegMaska = new RegExp(Maska);
RegMaska.IgnoreCase = true;

AllFiles(AllDir);

// -------------------------------------------
function AllFiles(WDir) {
var Folds = FSO.GetFolder(WDir);
var Finfo = FSO.OpenTextFile(WDir + "\\!!! " + Folds.Name + ".Info", 2, true);
var SubF = new Enumerator(Folds.SubFolders);
var Files = new Enumerator(Folds.Files);
var jf;
Finfo.WriteLine("+++ " + Folds.Name + " +++ " + WDir);

while (!Files.atEnd()) {
jf = Files.item().Name;
if (RegMaska.test(jf)) {
Finfo.WriteLine(jf);
}
Files.moveNext();
}
Finfo.Close();

while (!SubF.atEnd()) {
AllFiles(WDir + "\\" + SubF.item().Name);
SubF.moveNext();
}
}Public FSO, RegMaska

AllDir = "D:\CMD_Forum\Муз" ' --------- Полное имя рабочего каталога (без слэжа \ на конце)
Maska= "^.*\..*"

Set FSO = CreateObject("Scripting.FileSystemObject")

Set RegMaska = New RegExp
RegMaska.Pattern = Maska
RegMaska.IgnoreCase = True

Call AllFiles(AllDir)

MsgBox "Скрипт завершился"

' ---------------------------------------------------------------------------
Sub AllFiles(WDir)

Set Folds = FSO.GetFolder(WDir)
Set SubF = Folds.SubFolders
Set Files = Folds.Files

Set Finfo = FSO.OpenTextFile(WDir + "\!!! " + Folds.Name + ".Info", 2, True)
Finfo.WriteLine "+++ " + Folds.Name + " +++ " + WDir

For Each jF In Files
If RegMaska.Test(jf) Then
Finfo.WriteLine FSO.GetFileName(jF)
End If
Next

Finfo.Close

For Each Folder In SubF
Call AllFiles(WDir + "\" + Folder.Name)
Next

End Sub@Echo Off
chcp 1251 >nul

Set "AllDir=D:\CMD_Forum\Муз"

Set "Maska=*.*"

Call :SpisFiles "%AllDir%"
FOR /F "usebackq delims=" %%d IN (`2^>nul Dir "%AllDir%" /B /S /A:D`) DO Call :SpisFiles "%%d"
GoTo :Eof

:SpisFiles
>"%~1\!!! %~nx1.Info" (
Echo +++ %~nx1 +++ %~1
FOR /F "usebackq delims=" %%f IN (`2^>nul Dir "%~1\%Maska%" /B /A:-D`) DO Echo %%f
)
GoTo :Eofcmd/bat ваяется многократно быстрее

Iska
01-05-2018, 21:31
Iska, с вашим опытом перенести перенести простой скрипт из VB в JS - всё равно, что почесаться.»
Busla, вовсе нет, я крайне слабо знаю JScript.

А вы продолжаете некромантию пропагандировать. »
Что значит «некромантию»? Они ровесники. И вообще — «Мы работаем дедовскими методами, но зато на совесть»™ :).

cmd/bat ваяется многократно быстрее »
Кому как ;).

ruslaw
01-05-2018, 23:45
megaloman, большое спасибо, JS-скрипт отработал отлично.
Кстати, батник создал только один индекс-файл - в указанной папке, а по подпапкам не пошел, но это не страшно, меня интересует именно JS.
И еще вопрос. Можно ли исключить из индексации (на JS-скрипте) скрытые папки, причем у меня в таких папках находятся видимые (не скрытые) подпапки и файлы?

megaloman
02-05-2018, 07:30
ruslaw, var AllDir = "D:\\CMD_Forum\\Box_In"; // --------- Полное имя рабочего каталога (без слэжа \ на конце)

var Maska = "^.*\\..*$";

var FSO = WScript.CreateObject("Scripting.FileSystemObject");

var RegMaska = new RegExp(Maska);
RegMaska.IgnoreCase = true;

AllFiles(AllDir);

// -------------------------------------------
function AllFiles(WDir) {
var Folds = FSO.GetFolder(WDir);
var FAttr = Folds.Attributes;
if (FAttr & 2 || FAttr & 4) {return}

var Finfo = FSO.OpenTextFile(WDir + "\\!!! " + Folds.Name + ".Info", 2, true);
var SubF = new Enumerator(Folds.SubFolders);
var Files = new Enumerator(Folds.Files);
var jf;
Finfo.WriteLine("+++ " + Folds.Name + " +++ " + WDir);

while (!Files.atEnd()) {
jf = Files.item().Name;
if (RegMaska.test(jf)) {
Finfo.WriteLine(jf);
}
Files.moveNext();
}
Finfo.Close();

while (!SubF.atEnd()) {
AllFiles(WDir + "\\" + SubF.item().Name);
SubF.moveNext();
}
}Пора начинать, есть повод! :)

я крайне слабо знаю JScript. » - Скромничаете? Рискую быть подвергнутым остракизму и нехорошим словам, я крайне слабо знаю JScript и, главное, его недолюбливаю. Предложенное решение с атрибутами наверное очень кривое. Дело в том, что значение атрибута папки может принимать достаточно многочисленные значения, как сумма всех атрибутов, например: Папка (16), папка архивная (48), скрытая (18), системная (20), скрытая и системная (22), скрытая системная архивная (54) и это далеко не все значения. Как вычленить из всего многообразия значений признак скрытости не знаю. Наверное, есть какой-то метод или арифметический трюк .... Либо определить атрибуты папок, которые Вы хотите обрабатывать, а остальные отсекать. Наверное, это легче.
Исправил решение в соответствии с предложением Busla. Отсекаются скрытые и системные папки.

батник подправил

Busla
02-05-2018, 11:27
megaloman, конечно, костыльное: надо проверять один единственный бит, а не перечислять все мыслимые комбинации:
if (FAttr & 16) { // это директория }

и к языку программирования это не имеет отношения - оно везде так

Attributes Property (https://docs.microsoft.com/en-us/previous-versions/windows/internet-explorer/ie-developer/windows-scripting/5tx15443%28v%3dvs.84%29)

Iska
02-05-2018, 12:14
Busla, мысль правильная, но выражена не вполне точно. Проверять надо не один единственный бит, а все биты. К языку программирования это также имеет отношение — надо использовать именно битовые логические операторы/функции, а не просто логические (там, где они отличаются).

megaloman
02-05-2018, 12:18
Busla, ruslaw, Вариант в атрибутами исправлен.
Iska, Второй бит отвечает за скрытность. Третий - за системность.

Iska
02-05-2018, 13:49
- Скромничаете? »
Увы, нет.

я крайне слабо знаю JScript и, главное, его недолюбливаю. »
Аналогично.

Предложенное решение с атрибутами наверное очень кривое. Дело в том, что значение атрибута папки может принимать достаточно многочисленные значения, как сумма всех атрибутов, например: Папка (16), папка архивная (48), скрытая (18), системная (20), скрытая и системная (22), скрытая системная архивная (54) и это далеко не все значения. Как вычленить из всего многообразия значений признак скрытости не знаю. Наверное, есть какой-то метод или арифметический трюк .... »
Решение вполне нормальное, только сравнивать нужно именно биты (а точнее — наложить на атрибуты маску из потребных битов), так, как это показано в сообщении коллеги Busla, в данном случае а):
if(Folds.Attributes & 18) {return} // Directory (16) + Hidden (2)
либо просто:
if(Folds.Attributes & 2) {return} // Hidden (2)
учитывая то, что тут у нас и так всегда будут только каталоги, и нет необходимости проверять сие отдельно, и б) нам необходимо и достаточно проверить наличие только атрибута Hidden, а остальные атрибуты нам по сути безразличны: есть ли они, нет ли их — нам не важно.

Iska, Второй бит отвечает за скрытность. Третий - за системность. »
Правильнее будет так — первый и второй: отсчёт битов принято вести с нуля — нулевой, первый, второй и т.д.

ruslaw
02-05-2018, 22:49
megaloman, преогромное спасибо, и батник и JS работают идеально, как я ожидал.
Busla, Iska, спасибо за ценные замечания, несмотря на свою скромную компетентность, я уловил смысл.
Друзья, жму всем руки!

Busla
03-05-2018, 10:08
Busla, мысль правильная, но выражена не вполне точно. Проверять надо не один единственный бит, а все биты.»
ok, проверять надо отдельные биты, а все биты скопом проверялись в исходном варианте при сравнении с конкретным числом

К языку программирования это также имеет отношение — надо использовать именно битовые логические операторы/функции, а не просто логические (там, где они отличаются). »
речь была о методике работы, а не о конкретном синтаксисе

в каком языке логические операторы не отличаются от двоичных?

Iska
03-05-2018, 10:53
ok, проверять надо отдельные биты, а все биты скопом проверялись в исходном варианте при сравнении с конкретным числом »
Да, так будет правильнее.

в каком языке логические операторы не отличаются от двоичных? »
В VBScript, в VBA. В VB, надо полагать, было так же (лень сейчас проверять/искать). И, если я правильно понимаю, в VB.Net всё осталось ровно то же самое: Logical and Bitwise Operators in Visual Basic | Microsoft Docs (https://docs.microsoft.com/en-us/dotnet/visual-basic/programming-guide/language-features/operators-and-expressions/logical-and-bitwise-operators).




© OSzone.net 2001-2012