2012-01-20 3 views
3

설정 : 내가 몇 백 파일, input0.dat, input1.dat 같은 이름이 뭔가를 가지고bash는 : 청크 파일의 프로세스 목록

는 ..., input150.dat, 나는 몇 가지 명령 cmd를 (사용하여 처리해야하는 어떤 기본적으로 모든 파일의 내용을 병합합니다. cmd는 모든 입력 파일 이름의 목록 첫 번째 옵션으로 다음 출력 파일 이름 및 소요 :

./cmd output.dat input1.dat input2.dat [...] input150.dat 

문제 :

문제는 스크립트가 10 개 파일 정도 인한처럼 처리 할 수 ​​있다는 것입니다 메모리 문제 (저를 비난하지 마십시오). 따라서, 대신

./cmd output.dat *dat 

처럼 bash 와일드 카드 확장을 사용하는 나는 그 후 나는 임시 출력을 병합 할 수 있습니다

./cmd temp_output0.dat file0.dat file1.dat [...] file9.dat 
[...] 
./cmd temp_outputN.dat fileN0.dat fileN1.dat [...] fileN9.dat 

같은 것을 할 필요가있다.

./cmd output.dat output0.dat [...] outputN.dat 

어떻게 스크립트이 효율적으로 bash에서합니까?

나는 성공했으나 시도하지 못했습니다.

for filename in `echo *dat | xargs -n 3`; do [...]; done 

문제는 xargs의 출력 선이 연결된 얻을 수 있기 때문에이 다시 한 번에 모든 파일을 처리하는 것입니다.

편집 :cmd을 호출 할 때 첫 번째 명령 줄 인수로 출력 파일 이름을 지정해야합니다.

답변

3

당신은 할 수 있습니다 :

i=0 
opfiles= 
mkfifo /tmp/foo 
echo *dat | xargs -n 3 >/tmp/foo& 
while read threefiles; do 
    ./cmd tmp_output$i.dat $threefiles 
    opfiles="$opfiles tmp_output$i.dat" 
    ((i++)) 
done </tmp/foo 
rm -f /tmp/foo 
wait 
./cmd output.dat $opfiles 
rm $opfiles 

당신은뿐만 아니라 파일 세트 최종 연결 들어, i 변수 값을 유지하기 위해 FIFO를 사용해야합니다.당신이 할 수있는, 당신은 완전히 FIFO를 사용하지 않도록하려면

i=0 
opfiles= 
mkfifo /tmp/foo 
echo *dat | xargs -n 3 >/tmp/foo& 
while read threefiles; do 
    ./cmd tmp_output$i.dat $threefiles& 
    opfiles="$opfiles tmp_output$i.dat" 
    ((i++)) 
done </tmp/foo 
rm -f /tmp/foo 
wait 
./cmd output.dat $opfiles 
rm $opfiles 

갱신 :

당신은 당신이 배경 수 ./cmd의 내부 호출이, cmd를의 마지막 호출하기 전에 wait을 넣어하려는 경우

i=0 
opfiles=() 
while read threefiles; do 
    ./cmd tmp_output$i.dat $threefiles 
    opfiles+=("tmp_output$i.dat") 
    ((i++)) 
done < <(echo *dat | xargs -n 3) 
./cmd output.dat "${opfiles[@]}" 
rm "${opfiles[@]}" 

다시 잠시로 배관을 피할 수 있지만, 재로부터 판독하는 단계는 k : 않도록 제를 재기록을 에뮬레이션 프로세스 교체를 사용 while 루프 다음에 opfiles 변수를 eep하십시오.

+0

예! 그게 내가 찾고 있었던거야. 감사. – fuenfundachtzig

+0

이것은 실제로 필요한 것보다 훨씬 복잡합니다. 임시 파일을 피할 수 있습니다.'xargs '를'while read'로 파이프하면됩니다. 백그라운드 처리가 좋을 수도 있지만, 작업량이 얼마나되는지 등에 따라 불필요하게 복잡한 작업을 수행 할 수도 있습니다. – tripleee

2

가 다음을 시도, 그것은 당신을 위해 일해야합니다

echo *dat | xargs -n3 ./cmd output.dat 

편집 : 대응 댓글에 :

for i in {0..9}; do 
    echo file${i}*.dat | xargs -n3 ./cmd output${i}.dat 
done 

./cmd에 한 번에 세 개 이상의 파일을 보낼 수 없을 것입니다 즉, file00.dat에서 file99.dat까지의 모든 파일을 검토하고 10 개의 다른 출력 파일이있는 경우 output1.dat에서 output9.dat까지

+0

나는 당신을 위해 일할 수 있다고 생각하는 것을 추가했습니다. 그게 당신이 의미 한 것입니까? – spatz

+0

실제로 입력 파일마다 동일한 출력 이름을 여러 번 사용하기 때문에 실제로는 올바르게 작동하지 않습니다. – fuenfundachtzig