2

次のコードは、ティーにパイプするとパイプが壊れて終了しますが、パイプされていない場合は正しく動作します。

#!/usr/bin/python
import sys
def testfun():
    while 1:
        try :
            s = sys.stdin.readline()
        except(KeyboardInterrupt) :
            print('Ctrl-C pressed')
            sys.stdout.flush()
            return
        print s

if __name__ == "__main__":
    testfun()
    sys.exit()

期待される出力:

./bug.py 
Ctrl-C pressed

tee にパイプされたときに観察されるのは、パイプが壊れているか、出力がまったくないことです。つまり、ティー stdout には何もなく、 bug.log にも何もありません。

./bug.py | tee bug.log
Traceback (most recent call last):
  File "./bug.py", line 14, in <module>
    sys.stdout.flush()
IOError: [Errno 32] Broken pipe

この理由は何ですか?

4

3 に答える 3

9

いいえ、Ctrl-C を押しても両方のプロセスは終了しません。ティープロセスのみを終了し、ティープロセスの最後でスクリプトとティーの間のパイプが閉じられるため、スクリプトは壊れたパイプメッセージで終了します。

これを修正するために、tee にはパイプ内の前のプロセスに Ctrl-C を渡すオプションがあります: -i

試してみてください: マンティー

./bug.py
^CCtrl-C pressed
./bug.py | tee log
^CTraceback (most recent call last):
  File "./bug.py", line 14, in <module>
    testfun()
  File "./bug.py", line 9, in testfun
    sys.stdout.flush()
IOError: [Errno 32] Broken pipe

./bug.py | tee -i log
^CCtrl-C pressed
于 2011-08-31T00:52:17.033 に答える
5

これはPythonの問題ではありませんが、Brianが指摘したように、Ctrl-Cを押すと両方のプロセスが終了するシェルの問題です。回避策は、名前付きパイプを使用することです。

mknod mypipe p
cat mypipe | tee somefile.log &
./bug.py > mypipe
于 2009-07-28T09:25:35.077 に答える
4

Ctrl-C を押すと、シェルは両方のプロセス (pythontee) を終了し、それらを接続しているパイプを切断します。

したがって、プロセスで Ctrl-C を処理してフラッシュすると、終了し、パイプがなくなっているpythonことがわかります。teeしたがって、エラーメッセージ。

(余談ですが、ログに何か期待できますか?プロセスが終了時のフラッシュ以外のものを出力しているとは思いません)

于 2009-07-28T09:10:07.840 に答える