我在 PyQt5 中编写了一个应用程序/Gui,并且想要存储大图像(>5000 个 RGB 图像)
现在,我有一个函数,它用cv2.imwrite存储每张图片,但是这个过程需要很多时间。所以我在 Stackoverflow 上读到,我可以通过多处理来做到这一点。但我对 python 很陌生。
我的多处理代码:
def SaveImages(self):
jobs = []
for i in range(5):
p = multiprocessing.Process(target = self.SaveAllImages, args=self)
jobs.append(p)
p.start()
在函数 SaveAllImages 中,是存储每帧图像的基本代码。如果我运行此代码 - 出现错误:
p = multiprocessing.Process(target = SaveAllImages, args=self)
NameError: name 'SaveAllImages' is not defined
但 SaveAllImages 已定义:def SaveAllImages(self)
所以我的问题是:
为什么我会出现这个错误
如何实现非常简单的多重处理来存储图像
最佳答案
您看到的错误是因为您调用了一个不存在的方法,可能是因为它不是 self
的一部分。
您可能会看到多线程比多处理更好的性能。多处理最适合 CPU 密集型任务,原因很简单,Python 对所有操作都使用全局锁。多处理是绕过这个锁的一种技巧。它比线程更麻烦,除非绝对必要,否则最好避免使用它。
多线程可能足以满足您的用例,并且不会给新程序员带来很多麻烦。这是使用 Python 3 的 Futures API 的工作示例设置这将轻松扩展您的问题规模,只需在标记的位置添加您的参数和实际保存代码即可。
import concurrent.futures
# Save single image
def save_image(image_arg):
# your image save code goes here
print("Working on image {}...".format(image_arg))
return True
# max_workers specifies the number of threads. If None then use 5x your CPU count
with concurrent.futures.ThreadPoolExecutor(max_workers=None) as executor:
# Images we'll save. Depending on how you generate your images you might not
# want to materialize a list like this to avoid running out of memory.
image_args = ["image1", "image2", "image3"]
# Submit futures to the executor pool.
# Map each future back to the arguments used to create that future. That way
# if one fails we know which image it was that failed.
future_to_args = {executor.submit(save_image, image_arg): image_arg for image_arg in image_args}
# Images are being saved in worker threads. They will complete in any order.
for future in concurrent.futures.as_completed(future_to_args):
image_arg = future_to_args[future]
try:
result = future.result()
except Exception as exc:
print("Saving image {} generated an exception: {}".format(image_arg, exc))
else:
print("Image {} saved successfully.".format(image_arg))
如果您坚持多处理,只需使用ProcessPoolExecutor
即可。如果您还想并行生成图像,这可能是值得的。
ThreadPoolExecutor
还是 ProcessPoolExecutor
哪个更好,很大程度上取决于您的其余工作负载是什么以及您如何构建它。两者都尝试一下,看看哪种更适合您。请注意,多处理对工作人员之间的通信和共享状态施加了限制,因此我建议首先尝试线程。
关于python - 使用多重处理来存储大图像,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/57632036/