为 for 循环创建主进程

问题描述

这个程序返回视频的分辨率,但由于我需要一个大型项目,我需要多处理。我曾尝试使用不同的函数进行并行处理,但这只会多次运行它,并不能提高效率,我正在发布整个代码。你能帮我创建一个包含所有内核的主进程吗。

import os
from tkinter.filedialog import askdirectory
from moviepy.editor import VideoFileClip


if __name__ == "__main__":
    dire = askdirectory()
    d = dire[:]
    print(dire)
    death = os.listdir(dire)
    print(death)
    for i in death: #multiprocess this loop
        dire = d
        dire += f"/{i}"
        v = VideoFileClip(dire)
        print(f"{i}: {v.size}")

代码工作正常,但我需要帮助为单独的 for 循环创建主进程(使用所有内核)。你能原谅我对多处理生气的变量名称吗?此外,如果您有提高代码效率的技巧,我将不胜感激。

解决方法

您是,我想,假设目录中的每个文件都是视频剪辑。我假设处理视频剪辑是一个适合线程的 I/O 绑定“进程”。在这里,我以这种方式随意创建了一个 20 个线程的线程池:

MAX_WORKERS = 20 # never more than this
N_WORKERS = min(MAX_WORKERS,len(death))

在性能下降之前,您必须试验 MAX_WORKERS 的大小。这可能是一个较低的数字,不是因为您的系统不能支持大量线程,而是因为对磁盘上可能分布在介质上的多个文件的并发访问可能效率低下。

import os
from tkinter.filedialog import askdirectory
from moviepy.editor import VideoFileClip
from concurrent.futures import ThreadPoolExecutor as Executor
from functools import partial


def process_video(parent_dir,file):
    v = VideoFileClip(f"{parent_dir}/{file}")
    print(f"{file}: {v.size}")


if __name__ == "__main__":
    dire = askdirectory()
    print(dire)
    death = os.listdir(dire)
    print(death)
    worker = partial(process_video,dire)
    MAX_WORKERS = 20 # never more than this
    N_WORKERS = min(MAX_WORKERS,len(death))
    with Executor(max_workers=N_WORKERS) as executor:
        results = executor.map(worker,death) # results is a list: [None,None,...]

更新

根据@Reishin,moviepy 导致执行 ffmpeg 可执行文件,从而最终创建一个正在完成工作的进程。所以我们在这里也没有必要使用多处理。

相关问答

Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其...
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。...
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbc...