2014-09-25 27 views
2

如果我從python的stdin讀取輸入,for循環會在循環的主體運行之前收集很多行(至少在cpython中)。Python讀取unicode stdin而沒有批處理

from __future__ import print_function 
import sys 

for line in sys.stdin: 
    print("Echo:", line.strip()) 

輸出:

$ python ../test.py 
foo 
bar 
Echo: foo 
Echo: bar 

線在某種批次處理。 我能避免這樣的:

from __future__ import print_function 
import sys 

for line in iter(sys.stdin.readline, ''): 
    print("Echo:", line.strip()) 

輸出:

$ python ../test.py 
foo 
Echo: foo 
bar 
Echo: bar 

這正是我需要的。

我的問題是,我不得不閱讀utf-8輸入和iter()與伎倆不能與codecs.getwriter

from __future__ import print_function 
import sys 
import codecs 

sys.stdin = codecs.getreader('utf-8')(sys.stdin) 
for line in iter(sys.stdin.readline, ''): 
    print("Echo:", line.strip()) 

$ python ../test.py 
foo 
bar 
Echo: foo 
Echo: bar 

有沒有什麼辦法可以避免從標準輸入讀取utf8數據時的批處理?


編輯: 的完整性添加import語句。

+0

我想你的第一個例子,它沒有 「批」 的方式,你描述。你在做什麼系統? – tdelaney 2014-09-25 15:16:30

+0

當您在控制檯中運行時,Python 2.x應該爲您找出編碼。 'print sys.stdin.encoding'是什麼意思? – tdelaney 2014-09-25 15:41:58

+0

在Python2.7下運行的第一個程序不會產生你聲稱的輸出。 (它會打印'('Echo:','foo')')您使用的是哪個版本的Python? – 2014-09-25 16:04:11

回答

1

使用lambda

for line in iter(lambda: sys.stdin.readline().decode('utf-8'), ''): 
    print 'Echo:', line.strip() 

,或者解碼循環體:

for line in iter(sys.stdin.readline, ''): 
    print "Echo:", line.decode('utf-8').strip() 
+0

我不明白!這怎麼解決這個問題,特別是當我們不知道OP的控制檯有什麼編碼? – tdelaney 2014-09-25 15:43:06

+0

@tdelaney,OP在他/她的代碼中指定了'utf-8'。 – falsetru 2014-09-25 15:44:19

+0

@tdelaney,因爲'iter'調用'sys.stdin.readline'直到它遇到一個空行。 http://asciinema.org/a/12470 – falsetru 2014-09-25 15:47:23

1

您應該使用raw_inputstdin獲得一行輸入。

try: 
    while True: 
     print("Echo:", raw_input()) 
except EOFError: 
    pass 

問題是,Python 2只是有這種緩衝。見-u文檔的聯機幫助

-u Force stdin, stdout and stderr to be totally unbuffered. On systems 
    where it matters, also put stdin, stdout and stderr in binary mode. 
    Note that there is internal buffering in xreadlines(), readlines() and 
    file-object iterators ("for line in sys.stdin") which is not influenced 
    by this option. To work around this, you will want to use 
    "sys.stdin.readline()" inside a "while 1:" loop. 

的重要組成部分,是使用sys.stdin.readline()是行動的推薦課程;不太可能有強制unbuffer文件對象的好方法。

你應該只是解碼每一行,因爲你得到它。

+0

無緩衝模式如何解決問題? – tdelaney 2014-09-25 15:18:51

+0

@falsetru是的,'print'功能讓我失望。謝謝,這使理由更加明顯。不幸的是,我意識到我也離開了基地。 – Veedrac 2014-09-25 15:20:48