만약 현 디렉토리에 있는 수천개 이상의 파일을 전부 압축해야 한다고 가정하자. gzip *이라고 타이프하면 십중팔구는 인수가 너무 많아서 실행을 하지 못한다는 에러 메시지가 나올 것이다. 그러나 Parallel이 설치되었다면 다음과 같이 하면 된다.
$ parallel gzip ::: *Shell은 *를 확장하여 파일로 만들고, 이를 gzip 명령어에 공급하되 여러 core에서 병렬 작업이 일어나게 한다. 물론 이는 대단히 간단한 사례이다. 입력 파일을 분할하여(기본 가정은 ㄱ각각의 라인이 별도의 레코드라는 것이나, separator를 지정할 수 있다) 각각에 대한 동시 작업을 수행하고, 이를 합치는 것이 가장 전형적인 사례이다. 분할된 입력 파일은 명령어에게 표준 입력으로 전송되게 함으로써 매우 단순한 작업 지시를 할 수 있다. Biostars에 매우 훌륭한 설명 자료가 있다(Parallelize serial command line programs without changing them). 이 자료에서 설명한 사례를 하나 인용해 보겠다. 1GB나 되는 대용량의 fasta file에 대한 blast 검색을 하고 싶다면?
$ cat 1gb.fasta | parallel --block 100k --recstart '>' --pipe blastp -evalue 0.01 -outfmt 6 -db db.fa -query - > results입력 파일을 100 KB 단위로 자르되 각 레코드는 '>'로 시작하니 미련하게 query sequence 중간을 자르지 못하게 하고, 이를 blastp에 넘겨서 서열 검색을 한 뒤 최종적으로는 results 파일로 합친다. 잘려진 각 데이터에 대한 검색 결과까지 순서대로 저장되는 것은 아니니, 입력물의 순서를 그대로 유지해야 한다면 약간의 변형된 방법이 필요하다.
다음으로는 FASTX toolkit에 들어있는 fastq_to_fastq(-Q33)을 그냥 실행한 것과 GNU parallel을 거쳐서 실행한 것의 소요시간 차이를 비교해 보았다. 중간에 top을 쳐 보면 12개의 job이 동시에 돌아간 것으로 나온다. 블록 사이즈나 jop 수는 따로 지정하지 않았다. 먼저 그냥 실행한 것. 입력한 fastq 파일의 크기는 5.3 GB였다.
real 3m19.405s
user 3m14.986s
sys 0m8.562s
real 1m6.266s
user 5m40.297s
sys 1m22.576s
유용한 자료 링크를 몇가지 더 소개한다.
- GNU Parallel tutorial (from official website)
- 짤막한 소개 자료
- [PDF] GNU Parallel: The Command-Line Power Tool
- Parallelising jobs with GNU Parallel(2022년 6월 30일 추가)
댓글 없음:
댓글 쓰기