在Ubuntu终端中如何批量递归调整图像大小?

42

我有多张图片存储在一组有组织的文件夹中。我需要从它们所在的父目录开始,递归地按特定百分比重新调整这些图像的大小。我正在运行Ubuntu 11.10,并且更喜欢直接从终端学习如何完成此操作。

9个回答

88

您可以使用imagemagick。例如,如果要将当前目录下的所有JPG图像调整为其原始大小的50%,请执行以下操作:

for f in `find . -name "*.jpg"`
do
    convert $f -resize 50% $f.resized.jpg
done

生成的文件名中会有两个“.jpg”字样,如果这是一个问题,您可以考虑以下替代方案。

要遍历/查找要调整大小的文件,您也可以使用xargs。例如:

find . -name "*.jpg" | xargs convert -resize 50%

这将创建图像的副本。如果您只想原地转换它们,您可以使用:

find . -name "*.jpg" | xargs mogrify -resize 50%

1
问题提到了“一组有组织的文件夹”。需要一个“查找”。 - Alexander Gorshenev
很棒的脚本。如果使用mogrify,请注意执行以下命令: mogrify -resize 50% $f 而不是 mogrify $f -resize 50% - morpheus
for ...; do ... done 的解决方案似乎不能正常工作(它在循环内寻找 .jpg.jpg 文件)。这个修改后的版本可以正常工作:<pre>for f in find . -name "*.jpg"; do convert basename $f .jpg.jpg -resize x600 basename $f .jpg_resized.png; done</pre> - Thibaud Ruelle
对于格式不佳表示抱歉,我无法在5分钟内找到禁用code标记的方法,但您已经明白了…… - Thibaud Ruelle
@ThibaudRuelle 谢谢你发现了这个问题 :) - betabandido
显示剩余6条评论

9
您也可以使用。
sudo apt install imagemagick
sudo apt-get install nautilus-image-converter
nautilus -q

对于在当前文件夹中调整/旋转图像。您只需安装,然后右键单击一个或多个图像并选择所需大小即可完成。 nautilus -q 是停止nautilus。只需重新启动nautilus,您就可以使用图像转换器。


1
非常好用。谢谢。 - Fabio Gomes
嘿!这应该是被接受的答案。使用它非常方便。类似的答案在这里:https://askubuntu.com/questions/1053081/how-to-install-the-right-click-photo-resizer-on-ubuntu-18-04 - Nav
我不确定为什么这个没有更多的赞。作为一名程序员,我很熟悉命令行,但当我只想调整一些图片大小时,拥有一个用户界面比每次查找imagemagick命令要容易得多。 - kramer65

8

扩展@betabandido的答案:

如果图像所在的文件名或文件夹名中有空格,则应使用 -print0 和 find 以及 -0 和 xargs 来避免任何解析错误。

find . -name "*.jpg" -print0 | xargs -0 convert -resize 50%
find . -name "*.jpg" -print0 | xargs -0 mogrify -resize 50%

1
使用quality也可以:find . -name "*.jpg" -print0 | xargs -0 mogrify -quality 70% - Diego Somar

1
如果您提供新的调整大小分辨率,它也可以起作用:
convert $f.jpg -size 1024x768 $f.resized.png

1

虽然这是一个老问题,但我认为以下方法最简单,而且可以处理空格和非“标准”字符。

find -iname "*.jpg" -exec convert {} -resize 1280x1280 {} \;

这是我的解决方案,使用最大尺寸,但如果你想调整大小为百分比,只需适应即可。

find -iname "*.jpg" -exec convert {} -resize 50% {} \;

1

我稍微修改了被采纳的答案的代码,以包括png文件并在文件名中添加前缀而不是后缀,以便一次选择所有调整大小的文件更容易。

for p in `find . -name "*.jpg" -o -name "*.png"`
do
    d=${p%/*}
    f=${p##*/}
    b=${f%.*}
    e=${f##*.}
    convert $p -resize 33% $d/thumb.$b.$e
done

通过一些修改,可以重新创建目录结构到一个单独的目录,并只保留具有相同目录结构的调整大小的文件。另一个选项是将目录结构展平,并使用随机生成的文件名,并通过每个缩略图文件进行路径映射并将其收集到CSV文件中。


1
你可以使用imagemagick工具进行批量调整大小。
它将保持纵横比。
$ convert dragon.gif    -resize 64x64  resize_dragon.gif

它将不保持纵横比。
$ convert dragon.gif    -resize 64x64\!  exact_dragon.gif

$ cat resize.sh 
#!/bin/bash
for f in `find . -name "*.jpg"`
do
    convert $f -resize 45x60\!  $f.resize.jpg
done

它会将图像调整为45x60,而不在当前目录中保持纵横比。

0

有几个答案,例如:

find . -name "*.jpg" | xargs convert -resize 50%

这样做是行不通的,因为它会像这样扩展列表:

convert -resize 50% a.jpg b.jpg c.jpg

这将把 a.jpg 调整大小为 c-0.jpgb.jpg 调整大小为 c-1.jpg,而让 c.jpg 不变。

因此,您必须为每个匹配执行调整大小命令,并提供输入文件名和输出文件名,类似于以下内容:

find . -name "*.jpg" | xargs -n 1 sh -c 'convert -resize 50% $0 $(echo $0 | sed 's/\.jpg/-th\.jpg/')'

find 的每个匹配项都会被单独传递给调整大小脚本 xargs -n 1sh -c 'convert -resize 50% $0 $(echo $0 | sed 's/\.jpg/-th\.jpg/')'。 该脚本使用参数$0接收文件名,并使用sed通过替换原始的.jpg后缀为-th.jpg来生成输出文件名。 然后,它使用这两个文件名运行convert命令。

以下是不使用xargs而使用find -exec的版本:

find -name '*.jpg' -exec sh -c 'convert -resize 50% $0 $(echo $0 | sed 's/\.jpg/-th\.jpg/')' {} \;

嗯...使用这种方法,您将不得不为每个JPEG创建一个新进程来执行sh,为每个JPEG创建一个新进程来执行sed,并为每个JPEG创建一个新进程来执行convert,如果您有大量图像,这将会很痛苦。我建议使用mogrify,您只需要调用一次它就可以从单个进程处理所有图像,和/或使用GNU Parallel,或者至少使用shell参数替换来计算新文件名,而不是使用sed - Mark Setchell
绝对没错;使用mogrify,你不需要想出一个第二个文件名,所有的复杂性都消失了。 我的观点是,与几个答案中所写的一样,mogrify适用的方法在convert中并不适用。 - loic.jaouen
我的观点是,正如一些回答中所写的那样,mogrifyconvert并不能简单地互换使用。如果您愿意覆盖原始文件,那么mogrify就可以完成所有任务。如果不想这么做,您需要使用convert,这会变得有些混乱。去掉sed很好的建议: find -name '*.jpg' -exec sh -c 'convert -resize 50% $0 "${0%\.jpg}-th.jpg"' {} \; 或者只需在前面加上:"th-${0}"在我看来,我不确定创建进程的成本与图像处理任务相比有多大影响……但我同意;既然没有必要,为什么要创建新的进程呢? - loic.jaouen

0

没有使用XARGS并替换原始文件:

在我与Linux的无知(第一年)苦苦挣扎了很多小时后,我终于找到了最适合我的解决方案:

  • 使用ImageMagick;
  • 不使用XARGS;
  • 替换原始文件;
  • 设置特定的最大宽度和高度,并保持纵横比(以下代码中为700像素);
  • 包含大小写特定变体以避免遗漏;
  • 递归搜索所有子文件夹。

这是终端的代码:

for f in `find . -name "*.jpg" -or -name "*.JPG" -or -name "*.jpeg" -or -name "*.JPEG"` ; do convert "$f" -resize 700 "$f" ; done

希望这对你们有所帮助;无论如何,它已经为我未来的需求保存了下来。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接