我想做类似的事情:
$ convert [a,b,c,d,e].png -resize 50% <current_match>_half.png
我怎样才能做到这一点?是否有一些变量存储当前匹配?我在文档中找不到任何内容,但也许我正在寻找错误的关键字。
我想也许我可以做到这一点xargs
,但我也无法解决。
答案1
ImageMagick 工具的通配符功能有限。如果传递多个文件名或文字通配符,它将创建具有顺序编号的输出文件,例如:
convert [a-e].png -resize 50% half.png
创建half-0.png
、half-1.png
等
如果要匹配输入文件名,则必须convert
在循环中显式或通过工具一次调用一个文件。 (或者,您可以稍后重命名文件,但这样做没有任何优势。)在循环内,您可以使用 zsh文件名操作或者字符串操作结构体。
for i in [a-e].png; do
convert $i -resize 50% %{i:t}_half.png
done
如果您在脚本中使用它,您可能需要添加N
全局限定符这样,如果没有匹配的文件,通配符模式将扩展为空:for i in [a-e].png(N); do …
Zsh 附带了一个根据模式重命名文件的工具:zmv
。您可以将其用于其他基于名称的转换。
autoload -U zmv
zmv -p convert -o '-resize 50%' '([a-e]).png' '${1}_half.png'
编写这些名称模式的替代方法包括:
zmv -p convert -o '-resize 50%' '([a-e])(.png)' '${1}_half$2'
zmv -p convert -o '-resize 50%' -w '[a-e].png' '${1}_half.png'
zmv -p convert -o '-resize 50%' '[a-e].png' '${f:t}_half.png'
您可以创建别名并放入您的.zshrc
:
autoload -U zmv
alias zcp='zmv -C'
alias zln='zmv -L'
alias zconvert='zmv -p convert'
下面的包装器比上面的别名好一点,因为它消除了将所有选项传递到convert
内部引号的要求。如果您通过任何zmv
选项,它们必须位于所有convert
选项之前。
zconvert () {
typeset -a zmv_options=
while [[ $1 = -[finqQsvwW] ]]; do
zmv_options+=($1)
done
zmv -p convert $zmv_options -o "$@[1,-3]" $@[-2] $@[-1]
}
答案2
我可能会将其写为对 glob 生成的名称的循环:
for f in [abcde].png; do
convert "$f" -resize 50% "${f%.png}"_half.png
done
注意:上面的例子中没有任何特定内容嘚;它应该在任何 POSIX 兼容的 shell 中工作(短跑,克什,巴什,嘚, ETC。;包括几乎任何现代版本嘘)。
斯蒂芬·查泽拉斯还指出嘚当 glob 无法匹配任何文件时,有不同的默认行为:它给出错误消息,而不是使用模式本身作为扩展的唯一“结果”。这种情况下的这种行为也可以在其他 shell中进行调整(例如failglob
,nullglob
巴什,特殊的~(N)
全局前缀克什、NOMATCH
和NULL_GLOB
中的选项嘚)。