이 bash 스크립트를 어떻게 병렬로 실행할 수 있나요?

이 bash 스크립트를 어떻게 병렬로 실행할 수 있나요?

더 효율적이려면 이것이 필요합니다

현재 라인에 따라 최대 20시간이 소요됩니다(상당히 큰 MCS 데이터 세트임).

  • 빅데이터 파일을 "샷"으로 분할
  • for 루프에 사용할 각 렌즈 이름 목록을 만듭니다.
  • 각 샷을 반복하고 동일한 프로세스를 수행합니다.
  • 이전과 동일한 행을 가지지만 처리되도록 각 샷을 새 데이터 파일에 추가합니다. 이 경우 데이터를 반복적으로 필터링하므로 병렬로 실행할 수 있다고 생각했습니다.

모든 SU 명령과 for 루프의 모든 내용을 무시할 수 있습니다. 병렬로 실행하는 방법만 알면 됩니다(예: 32개 노드). 이것은 나에게 비교적 새로운 주제이므로 심층적인 설명을 해 주시면 감사하겠습니다!

스크립트:

#! /bin/bash    
# Split the input file into one file for each shot. NB mustclose each o/p file at the earliest opportunity otherwise it will crash!
susplit <$1 key=fldr stem=fldr_ verbose=1 close=1

# Create a list of shot files
ls fldr* > LIST

# Loop over each shot file; suppress direct wave; write to new concatenated output file
for i in `cat LIST`; do
    echo $i
    suchw key1=tstat key2=tstat a=200 < $i | suwind key=tracf min=10 max=400 tmin=0 tmax=6 | suweight a=0 | suresamp rf=4 | sustatic hdrs=1 sign=-1 | sureduce rv=1.52 | sumedian median=1 xshift=0 tshift=0 nmed=41 | suflip flip=3 | sureduce rv=1.52 | suflip flip=3 | suresamp rf=0.25 | suweight inv=1 a=0 | sustatic hdrs=1 sign=1 >> $2
done

# Tidy up files by removing single shot gathers and LIST
rm -f fldr* LIST &

답변1

나는 이것이 for병렬화하려는 루프라고 가정합니다.

#! /bin/bash    
# Split the input file into one file for each shot. NB mustclose each o/p file at the earliest opportunity otherwise it will crash!
susplit <$1 key=fldr stem=fldr_ verbose=1 close=1

sucit() {
    i=$1
    echo $i
    suchw key1=tstat key2=tstat a=200 < $i | suwind key=tracf min=10 max=400 tmin=0 tmax=6 | suweight a=0 | suresamp rf=4 | sustatic hdrs=1 sign=-1 | sureduce rv=1.52 | sumedian median=1 xshift=0 tshift=0 nmed=41 | suflip flip=3 | sureduce rv=1.52 | suflip flip=3 | suresamp rf=0.25 | suweight inv=1 a=0 | sustatic hdrs=1 sign=1
}
export -f sucit

parallel sucit ::: fldr* > $2

# Tidy up files by removing single shot gathers and LIST
rm -f fldr* LIST &

상황에 따라 susplit더 빠르게 처리할 수 있습니다. "large_data_file"의 샷이 다음으로 시작 <shot>\n하고 끝나는 경우 </shot>\n:

sucpipe() {
    suchw key1=tstat key2=tstat a=200 | suwind key=tracf min=10 max=400 tmin=0 tmax=6 | suweight a=0 | suresamp rf=4 | sustatic hdrs=1 sign=-1 | sureduce rv=1.52 | sumedian median=1 xshift=0 tshift=0 nmed=41 | suflip flip=3 | sureduce rv=1.52 | suflip flip=3 | suresamp rf=0.25 | suweight inv=1 a=0 | sustatic hdrs=1 sign=1
}
export -f sucpipe

parallel --block -1 --recstart '<shot>\n' --recend '</shot>\n' --pipepart -a $1 sucpipe > $2

대용량 파일을 n개의 청크로 분할하려고 시도합니다. 여기서 n은 코어 수입니다. 분할은 즉시 수행되므로 임시 파일이 먼저 기록되지 않습니다. 그런 다음 GNU Parallel은 각 청크를 sucpipe에 전달합니다.

대용량 파일이 바이너리(즉, 텍스트가 아님)이고 헤더가 3200바이트이고 레코드 길이가 1000바이트인 경우 다음이 작동할 수 있습니다.

parallel -a bigfile  --pipepart --recend '' --block 1000 --header '.{3200}' ...

자세한 내용은 이 튜토리얼을 확인하세요. man parallel_tutorial명령줄이 도움이 될 것입니다.

관련 정보