나는 입력을 여러 가지 방식으로 병렬로 처리하여 입력되는 결과 줄을 작성하려고 합니다. 현재 접근 방식은 다음과 같습니다.
# process_parallel.sh
read input
parallel --colsep ' ' --linebuffer 'echo $input | {}' \
::: 'python process1.py' ./process2.sh ./process3
컨텍스트는 다음과 같이 요약됩니다.
(sleep 1; echo "short input arriving late") | ./process_parallel.sh | ./collate_results.sh
위의 방법은 작동하지만 한 가지 중요한 단점이 있습니다. 입력을 읽을 때까지 프로세스가 시작되지 않습니다. 시간이 좀 걸릴 수 있으므로 즉시 시작하고 싶습니다. 그런 다음 전체 표준 입력을 병렬 파이프로 각각에 연결하도록 합니다.
어떻게 이를 달성할 수 있나요?
답변1
실행할 데이터가 없으면 새 작업을 시작하지 않도록 GNU Parallel에 상당한 작업이 추가되었습니다. 이는 입력을 받지 못하는 일부 프로그램이 제대로 작동하지 않기 때문입니다. 따라서 당신은 GNU Parallel의 디자인에 반대하는 작업을 하게 될 것입니다.
입력을 복제하려면 tee
대체를 사용하고 처리할 수 있습니다.
cat namedpipe_or_file | tee >(process1) >(process2) >(process3) >/dev/null
process1
, process2
및 즉시 시작됩니다 process3
. 그러나 출력이 혼합될 수 있으므로 출력을 사용해야 하는 경우 다른 파일로 리디렉션해야 합니다.
cat namedpipe_or_file | tee >(process1 > out1) >(process2 > out2) >(process3 > out3) >/dev/null
답변2
두 개의 래퍼 스크립트가 있습니다. 먼저 각 프로세스가 세 개의 파일(예: file1, file2, file3)에서 입력을 읽도록 지시하도록 process_parallel.sh를 수정합니다.
이제 다음과 같이 표준 입력을 세 개의 파일에 병렬로 보내는 두 번째 래퍼 스크립트를 작성합니다.
#!/bins/bash
#parallelise input
# let's call this file parallelise
parallel -j 3 -- "echo $1 > file1" "echo $1 > file2" "echo $1 file3"
이제 다음과 같이 작업을 시작합니다.
./process_parallel_sh; cat InputFile | parallelise;
답변3
Parallel에는 --tee
다음과 같이 사용할 수 있는 옵션이 있습니다.
(sleep 1; echo "short input arriving late") |\
parallel --colsep ' ' --linebuffer --pipe --tee ::: 'python process1.py' ./process2.sh ./process3 |\
./collate_results.sh