2013-02-05 10 views
7

Say Ho tre programmi: generatore, che produce dati di ingresso alimentati al processore e verificatore che può verificare se il processore l'output è corretto per input dato (quindi ha bisogno di entrambi i file).Duplicate stdout, pipe a due comandi differenti, raccogliere risultati sia per stdin del programma finale

Quello che attualmente faccio è:

generatore> in.txt & & processore < in.txt> out.txt & & cat in.txt out.txt | verificatore

È possibile ottenere lo stesso risultato senza utilizzare file espliciti? Ho letto di duplicare gli input usando Tee e la sostituzione dei processi, ma non ho trovato un modo per raccogliere entrambi i flussi in uno solo per il passaggio finale.

risposta

1

Se è possibile modificare il codice processore di uscita sequenzialmente stdin quindi stdout il comando di una sola linea potrebbe essere semplice come questo:

generator | processor | verifier 

Altrimenti può usare questo

generator | tee in.txt | processor | verifier in.txt 

Il comando tee duplicare lo stdout e reindirizzare uno stream su in.txt e l'altro verso la pipe successiva. In questo caso è necessario modificare verifier per leggere l'output di processor da stdin e il file generato da generator viene passato come parametro.

So che stai cercando un metodo per duplicare e reindirizzare l'stdin-stdout ma io non sono a conoscenza di questo e onestamente non credo sia possibile

+1

penso che ho provato questo approccio, e non ha funzionato perché non v'è alcuna garanzia che in.txt sarà fatto per iscritto dal prima che il verificatore inizi a leggerlo (quindi ha finito per leggere il file vuoto). –

+0

È dovere di ogni processo verificare la validità dei parametri di input. Basta tornare se i parametri di input non sono validi. –

+0

@KimStrauss, se vuoi sincronizzare le linee 'generator' e' processor' con 'verifier', devi fare in modo che' processor' esegua l'interleaving. Altrimenti basta fare qualcosa seguendo le linee date dalla risposta di DavideBerra: Stuff emette da qualche parte, quindi chiama 'verificatore 'su entrambi. – vonbrand

2

Se non si desidera creare file reali sul disco rigido lento, è possibile utilizzare FIFO (First In First Out), che sono anche chiamati named pipe, a causa del loro comportamento.

mkfifo myfifo 
generator | tee myfifo | processor | verifier myfifo 

questo torrenti il ​​contenuto generato a tee, che duplica a myfifo ea stdout, che viene convogliata attraverso il processor al verifier. E lo verifier riceve anche lo stream da myfifo.

2

non ho ancora testato questo, ma provate:

{ generator | tee /dev/stderr | processor ; } 2>&1 | verifier 

Questo reindirizzerà una copia digenerator uscita stderr. Quindi eseguire processor su stdout di generator. Quindi combinare entrambi i tubi & su verifier.

Tuttavia, questo non può garantire l'ordine, in cui le linee dal generatore & potrebbero raggiungere il verificatore.


In alternativa, si può provare a sostituzione di processo come di seguito:

(generator | tee >(processor)) | verifier 
+1

L'ultimo è bello. – ffledgling