체인의 여러 다운스트림 프로세스에 표준 출력 보내기

체인의 여러 다운스트림 프로세스에 표준 출력 보내기

다음과 같이 실행되는 일련의 명령이 있습니다.

cmd1 < input > foo
cmd2 < foo > bar
cmd3 foo bar > output

중간 파일 없이 foo이를 수행할 수 있는 방법이 있습니까 bar?

또한 이 작업을 두 번 실행하는 것을 피하고 싶습니다 cmd1.

cmd3 <(cmd1 < input) <(cmd1 < input | cmd2) > output

3가지 명령을 모두 실행하는 데 몇 시간이 걸릴 수 있으며 파일 크기는 1GB~100GB(생물정보학)입니다.

다음은 인위적이지만 실행 가능한 예입니다.

function cmd1 { sed -r 's/[246]/x/g'; }
function cmd2 { sed -r 's/[135]/-/g'; }
function cmd3 { paste $1 $2; }
seq 10 > input
cmd3 <(cmd1 < input) <(cmd1 < input | cmd2)  # cmd1 runs twice

산출

1       -
x       x
3       -
x       x
5       -
x       x
7       7
8       8
9       9
10      -0

이것이 도움이 될지는 확실하지 않지만 데이터가 다음과 같이 흐르기를 원합니다.

input --> cmd1 ---> cmd2  -->|
                |            |--> cmd3  --> output
                ------------>|

https://unix.stackexchange.com/a/43536가깝지만 충분하지는 않습니다.

답변1

이런 일이 가능합니까?

rm -f fifo
mkfifo fifo

cmd1 <input | tee fifo | cmd2 | cmd3 fifo /dev/stdin >output

그러면 이름이 지정된 파이프가 생성됩니다 fifo. 첫 번째 명령은 명명된 파이프에 쓰기를 사용하고 두 번째 명령은 표준 입력을 사용합니다 tee. 세 번째 명령은 명명된 파이프와 표준 입력에서 읽습니다.

디스크에는 중간 데이터가 저장되지 않지만 cmd3파이프 버퍼가 가득 찰 때까지 명명된 파이프에서 소비가 이루어지지 않거나 cmd2소비하는 데이터 양에 비해 생성되는 데이터가 매우 적은 경우 파이프가 교착 상태에 빠질 수 있습니다(및 , 대부분 중요한 것은 cmd3파이프 버퍼가 가득 찰 때까지 충분한 소비를 생성하지 않는다는 것입니다 . fifo당신은 할 수가능한작성자 사이트 (또는 그 변형) 에서 pv사용되는 명명된 파이프의 데이터 버퍼링과 같은 방법을 사용하여 이 문제를 해결하십시오.cmd3 <( pv --quiet <fifo ) /dev/stdintee >( pv --quiet >fifo )

관련 정보