2017-02-02 5 views
2

私は名前付きパイプ 'timer_fifo'を持っていますが、pythonスクリプトのstdoutはtimer_fifoにリダイレクトされ、 。stdoutをファイルにリダイレクトすると間違った内容が表示される

のPythonスクリプト:

python above_file_name > timer_fifo 

シェルスクリプト:

while true 
do 
    read action <timer_fifo; 
    echo $action | stdbuf -o0 -e0 -i0 sed -n "s/^\([^[:space:]].*\)/\1 Cinnamon/p" >> activity_file 
done 

注:

import time 
while True: 
    print(time.strftime('%Y_%m_%d', time.gmtime())) 
    time.sleep(1) 

はPythonスクリプト上で実行上のsedコマンドもappend 'シナモン' と活動ファイルにリダイレクトしたがって、入力が '2017_02_01'であれば '2017_02_01 Cinnamon'になり、入力sは無視されますスペースで始めるならば、おしゃれです。

./file_name 

いくつかの時間のために、ファイルの末尾:

2017_02_01 Cinnamon 
2017_02_01 Cinnamon 
2017_02_01 Cinnamon 
2017_02_01 Cinnamon 
2017_02_01 Cinnamon 
2017_02_01 Cinnamon 
2017_02_01 Cinnamon 

しかし、ファイルの中に尾の後:

2017_02_01 Cinnamon 
2017_02_01 Cinnamon 
2017_02_01 Cinnamon 
2017_02_01 Cinnamon 
017_02_01 Cinnamon 
207_20 Cinnamon 
270_1 Cinnamon 
210_101_2001_20 Cinnamon 
2017_02_0 Cinnamon 
270_11207_02_01 Cinnamon 
107_20 Cinnamon 
0020 Cinnamon 

を見てのとおり、シェルスクリプト上で実行

なぜ出力が乱れるのでしょうか? また、上記のスクリプトを複数回実行している可能性があります。複数のプロセスが同時に同じファイルに書き込むと、そのソート出力が発生しますか?もしそうなら、理由を説明してください。

+0

Googleでたくさんのものを試してみてください。 – Marichyasana

+0

それは私がここに来る前にしたものです。 – druuu

答えて

0

プログラムのコピーを1つしか実行していない場合は、すべてがFIFOに順番に到着しており、バッファリングは順序に影響しません。

プログラムの複数のコピーを実行していて、それぞれが独自のstdoutのバッファリングを行っている場合は、部分行を取得できます。

私はあなたが見ていると思います。

私はこのケースで(不完全)ソリューションは、以下のように print()sleep()の間、あなたのPythonスクリプトに行を追加することだと思います

sys.stdout.flush() 

これは、それは非常に可能性が全体の行が取得することになります単一の、中断のないシステムコールでFIFOに書き込まれます。毎回print()/flush()が呼び出されます。それはまだ確実ではありません - あなたは原子性について保証されません。しかし実際には、このような短い文字列は単一のシステムコールとして扱われます。

(あなたはまた、sys.stdoutのバッファリングを変更してみてください、またはのpythonにランタイムフラグを使用しますが、私は上記のようflush()を呼び出して考えることが最善のアプローチである。)sys.stdout docsから

:インタラクティブ、標準ストリームがラインある場合-緩衝。それ以外の場合は、ブロックバッファーされます。通常のテキストファイルと同じです。

+0

明確な説明のためにAlexに感謝します。 – druuu

+0

あなたは大歓迎です! –

関連する問題