stdin(한 줄)에서 읽고 일부 처리(문자열 구문 분석, IO 관련 없음)를 수행하고 stdout으로 출력하는 간단한 Python 스크립트가 있습니다.
e.g. python parse.py < in.txt > out.txt
나는 in.txt
크기가 약 200GB이고 속도를 높이기 위해 병렬을 사용합니다(CPU 코어는 8개입니다).
cat in.txt | parallel -j8 -N1 --pipe python parse.py
내가 관찰한 바에 따르면 CPU는 완전히 활용되지 않고 있습니다.
%Cpu0 : 9.1 us, 22.7 sy, 0.0 ni, 68.2 id, 0.0 wa, 0.0 hi, 0.0 si, 0.0 st
%Cpu1 : 27.3 us, 13.6 sy, 0.0 ni, 59.1 id, 0.0 wa, 0.0 hi, 0.0 si, 0.0 st
%Cpu2 : 14.3 us, 71.4 sy, 0.0 ni, 14.3 id, 0.0 wa, 0.0 hi, 0.0 si, 0.0 st
%Cpu3 : 14.3 us, 28.6 sy, 0.0 ni, 57.1 id, 0.0 wa, 0.0 hi, 0.0 si, 0.0 st
%Cpu4 : 14.3 us, 38.1 sy, 0.0 ni, 47.6 id, 0.0 wa, 0.0 hi, 0.0 si, 0.0 st
%Cpu5 : 4.8 us, 23.8 sy, 0.0 ni, 71.4 id, 0.0 wa, 0.0 hi, 0.0 si, 0.0 st
%Cpu6 : 15.0 us, 20.0 sy, 0.0 ni, 65.0 id, 0.0 wa, 0.0 hi, 0.0 si, 0.0 st
%Cpu7 : 23.8 us, 19.0 sy, 0.0 ni, 57.1 id, 0.0 wa, 0.0 hi, 0.0 si, 0.0 st
그리고
ps ax | grep python
나는 얻었다
12450 ? S 0:00 /bin/bash -c sh -c 'dd bs=1 count=1 of=/tmp/2NQLo8j4qy.chr 2>/dev/null'; test ! -s "/tmp/2NQLo8j4qy.chr" && rm -f "/tmp/2NQLo8j4qy.chr" && exec true; (cat /tmp/2NQLo8j4qy.chr; rm /tmp/2NQLo8j4qy.chr; cat - ) | (python parse.py);
12453 ? S 0:00 /bin/bash -c sh -c 'dd bs=1 count=1 of=/tmp/zYnfr4Ss8H.chr 2>/dev/null'; test ! -s "/tmp/zYnfr4Ss8H.chr" && rm -f "/tmp/zYnfr4Ss8H.chr" && exec true; (cat /tmp/zYnfr4Ss8H.chr; rm /tmp/zYnfr4Ss8H.chr; cat - ) | (python parse.py);
12456 ? S 0:00 /bin/bash -c sh -c 'dd bs=1 count=1 of=/tmp/wlrI14juYz.chr 2>/dev/null'; test ! -s "/tmp/wlrI14juYz.chr" && rm -f "/tmp/wlrI14juYz.chr" && exec true; (cat /tmp/wlrI14juYz.chr; rm /tmp/wlrI14juYz.chr; cat - ) | (python parse.py);
12459 ? S 0:00 /bin/bash -c sh -c 'dd bs=1 count=1 of=/tmp/cyArLNBTTm.chr 2>/dev/null'; test ! -s "/tmp/cyArLNBTTm.chr" && rm -f "/tmp/cyArLNBTTm.chr" && exec true; (cat /tmp/cyArLNBTTm.chr; rm /tmp/cyArLNBTTm.chr; cat - ) | (python parse.py);
12461 pts/0 S+ 0:00 grep --color=auto python
15211 ? S 144:22 perl /usr/bin/parallel -j8 -N1 --pipe python parse.py
실행할 때마다 ps ax | grep python
다른 임시 파일이 생성됩니다. 이러한 임시 파일을 처리하는 데 CPU가 낭비된다고 가정합니까? 아니면 내가 뭔가 잘못하고 있는 걸까요?
답변1
Mark의 답변은 정확하고 완벽하게 지원되지만 새로운 기능을 사용해 보고 싶을 수도 있습니다.
cat file | parallel --pipe ...
최대 속도는 약 100MB/s입니다.
새로운 실험적 옵션 --pipepart는 > 2GB/s를 제공하지만 in.txt가 실제(검색 가능한) 파일이어야 합니다.
parallel -a in.txt --block 100M --pipepart python parse.py
답변2
이로 -N1
인해 한 줄에 하나의 프로세스가 생성됩니다. 병렬 설정의 오버헤드가 표시됩니다. 두 개 이상의 라인을 처리하려면 Python 스크립트를 변경해야 합니다. 그런 다음 cat in.txt | parallel --pipe python parse.py
CPU를 최대한 활용해야 합니다.