如何在 Linux 中循环目录?

2024-10-17 08:46:00
admin
原创
212
摘要:问题描述:我正在 Linux 上用 bash 编写脚本,需要遍历给定目录中的所有子目录名称。我该如何循环遍历这些目录(并跳过常规文件)?例如: 给定的目录/tmp/ 具有以下子目录:/tmp/A, /tmp/B, /tmp/C我想要检索 A、B、C。解决方案 1:到目前为止,所有答案都使用find,因此这...

问题描述:

我正在 Linux 上用 bash 编写脚本,需要遍历给定目录中的所有子目录名称。我该如何循环遍历这些目录(并跳过常规文件)?

例如:

给定的目录/tmp/

具有以下子目录:/tmp/A, /tmp/B, /tmp/C

我想要检索 A、B、C。


解决方案 1:

到目前为止,所有答案都使用find,因此这里只使用 shell。您的情况不需要外部工具:

for dir in /tmp/*/     # list directories in the form "/tmp/dirname/"
do
    dir=${dir%*/}      # remove the trailing "/"
    echo "${dir##*/}"    # print everything after the final "/"
done

解决方案 2:

cd /tmp
find . -maxdepth 1 -mindepth 1 -type d -printf '%f
'

简短解释一下:

  • find找到文件(很明显)

  • .是当前目录,位于cdis之后/tmp(恕我直言,这比/tmp直接在命令中使用更灵活。如果您想在此文件夹中进行更多操作find,则只有一个地方需要更改,即)cd

  • -maxdepth 1-mindepth 1确保find只在当前目录中查找,并且不会将.其自身包含在结果中

  • -type d仅查找目录

  • `-printf '%f
    `对于每个匹配仅打印找到的文件夹的名称(加上换行符)。

瞧!

解决方案 3:

您可以使用以下命令循环遍历所有目录,包括隐藏目录(以点开头):

for file in */ .*/ ; do echo "$file is a directory"; done

注意:仅当文件夹中至少有一个隐藏目录时,列表才在 zsh 中有效。在 bash 中,它还会显示*/ .*/`.`..


bash 包含隐藏目录的另一种可能性是使用:

shopt -s dotglob;
for file in */ ; do echo "$file is a directory"; done

如果您想排除符号链接:

for file in */ ; do 
  if [[ -d "$file" && ! -L "$file" ]]; then
    echo "$file is a directory"; 
  fi; 
done

要在每个解决方案中仅输出尾随目录名称(询问的 A、B、C),请在循环内使用它:

file="${file%/}"     # strip trailing slash
file="${file##*/}"   # strip path and leading slash
echo "$file is the directoryname without slashes"

示例(这也适用于包含空格的目录):

mkdir /tmp/A /tmp/B /tmp/C "/tmp/ dir with spaces"
for file in /tmp/*/ ; do file="${file%/}"; echo "${file##*/}"; done

解决方案 4:

适用于包含空格的目录

灵感来自Sorpigal

while IFS= read -d $'' -r file ; do 
    echo $file; ls $file ; 
done < <(find /path/to/dir/ -mindepth 1 -maxdepth 1 -type d -print0)

原始帖子(不支持空格)

受到Boldewyn的启发:带有命令的循环示例find

for D in $(find /path/to/dir/ -mindepth 1 -maxdepth 1 -type d) ; do
    echo $D ;
done

解决方案 5:

find . -mindepth 1 -maxdepth 1 -type d -printf "%P
"

解决方案 6:

我最常用的技术是find | xargs。例如,如果你想让此目录及其所有子目录中的每个文件都可读,你可以执行以下操作:

find . -type f -print0 | xargs -0 chmod go+r
find . -type d -print0 | xargs -0 chmod go+rx

-print0选项以 NULL 字符而不是空格结尾。该-0选项以相同的方式拆分其输入。因此,这是在带有空格的文件上使用的组合。

您可以将此命令链想象为获取每一行输出find并将其粘贴在命令的末尾chmod

如果您想在命令中间而不是末尾运行该命令作为其参数,则必须有点创造力。例如,我需要切换到每个子目录并运行命令latemk -c。所以我使用了(来自维基百科):

find . -type d -depth 1 -print0 | \n    xargs -0 sh -c 'for dir; do pushd "$dir" && latexmk -c && popd; done' fnord

这会产生 的效果for dir $(subdirs); do stuff; done,但对于名称中带有空格的目录而言是安全的。此外,对 的单独调用stuff是在同一个 shell 中进行的,这就是为什么在我的命令中我们必须使用 返回到当前目录popd

解决方案 7:

总结:

(cd /tmp; for d in */; do echo "${d%/}"; done)

解释。

无需使用外部程序。您需要的是 shell 通配符模式。为了避免/tmp事后需要删除,我在子 shell 中运行它,这可能适合您的目的,也可能不适合您。

简而言之,Shell 通配符模式:

  • *匹配任何非空字符串任意次。

  • ?匹配一个字符。

  • [...]与括号之间的字符匹配。您还可以指定范围([a-z][A-F0-9]等)或类别([:digit:][:alpha:]等)。

  • [^...]匹配括号之间以外的一个字符。

* 如果没有文件名与模式匹配,shell 将返回未改变的模式。任何不属于上述字符或字符串都代表其自身。


因此,该模式*/将匹配以 结尾的任何文件名//文件名尾部的 明确标识了一个目录。

最后一点是删除尾部斜杠,这可以通过变量替换来实现${var%PATTERN},它从 中包含的字符串末尾删除最短的匹配模式var,其中PATTERN是任何有效的通配符模式。所以我们写${d%/},这意味着我们要从 表示的字符串中删除尾部斜杠d

解决方案 8:

如果要在 for 循环中执行多个命令,可以将findwith mapfile(bash >= 4) 的结果保存为变量,然后使用 遍历数组${dirlist[@]}。它也适用于包含空格的目录。

find命令基于Boldewyn 的回答。有关该find命令的更多信息可在此处找到。

IFS=""
mapfile -t dirlist < <( find . -maxdepth 1 -mindepth 1 -type d -printf '%f
' )
for dir in ${dirlist[@]}; do
    echo ">${dir}<"
    # more commands can go here ...
done

解决方案 9:

你可以构建一个最小的 bash 循环(基于 ghostdog74 的答案)

for dir in directory/*                                                     
do                                                                                 
  echo ${dir}                                                                  
done

按目录压缩一大堆文件

for dir in directory/*
do
  zip -r ${dir##*/} ${dir}
done                                               

解决方案 10:

find . -type d -maxdepth 1

相关推荐
  为什么项目管理通常仍然耗时且低效?您是否还在反复更新电子表格、淹没在便利贴中并参加每周更新会议?这确实是耗费时间和精力。借助软件工具的帮助,您可以一目了然地全面了解您的项目。如今,国内外有足够多优秀的项目管理软件可以帮助您掌控每个项目。什么是项目管理软件?项目管理软件是广泛行业用于项目规划、资源分配和调度的软件。它使项...
项目管理软件   1124  
  IPD(Integrated Product Development,集成产品开发)流程是一种广泛应用于高科技和制造业的产品开发方法论。它通过跨职能团队的紧密协作,将产品开发周期缩短,同时提高产品质量和市场成功率。在IPD流程中,CDCP(Concept Decision Checkpoint,概念决策检查点)是一个关...
IPD培训课程   79  
  研发IPD(集成产品开发)流程作为一种系统化的产品开发方法,已经在许多行业中得到广泛应用。它不仅能够提升产品开发的效率和质量,还能够通过优化流程和资源分配,显著提高客户满意度。客户满意度是企业长期成功的关键因素之一,而IPD流程通过其独特的结构和机制,能够确保产品从概念到市场交付的每个环节都围绕客户需求展开。本文将深入...
IPD流程   70  
  IPD(Integrated Product Development,集成产品开发)流程是一种以跨职能团队协作为核心的产品开发方法,旨在通过优化资源分配、提高沟通效率以及减少返工,从而缩短项目周期并提升产品质量。随着企业对产品上市速度的要求越来越高,IPD流程的应用价值愈发凸显。通过整合产品开发过程中的各个环节,IPD...
IPD项目管理咨询   82  
  跨部门沟通是企业运营中不可或缺的一环,尤其在复杂的产品开发过程中,不同部门之间的协作效率直接影响项目的成败。集成产品开发(IPD)作为一种系统化的项目管理方法,旨在通过优化流程和增强团队协作来提升产品开发的效率和质量。然而,跨部门沟通的复杂性往往成为IPD实施中的一大挑战。部门之间的目标差异、信息不对称以及沟通渠道不畅...
IPD是什么意思   74  
热门文章
项目管理软件有哪些?
云禅道AD
禅道项目管理软件

云端的项目管理软件

尊享禅道项目软件收费版功能

无需维护,随时随地协同办公

内置subversion和git源码管理

每天备份,随时转为私有部署

免费试用