【问题标题】:Listing entries in a directory using grep使用 grep 列出目录中的条目
【发布时间】:2013-01-20 20:14:42
【问题描述】:

我正在尝试列出目录中名称仅包含大写字母的所有条目。目录需要附加“/”。

#!/bin/bash
cd ~/testfiles/
ls | grep -r *.*

由于 grep 默认只查找大写字母(对吗?),我只是递归地在 testfiles 下的目录中搜索所有仅包含大写字母的名称。

不幸的是,这不起作用。

至于附加目录,我不确定为什么我需要这样做。有谁知道我可以从哪里开始详细解释我可以用 grep 做什么?此外如何解决我的问题?

【问题讨论】:

  • 一个好的起点是 man grep :-/
  • 我有,但它真的没有给我太多的工作。我承认我在这方面是个新手,所以我不太确定我应该为搜索字符串使用什么。 D:

标签: linux unix grep ls


【解决方案1】:

确切的正则表达式取决于 ls 命令的输出格式。假设你不使用 ls 的别名,你可以试试这个:

ls -R  | grep -o -w "[A-Z]*"

请注意,使用 ls 中的-R,您将递归地列出当前目录下的目录和文件。 grep 选项-o 告诉grep 只打印文本的匹配部分。 -w 选项告诉 grep 只考虑匹配整个单词。 "[A-Z]*" 是一个只过滤大写单词的正则表达式。

请注意,此正则表达式将打印 TEST.txt 和 TEXT.TXT。换句话说,它只会考虑由字母组成的名称。

【讨论】:

    【解决方案2】:

    列出文件的是ls,而不是grep,因此您需要指定要将“/”附加到目录的位置。使用ls --classify 将“/”附加到目录。

    grep 用于处理来自ls(或其他一些来源,一般来说)的结果,并且只显示与您指定的模式匹配的行。它不限于大写字符。您可以使用grep -E '^[A-Z/]*$ 将其限制为仅大写字符和“/”,或者如果您还需要数字、句点等,您可以使用grep -v -E [a-z] 过滤掉包含小写字符的行。

    由于grep 不是列出文件的程序,所以它不是您要执行递归的地方。如果您使用ls -Rls 可以递归地列出路径。但是,您只会以这种方式获取文件路径的最后一个组成部分。

    您可能需要考虑使用find 来处理递归。这对我有用:

    find . -exec ls -d --classify {} \; | egrep -v '[a-z][^/]*/?$'

    我应该注意,使用ls --classify 将“/”附加到目录末尾也可能会将一些其他字符附加到它可以分类的其他类型的路径中。例如,它可以将“*”附加到可执行文件的末尾。如果这不行,但您可以单独列出目录和其他路径,这可以通过运行find 两次来解决 - 一次用于目录,然后再次用于其他路径。这对我有用:

    find . -type d | egrep -v '[a-z][^/]*$' | sed -e 's#$#/#'

    find . -not -type d | egrep -v '[a-z][^/]*$'

    【讨论】:

      【解决方案3】:

      不,grep 不仅仅考虑大写字母。

      你的问题我有点不清楚,例如:

      • 从您对 -r 选项的使用来看,您似乎想要递归搜索,但您并没有这么说。为简单起见,我假设您不需要;如果您需要递归,请考虑查看@twm 的答案。
      • 您只想查找大写字母(字母)。这是否意味着您不想接受任何其他(非字母)字符,但它们对文件名有效(如数字或破折号、点等)
      • 因为你没有说我不允许每行只在文件上,我假设它没问题(因此使用ls -1)。

      天真的解决方案是:

      ls -1 | grep "^[[:upper:]]\+$"
      

      也就是说,打印所有只包含大写字母的行。在我打印的 TEMP 目录中,例如:

      ALLBIG
      LCFEM
      WPDNSE
      

      但是,这将排除 README.TXTFILE001 之类的文件,根据您的要求(见上文)很可能应该包含这些文件。

      因此,更好的解决方案是:

      ls -1 | grep -v "[[:lower:]]\+"
      

      也就是说,打印所有不包含小写字母的行。在我打印的 TEMP 目录中,例如:

      ALLBIG
      ALLBIG-01.TXT
      ALLBIG005.TXT
      CRX_75DAF8CB7768
      LCFEM
      WPDNSE
      ~DFA0214428CD719AF6.TMP
      

      最后,要“正确标记”带有结尾“/”的目录,您可以使用-F(或--classify)选项。

      ls -1F | grep -v "[[:lower:]]\+"
      

      再次,示例输出:

      ALLBIG
      ALLBIG-01.TXT
      ALLBIG005.TXT
      CRX_75DAF8CB7768
      LCFEM/
      WPDNSE/
      ~DFA0214428CD719AF6.TMP
      

      请注意,如果您可以使用不同的输出(例如find ! -regex ".*[a-z].*"),则可以使用不同的选项find,但这会有不同的输出。

      【讨论】:

      • 嗨,Christain.K - 我喜欢你的回答,谢谢。这说得通。 -1 设置到底有什么作用?
      • 嗯,我不确定我是不是做错了什么,但你的答案不起作用,它还会打印小写文本。
      • 可能有问题 - 我现在没有电脑,明天我会检查它。
      • 我认为应该是 '*' 而不是 '+'
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-04-14
      • 2013-04-28
      • 1970-01-01
      • 2021-04-10
      • 2018-06-15
      • 2012-12-09
      相关资源
      最近更新 更多