首页 > 解决方案 > Linux - 如何编写一个 glob 模式以匹配扩展名中至少有一个大写字符的所有文件名

问题描述

如何编写正则表达式以查找文件扩展名中至少包含 1 个大写字符(仅)的所有文件。

例如:

TextFile2.TXT.tXT
TextFile3.TXT.txt
TextFile.Txt
TextFile1.tXt
TextFile.TXT.txT

这个“查找”命令有什么问题?

find . -type f -name "*.*[[:upper:]]*"

输出:

./TextFile2.TXT.tXT
./TextFile3.TXT.txt        (->this file shouldn't be here) 
./TextFile.Txt
./TextFile1.tXt
./TextFile.TXT.txT

谢谢 !

标签: linuxbashmacos

解决方案


假设:

  • OP提供了一个find/glob代码示例,但regular expression在问题中提到;我将假设一个regex解决方案是可以接受的
  • 对于看起来有多个扩展名的文件(例如,TextFile2.TXT.tXT),我们只对“最后一个”扩展名感兴趣(即,文件名中最后一个句点之后的内容)
  • 感兴趣的文件必须在最后一个句点之后至少有 1 个字符
  • 我们只对A-Z最后一个句点后至少有 1 个大写字母 ( )的文件名感兴趣

示例文件:

$ ls -1 | sort
TextFile.TXT.txT
TextFile.Txt
TextFile1.tXt
TextFile1.tXt.               # ignore this file
TextFile2.TXT.X
TextFile2.TXT.t              # ignore this file
TextFile2.TXT.tXT
TextFile3.TXT.txt            # ignore this file

find's -regex使用选项的一个想法:

$ find . -regex '.*TextFile.*[.][^.]*[A-Z]+[^.]*' | sort
./TextFile.TXT.txT
./TextFile.Txt
./TextFile1.tXt
./TextFile2.TXT.X
./TextFile2.TXT.tXT

在哪里:

  • .*- 匹配字符串之前的任何内容TextFile
  • .*[.]- 将所有内容匹配到一个时期,然后......
  • [^.]*[A-Z]+[^.]*- 零个或多个非句+点 至少一个大写字母+零个或多个非句点

注意事项

  • sort不是必需的;sort添加以更容易比较两个文件名列表
  • 以上适用于(GNU)find4.6.0
  • 问题已被标记为macos; 这个“查找”的 MacOS 手册页似乎显示了对该-regex选项的支持;我无权访问 MacOS 机器来验证工作是否-regex与建议的相同

推荐阅读