CLI 中的正则表达式匹配

CLI 中的正则表达式匹配

cli 是否有类似逻辑的东西?我想实现这个目标

mv -t newfolder *.(png|jpg)

这样所有 jpg 和 png 文件都将移动到新文件夹中。我知道这可以用

mv -t newfolder *.png && mv -t newfolder *.jpg

但总有一些语法糖,不是吗?

答案1

在重击中:

mv -t newfolder *.@(png|jpg)
  • ?(pattern) 匹配零次或一次出现的给定模式
  • *(pattern) 匹配零次或多次出现的给定模式
  • +(pattern) 匹配一次或多次出现的给定模式
  • @(pattern) 匹配给定模式之一
  • !(pattern) 匹配除给定模式之一之外的任何内容

它需要 extglob 选项:

$ shopt extglob
extglob         on

如果它关闭了,您可以使用以下命令将其打开

$ shopt -s extglob

答案2

mv -t newfolder *.(png|jpg)

zsh语法,但您需要通过以下方式启用它:

setopt extended_glob

严格来说,你应该这样写:

mv -t newfolder -- *.(png|jpg)

否则,如果某些文件名以-字符开头,则它将无法正常工作。


mv -t newfolder -- *.@(png|jpg)

ksh语法。zsh如果您打开该kshglob选项 ( ),则可以识别它;如果您打开该选项 ( ) setopt kshglob,则可以通过 bash识别它。extglobshopt -s extglob

但请注意,在这种情况下,kshbash两者都会遇到一个问题:如果没有pngjpg文件,*.@(png|jpg)将原封不动地传递到mv,如果确实存在该名称的文件(诚然不常见),它将被移动到newfolder

在 中bash,您可以通过打开该failglob选项来避免该问题。在ksh(仅限 ksh93 的最新版本)中,您能做的最好的事情就是编写~(N)*.@(png|jpg)(这相当于nullglobbash 中的或(N)zsh 中的通配限定符),如果没有匹配的文件,这将导致模式扩展为空,并且您然后会得到一个错误mv

答案3

Nykakin 的回答解释很多。只是补充一点——

中没有像正则表达式这样的东西CLI。它总是globbing您看到并使用的。

如果那是纯正则表达式,那么为什么.在您键入时不显示以点 []开头的文件和目录ls *?在正则表达式中*匹配一切对吗?但 glob 的情况并非如此。

答案4

我不知道任何正则表达式或任何漂亮的语法糖可以得到所需的结果。不过,这里有一种获得所需结果的方法,即使用 find。

find . -maxdepth 1 -mindepth 1 -type f -name '*.png' -o -name '*.jpg' -exec mv -t newfolder {} +

相关内容