如何使用基本的 Bash 命令和脚本命名目录树最深层的一个随机文件?
我正在寻找一种方法来将其作为单行代码而不需要函数来完成。还假设我从当前目录开始,然后逐步深入。
find
、grep
、sed
和awk
是可接受的命令。
我当前的尝试如下所示,但不起作用:
查找-类型 d |声明 COUNT=-1;声明 P="";读取 LINE 时;回显$LINE;声明C; C=$(echo $LINE | cut -c3- | sed "s/\//\n\//g" | grep '/' -c);回声 $C;如果 [ $COUNT -gt $C ];然后让 COUNT=$C;让 P=$LINE;回显“完成”;菲;完毕
这只会找到目录。
如何以最简单的方式解决这个问题?
答案1
这是一个奇怪的要求!
我会使用find
+awk
来获取最深目录中的文件:
bash-3.2$ deepest=$(find / -type f | awk -F'/' 'NF > depth {
> depth = NF;
> deepest = $0;
> }
>
> END {
> print deepest;
> }')
${deepest}
在命令中使用mv
作为练习,但以下五行可以帮助您进一步:
bash-3.2$ echo "${deepest}"
/Developer/SDKs/MacOSX10.6.sdk/System/Library/Frameworks/Ruby.framework/Versions/1.8/usr/lib/ruby/gems/1.8/gems/activesupport-2.3.5/lib/active_support/vendor/tzinfo-0.3.12/tzinfo/definitions/America/Argentina/Buenos_Aires.rb
bash-3.2$ echo "${deepest%.*}"
/Developer/SDKs/MacOSX10.6.sdk/System/Library/Frameworks/Ruby.framework/Versions/1.8/usr/lib/ruby/gems/1.8/gems/activesupport-2.3.5/lib/active_support/vendor/tzinfo-0.3.12/tzinfo/definitions/America/Argentina/Buenos_Aires
bash-3.2$ echo "${deepest%/*}"
/Developer/SDKs/MacOSX10.6.sdk/System/Library/Frameworks/Ruby.framework/Versions/1.8/usr/lib/ruby/gems/1.8/gems/activesupport-2.3.5/lib/active_support/vendor/tzinfo-0.3.12/tzinfo/definitions/America/Argentina
bash-3.2$ echo "${deepest##*/}"
Buenos_Aires.rb
bash-3.2$ echo "${deepest##*.}"
rb
以下更新问题:
find -type d
[...]“这只会找到目录。[...] 如何以最简单的方式解决这个问题?”。
通过供应-type f
给find
找到所有文件( f
),不是全部目录( d
)。
答案2
您缺少一些大括号,您颠倒了比较,并且需要打印结果:
find -type d | {
declare COUNT=-1
declare P=""
while read LINE
do echo $LINE
declare C=$(echo $LINE | cut -c3- | sed "s/\//\n\//g" | grep '/' -c)
echo $C
if [ $C -gt $COUNT ]; then let COUNT=$C; let P=$LINE; echo "Done"; fi
done
echo deepest: "$P"
}
稍微改进的版本,丢弃了调试内容:
find -type d -links 2 | (
declare COUNT=-1
P=""
while IFS= read -r LINE; do
declare C=$(echo $LINE | tr -cd / | wc -c)
if [ $C -gt $COUNT ]; then let COUNT=$C; P=$LINE; fi
done
echo deepest: "$P"
)
答案3
find -type f | awk -F/ 'NF > maxdepth { maxdepth = NF; file = $0 }; END {print file}'
看起来这本质上是一样的这个答案关于您发布的另一个问题,那个/这个有什么问题?
答案4
我会选择这些,尽管它们在包含前导空格的文件名上会失败。第一个仅输出文件名,第二个也包含该文件的路径:
find -type f | sed 's:[^/]*/: :g' | LC_ALL=C sort | head -1 | sed 's/^ *//'
find -type f | sed 'h;s:[^/]*/: :g;G;s/\n/\t/' | LC_ALL=C sort | head -1 | sed 's/.*\t//'