我知道你可以使用这个find命令完成这个简单的工作,但我得到了一个不使用find或ls完成工作的任务.我怎样才能做到这一点?
gho*_*g74 30
你可以只使用shell来做到这一点
#!/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
Run Code Online (Sandbox Code Playgroud)
或者如果你有bash 4.0
#!/bin/bash
shopt -s globstar
for file in /path/**
do
echo $file
done
Run Code Online (Sandbox Code Playgroud)
Alb*_*gni 11
尝试使用
tree -d
Run Code Online (Sandbox Code Playgroud)
以下是一种可能的实现:
# 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 .
Run Code Online (Sandbox Code Playgroud)
作为练习,你可以想到如何修改上面的脚本来打印文件的完整路径(而不仅仅是缩进的文件/ 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
...
Run Code Online (Sandbox Code Playgroud)
注意使用!=(字符串比较)而不是-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
)
}
Run Code Online (Sandbox Code Playgroud)
请注意,在某些shell实现上,对于可以作为参数传递的字符数for(或者对于任何内置命令或外部命令),存在硬限制(~4k).由于shell 扩展,内联,*以在实际执行之前所有匹配的文件名的列表,for如果*在包含大量文件的目录中扩展,则会遇到麻烦(运行时会遇到同样的问题,比如ls *在同一目录中,例如得到类似的错误)Command too long.)
小智 5
由于它是针对 bash 的,所以令人惊讶的是,这还没有被提及:
(globstar 从 bash 4.0+ 起有效)
shopt -s globstar nullglob dotglob
echo **/*/
Run Code Online (Sandbox Code Playgroud)
就这样。
尾部斜杠/仅用于选择目录。
选项globstar激活**(递归搜索)。选项在不匹配任何文件/目录时nullglob删除 an 。*选项dotglob包括以点开头的文件(隐藏文件)。
| 归档时间: |
|
| 查看次数: |
39356 次 |
| 最近记录: |