不同的CPU核心上有不同的屏幕吗?

不同的CPU核心上有不同的屏幕吗?

我正在连接到具有多个 CPU 的 (osX) 服务器。我想为许多不同的输入文件运行我的程序。现在,我一一运行:

for input in "${inputs[@]}"
do
    .<my-program.sh> --input $input
done

这非常慢并且没有使用全部 CPU 能力,所以我想改为并行运行。

我想打开一个新的独立屏幕并在其中运行我的程序,例如:

for input in "${inputs[@]}"
do
    screen -S test -X screen .<my-program.sh> --input $input
done

每个屏幕是否会在不同的 CPU 上工作(我想使用可用的 CPU 功率)并且命令是否正确?或者我应该为每个输入打开一个新的外壳(我认为它肯定在不同的CPU上运行)?

答案1

为了直接回答你的问题,除非你使用 CPU pinning 手动将特定进程分配给特定 CPU,否则你的操作系统通常会安排任务在它认为当时处理它的“最佳”CPU 上运行,而且它是任务甚至可能在多个 CPU 核心之间来回移动,具体取决于机器同时执行的其他操作。

这样做的实际结果是,如果您运行程序的五个实例,它们可能在五个独立的 CPU 上运行,但不能保证它们将要在单独的 CPU 上运行。如果每个单独的进程使用的 CPU 容量低于 20%,则甚至有可能(尽管不太可能)所有五个进程都在同一处理器上运行。

为了解决您更广泛的情况,如果您有一个处理多个文件并且仅使用少量 CPU 能力的程序,那么您的瓶颈很可能是磁盘 I/O 容量。如果是这种情况,加快速度将需要更快的磁盘(或更大的磁盘缓存,如果您重复读取相同的数据),并且跨多个进程和 CPU 并行化它实际上可能减少通过强制磁盘花时间在读取第一个实例的输入文件和读取每个其他进程的其他文件之间切换来提高性能。

测试是否受到磁盘 I/O 瓶颈的快速而简单的方法是cat file_1 file_2 file_3... >/dev/nullfile_1其中 等是程序处理的所有文件的列表)并比较读取文件所需的时间(不执行任何处理)到处理它们所需的时间。

答案2

每当您运行多个进程时,它们可能会在不同的内核上运行。即使单个进程每秒也可以从一个核心迁移到另一个核心多次。这也适用于进程内的各个线程。内核将始终尝试并行运行尽可能多的线程。例如,如果您有 4 个核心,并且当前有 3 个线程需要 CPU 时间,则 3 个核心将很忙。如果 6 个线程需要 CPU 时间,则所有 4 个核心都将繁忙,并且 2 个线程将等待轮到它们。

从不同的 shell 或不同的屏幕窗口启动程序不会影响程序的调度方式。导致程序在第二个片段中并行运行的原因是每次调用都会screen启动一个实例myprogram.sh并且不会等待它终止。您可以在不涉及 screen 的情况下执行相同的操作,只需使用&shell 中的运算符在后台运行程序,即启动程序并立即移动到脚本中的下一条指令,而无需等待程序结束。

for input in "${inputs[@]}"
do
  .<my-program.sh> --input "$input" &
done

同时开始所有跑步不一定是最快的方法。这取决于您的程序使用哪些资源。如果程序使用 CPU 时间并且不执行太多输入/输出,那么您可以通过运行与内核数量一样多的实例来获得最佳结果。如果程序使用大量内存,则仅运行内存适合的实例;如果机器必须交换或者没有足够的磁盘缓存空间,那么它的运行速度会慢很多。如果程序是 I/O 密集型,那么请确保不会使作为瓶颈的 I/O 带宽(网络、磁盘……)饱和。

有一些工具可以帮助并行运行一定数量的程序实例。您可以使用xargs

printf '%s\000' "${inputs[@]}" | xargs -0 -L 1 -P 4 myprogram.sh 

make也可以并行运行程序。调用以下文件Makefile(用制表符替换行开头的 8 个空格):

all = $(patsubst %.in,%.out,$(wildcard *.in))
%.out: %.in
        myprogram.sh --input $< --output $@

Run对所有文件make -j4 all运行并生成相应的文件,最多并行运行 4 个实例。myprogram.sh.in.out

对于更复杂的场景,您可能需要安装GNU并行

相关内容