Я знаю, что вы можете использовать команду find для этой простой работы. Но у меня есть задание не использовать find или ls и выполнять эту работу. Пожалуйста, помогите ....Как рекурсивно перечислить подкаталоги в bash без использования команд find или ls?
ответ
Команда du
будет перечислять подкаталоги рекурсивно.
Я не уверен, если пустые каталоги получить упоминания, хотя
пустые каталоги отображаются для меня с помощью bash на моем mac –
Попробуйте использовать
tree -d
Почему я получил -1? Прокомментируйте пожалуйста. –
Я не дал вам -1, но для меня это очевидно, почему вы его получили. Почему бы не дать ответ «alias bla ls»; bla'? Заданный вопрос заключался в том, чтобы написать алгоритм, а не найти некоторую * команду *, которая делает то же самое, что и 'ls', но не называется' ls'. – vladr
@ Vlad Romascanu: О, хорошо, но из «У меня есть задание не использовать find или ls и выполнять работу». Я понял, что все было достаточно хорошо, кроме find и ls ^^ –
Как Марк Байерс сказал, что вы можете использовать echo *
, чтобы получить список всех файлов в текущем каталог.
Команда test
или []
имеет возможность проверить, является ли файл каталогом.
Применить рекурсию, и все готово.
В качестве альтернативы' echo', 'for' будет glob , поэтому OP может использовать 'for file in *; делать ... ; done'. – outis
вы можете сделать это только с оболочкой
#!/bin/bash
recurse() {
for i in "$1"/*;do
if [ -d "$i" ];then
echo "dir: $i"
recurse "$i"
elif [ -f "$i" ]; then
echo "file: $i"
fi
done
}
recurse /path
ИЛИ если у вас есть Баш 4,0
#!/bin/bash
shopt -s globstar
for file in /path/**
do
echo $file
done
Почему бы вам не сделать так, чтобы вы с помощью команды tree тоже? или тот, у кого есть эхо, это также действительные ответы. – ghostdog74
Это не удастся, если каталог пуст, то есть он будет печатать 'dir: bla/*', поскольку 'bla/*' рассматривается как литерал, поскольку у него нет потомков. Вы можете использовать 'pushd/popd' или добавить' if [["$ 1/*" = "$ i"]]; затем продолжить; fi' как первая строка после 'do'. – Bogdan
$ function f { for i in $1/*; do if [ -d $i ]; then echo $i; f $i; fi; done }
$ mkdir -p 1/2/3 2/3 3
$ f .
./1
./1/2
./1/2/3
./2
./2/3
./3
-1 Если вы собираетесь предоставить полный ответ на вопрос о домашнем задании, сделайте его правильным. как насчет пробелов в именах записей в каталоге? –
, и он не вводит каталоги и не отображает текстовые файлы. – 18446744073709551615
он вводит каталоги, а ОП ничего не говорит о текстовых файлах (или любых файлах, кроме каталогов). Я не буду исправлять проблемы с «каталогами с пробелами». –
Ниже одна из возможных реализаций:
# my_ls -- recursively list given directory's contents and subdirectories
# $1=directory whose contents to list
# $2=indentation when listing
my_ls() {
# save current directory then cd to "$1"
pushd "$1" >/dev/null
# for each non-hidden (i.e. not starting with .) file/directory...
for file in * ; do
# print file/direcotry name if it really exists...
test -e "$file" && echo "$2$file"
# if directory, go down and list directory contents too
test -d "$file" && my_ls "$file" "$2 "
done
# restore directory
popd >/dev/null
}
# recursively list files in current
# directory and subdirectories
my_ls .
В качестве вы можете подумать о том, как изменить abov e, чтобы печатать полные пути к файлам (а не только отступы файла/dirnames), возможно, избавиться от pushd
/popd
(и необходимости второго параметра $2
).
Кстати, обратите внимание на использование test XYZ && command
, который полностью эквивалентен if test XYZ ; then command ; fi
(т.е. выполнять command
, если test XYZ
успешно). Также обратите внимание, что test XYZ
эквивалентен [ XYZ ]
, то есть вышеуказанное также эквивалентно if [ XYZ ] ; then command ; fi
. Также обратите внимание, что любая точка с запятой ;
может быть заменена новой строкой, они эквивалентны.
Извлеките условие test -e "$file" &&
(оставляйте только echo
) и посмотрите, что произойдет.
Удалите двойные кавычки около "$file"
и посмотрите, что произойдет, когда каталог, содержимое которого вы указываете, содержит имена файлов с пробелами в них. Добавьте set -x
в начало скрипта (или вместо него вместо этого введите sh -x scriptname.sh
), чтобы включить отладочный вывод и посмотреть, что происходит в деталях (перенаправить вывод отладки в файл, запустите sh -x scriptname.sh 2>debugoutput.txt
).
также список скрытых файлов (например .bashrc
):
...
for file in * .?* ; do
if [ "$file" != ".." ] ; then
test -e ...
test -d ...
fi
done
...
Обратите внимание на использование !=
(сравнение строк) вместо -ne
(числовое сравнение.)
Другой метод будет порождать подоболочки вместо использования pushd
/popd
:
my_ls() {
# everything in between roundbrackets runs in a separatly spawned sub-shell
(
# change directory in sub-shell; does not affect parent shell's cwd
cd "$1"
for file in ...
...
done
)
}
Обратите внимание, что на некоторых реализациях оболочки существует жесткое ограничение (~ 4k) на количество символов, которые могут быть переданы как аргумент for
(или любой встроенной или внешней команде.) Поскольку оболочка expands, inline, *
to a list of all matching filenames до фактического выполнения на нем for
, вы можете столкнуться с проблемой, если *
раскрывается внутри каталога с большим количеством файлов (такая же проблема вы столкнетесь при запуске, скажем ls *
в том же каталоге, e .г. получите ошибку, например Command too long
.)
вы можете использовать 'shopt -s dotglob' для отображения скрытых файлов. – ghostdog74
@ghostdog - не переносится. '. *' (или '.? *', чтобы пропустить '.' с места в карьер) делает трюк просто прекрасным и переносимым тоже. – vladr
С технической точки зрения, ни find, ни ls не используются find2perl | perl или File::Find напрямую.
$ find2perl -type d | perl $ perl -MFile::Find -e'find(sub{-d&&print"$File::Find::name\n"},".")'
, но тогда, если это так, используя Python/Ruby/PHP и т. Д. Любой язык, который может отображать файлы, технически не будет использовать 'ls' или' find' – ghostdog74
@ ghostdog74 Очевидно. Но поскольку все серьезные ответы получили меньше, чем потрясающие отзывы, это что-то ... менее серьезное. (Я на самом деле собирался написать клоун 'find' в C и скрипт оболочки, который компилирует + запускает его, но решил, что это слишком много усилий для шутки.) – ephemient
Поскольку для Баша, это удивительно, что это не было уже сказано:
(globstar действует с Баша 4.0+)
shopt -s globstar nullglob dotglob
echo **/*/
Это все.
Конечная косая черта /
есть, чтобы выбрать только dirs.
Опция globstar
активирует **
(поиск рекурсивно). Вариант nullglob
удаляет *
, когда он не соответствует файлу/директории. Опция dotglob
содержит файлы, начинающиеся с точки (скрытые файлы).
- 1. Рекурсивно перечислять скрытые файлы без ls, find или extendedglob
- 2. Как перечислить все подкаталоги со строкой, но не подкаталоги соответствия
- 3. Как отредактировать точечные фрагменты рекурсивно, используя find в bash?
- 4. Понимание использования подстановки команд в bash
- 5. Рекурсивный список каталогов в оболочке без использования ls
- 6. Рекурсивно выполняя команду ls без -R
- 7. bash перечислить все подкаталоги в папке, записать их в массив для использования в меню
- 8. UBUNTU команд bash'а Ls
- 9. bash | подсчет файлов без «find»
- 10. Удаление каталога рекурсивно без использования команды rm
- 11. Как перечислить каталог рекурсивно
- 12. Как создать несуществующие подкаталоги рекурсивно с помощью Bash?
- 13. Perl: Подкаталоги Glob рекурсивно
- 14. Сценарий Bash: расширение аргумента без использования $ @ или $ *
- 15. Портативный способ перечислить все файлы в каталоге без разбора ls или найти
- 16. Создать идентификатор без использования команд или сортировки
- 17. Как перечислить каталоги и подкаталоги в VB.net
- 18. Предел SSH - bash без команд
- 19. Как перечислить все подкаталоги в C#?
- 20. Использование Bash, как мне подавать список файлов в «ln -s» без использования «find»?
- 21. Как рекурсивно перечислить файлы из папки?
- 22. Как перебирать каталоги (включая скрытые) в bash без команды «find»?
- 23. Перечислить все каталоги и файлы рекурсивно с FTP-сайта
- 24. LS без использования системных вызовов в PHP
- 25. Как рекурсивно перечислить свойства объекта?
- 26. Выполнение команд ls в c
- 27. Как я рекурсивно перечислить все каталоги в месте, в ширину?
- 28. Как рекурсивно перечислить все файлы и каталоги
- 29. Git добавить отдельные подкаталоги рекурсивно
- 30. Выполнение нескольких команд без использования; а также &?
Что вы должны использовать для этого? Ваш собственный сценарий оболочки, программа на C, Java ...? Если вы сообщите нам, что вы * можете использовать *, помощь должна быть более прибыльной :-) – Grundlefleck
Возможно, вы сможете использовать 'echo *' или варианты для эмуляции 'ls'. –