如何在Bash中并行处理10000个文件的codeml任务?
针对10000个codeml任务的最优并行方案
本地机器快速并行(GNU Parallel)
如果是在单台多核机器上运行,用GNU Parallel是最简便的方案,自动适配CPU资源:
- 先确认可用CPU核心数:
nproc - 并行执行命令(默认每个任务用1核,同时运行任务数等于核心数):
parallel --jobs $(nproc) /N/project/tomWGS/OVULERNASEQ/scripts/moEvoScripts/Programs/paml/bin/codeml {} ::: *.ctl - 进阶优化:
- 若codeml部分模型支持多线程,可给每个任务分配多核心(比如每个任务用2核,同时运行任务数减半):
parallel --jobs $(( $(nproc)/2 )) --env OMP_NUM_THREADS=2 /N/project/tomWGS/OVULERNASEQ/scripts/moEvoScripts/Programs/paml/bin/codeml {} ::: *.ctl - 务必在每个
.ctl文件中指定唯一outfile(比如outfile = {}.txt),避免输出文件冲突覆盖。
- 若codeml部分模型支持多线程,可给每个任务分配多核心(比如每个任务用2核,同时运行任务数减半):
HPC集群并行(SLURM调度器)
如果是在集群环境,优先用数组任务来高效管理大量独立任务:
数组任务提交脚本(推荐)
创建codeml_array.sh脚本:
#!/bin/bash #SBATCH --job-name=codeml_batch #SBATCH --output=codeml_%A_%a.out #SBATCH --error=codeml_%A_%a.err #SBATCH --nodes=1 #SBATCH --ntasks-per-node=1 #SBATCH --cpus-per-task=1 # 单个codeml任务的CPU数,按需调整 #SBATCH --mem=1G # 单个任务的内存分配,先测试再调整 #SBATCH --time=01:00:00 # 单个任务的最大运行时长,按需延长 #SBATCH --array=1-10000%50 # 总任务数10000,同时运行50个(根据集群队列容量调整) # 获取当前任务对应的ctl文件 FILES=(*.ctl) CURRENT_FILE=${FILES[$SLURM_ARRAY_TASK_ID-1]} # 执行codeml /N/project/tomWGS/OVULERNASEQ/scripts/moEvoScripts/Programs/paml/bin/codeml "$CURRENT_FILE"
提交命令:
sbatch codeml_array.sh
- 关键参数调整:
--array=1-10000%N中的N是同时运行的任务数,需根据集群允许的并发任务数设置(比如集群限100并发就设为100)。
批量单个任务提交(备选)
若需给不同任务配置差异化资源,可循环生成单个任务脚本并提交:
for file in *.ctl; do cat > submit_${file%.ctl}.sh << EOF #!/bin/bash #SBATCH --job-name=codeml_${file%.ctl} #SBATCH --output=${file%.ctl}.out #SBATCH --error=${file%.ctl}.err #SBATCH --nodes=1 #SBATCH --ntasks-per-node=1 #SBATCH --cpus-per-task=1 #SBATCH --mem=1G #SBATCH --time=01:00:00 /N/project/tomWGS/OVULERNASEQ/scripts/moEvoScripts/Programs/paml/bin/codeml "$file" EOF sbatch submit_${file%.ctl}.sh done
注意:此方法会生成大量脚本,集群可能限制批量提交数量,建议分批次执行。
通用优化要点
- 先做小范围测试:拿10个任务测试单个任务的CPU、内存消耗和运行时间,再调整全局配置,避免资源浪费或不足。
- 输出文件隔离:确保每个
.ctl文件的outfile参数唯一,防止多任务覆盖输出。 - 故障恢复:用
parallel --resume或SLURM数组任务的重跑功能,快速处理失败的任务。
内容的提问来源于stack exchange,提问作者tbiewerh
相关产品推荐
相关产品推荐

