这是一个更通用的问题方法。
ImageMagick 提供了一些巧妙的技巧,可以帮助优化处理速度......
- ...您要处理大图像和
- ...当您想从同一个原件创建不同的输出时。
甚至可以组合不同的方法:
- 利用 ImageMagick 的特殊
mpr:{label} 格式和语法。
这告诉 ImageMagick 将输入图像临时保存到一个命名的 magick 程序寄存器 标签中。
(我也看到它被解释为 magick persistent (memory) register 或 memory program register。)
然后,命令管道可以稍后(在处理时)从那里读取图像数据,这比从硬盘读取的速度要快得多。
该命令可以根据需要多次读取它。
- 利用 ImageMagick 的特殊
mpc:{name} 格式和语法。
这类似于mpr:。
它的全名是magick pixel cache。
我也将其视为magick 持久(磁盘)缓存。
MPC 是 ImageMagick 的原生 in-memory 未压缩文件格式,但转储到磁盘。
写入磁盘后,它可以比 JPEG、TIFF 或 PNG 更快地重新读入内存,因为不需要转换。
- 构建一个巧妙的命令序列。
利用“横向”处理,在适当的情况下使用转义括号中的
\( ... \) 语法。
MPC
当convert 命令读取输入图像(JPEG、TIFF、GIF、PNG...任何当前格式)时,它首先将此格式处理为 MPC。
此处理后的结果以未压缩的光栅格式保存在 RAM 中。
从那里发生进一步的转换和图像处理。
当您想将 MPC作为 MPC 写入磁盘时,您可以使用 +write mpc:myfilename。
这基本上只是直接将内存转储到磁盘。
ImageMagick 然后写入两个,而不是一个,(并且比平常大)二进制文件:myfilename.mpc 和 myfilename.cache。
.mpc 文件保存图像的元数据,.cache 保存实际像素缓存数据。
从此磁盘文件中读取是根据需要从磁盘到内存的快速内存映射(类似于内存页面交换)。
但由于最初的+write 操作确实存储了原生未压缩的内部、IM 原生光栅格式,因此现在不需要图像解码。
所以这可以更快地使用(特别是对于大图像),如果你不能避免写出你需要再次读入的临时文件。
但是,请注意您的磁盘空间。
记住清理,一旦您不再需要磁盘上的 MPC 文件。
IM 不会自动为您跟踪您的+write 命令。
(更多技术细节:MPC 作为磁盘文件格式不可移植。
它也不适合作为长期存档格式。
它唯一的适用性是作为高性能图像处理的中间格式。
它需要 两个 文件来支持 一个 图像。
它不能保证在 ImageMagick 版本之间是“稳定的”。
它可能无法在与您创建它的机器不同的机器上运行。)
如果您仍想将此格式保存到磁盘,请记住:
- 图像属性被写入扩展名为.mpc的文件中。
- 图像像素被写入扩展名为.cache的文件中。
MPC 的主要优势在于...
- ...处理非常大的图像,或者当
- ...在“操作管道”中对同一图像应用多个操作。
MPC 专为符合条件“多次读取,一次写入”的工作流模式而设计。
MPR
MPR 格式(内存持久寄存器)的作用类似于 MPC。
它通过命名的内存寄存器使图像可用。
您可以使用任何您想要的名称(偶数)。
您的流程管道还可以从该寄存器再次读取图像 - 如果需要,甚至可以多次读取。
图像mpr:label 保留在寄存器中,直到当前命令管道退出。 (这与写入磁盘的mpc:filename 不同。这会持续完成当前管道;它甚至可以在系统重新启动后继续存在。)
聪明的命令管道
(我在这里使用的“管道”一词不要与 shell 中的管道混淆,其中启动并链接了多个命令和进程。
这里我只讨论convert 的单个调用,它将多个图像操作和操作链接到一个进程中。)
因此可以在一个过程中完成所有调整大小、裁剪、追加、缩略图、颜色处理、模糊等操作,写出您需要的不同中间输出。
实际例子...
...嗯,我不太确定它是否soooo 实用。我没有测试过,我只是用我的幻想构建了一个例子,展示了不同概念的使用原理。
注意:+write someimage 与 -write someimage +delete 相同。
convert \
very-very-large.jpg \
-write mpr:XY \
+delete \
-respect-parentheses \
\( mpr:XY -crop '3000x2001+0+491' -resize '170x116!>' +write pic1.png \) \
\( mpr:XY -crop '2981x2883+8+0' -resize '75x75!>' +write pic2.png \) \
\( mpr:XY -crop '1100x1983+0+0' -resize '160x160!>' +write pic3.png \) \
\( mpr:XY -crop '2000x2883+0+0' -resize '1024x960!>' +write pic4.png \) \
\( mpr:XY -crop '1000x2883+0+0' -resize '190x188!>' +write mpr:pic5 \) \
\( mpr:pic5 +write pic5.png \) \
\( mpr:XY -crop '3000x2000+0+0' -resize '2048x2047!>' +write pic6.png \) \
\( mpr:XY -crop '3000x2883+0+0' -resize '595x421!>' +write pic7.png \) \
\( mpr:XY -crop '3000x2883+0+0' -resize '3000x2883!>' +write mpr:AB \) \
\( mpr:AB +write pic8.tiff \) \
\( mpr:AB -blur 0x8 +write blur1.gif \) \
\( mpr:pic5 mpr:AB +append mpr:pic5 -append +write append.jpg \) \
\( mpr:pic5 -rotate -130 mpr:AB -gravity center \
-compose difference -composite +write final.png \) \
null:
第一次操作-write mpr:XY后,栈中有两张图片:
- 输入文件
very-very-large.png,和
- 它的一个副本,可以使用标签
XY从内存中读取。
我们不再需要这两个中的第一个。
因此我们使用+delete 将其从堆栈中删除。
因此,此命令使用一个命令管道,该管道执行多个命令和操作,一次创建 11 个不同的输出图像:
pic{1,2,3,4,5,6,7}.png、blur1.gif、pic8.tiff、append.jpg 和 final.png。