web-dev-qa-db-ja.com

pythonのstdinから1行ずつ読み込む方法

CのSTDINから文字を数える方法は誰もが知っています。しかし、python3でそれをしようとしたとき、それはパズルであることがわかりました。 (counter.py)

import sys
chrCounter = 0

for line in sys.stdin.readline():
    chrCounter += len(line)

print(chrCounter)

その後、私はプログラムをテストしようとします

python3 counter.py < counter.py

答えは、最初の行「import sys」の長さだけです。実際、プログラムは標準入力から最初の行のみを読み取り、残りを破棄します。

Sys.stdin.read()によってsys.stdin.readlineの代わりをする場合、それは動作します

import sys
print(len(sys.stdin.read()))

ただし、プログラムが大規模な入力に適していないことは明らかです。エレガントなソリューションを教えてください。ありがとうございました!

17
Storm-Eyes

より簡単です:

_for line in sys.stdin:
    chrCounter += len(line)
_

ファイルのようなオブジェクト_sys.stdin_は、行ごとに自動的に繰り返されます。その上で.readline()を呼び出すと、最初の行だけを読み取ります(そして、その文字ごとに繰り返します)。 read()を呼び出すと、入力全体を単一の文字列に読み取り、that character-by.characterを反復処理します。

30
Tim Pietzcker

文字カウントが必要な場合は、一度に1行ずつではなく、ブロック単位で読み取ります。

# 4096 chosen arbitrarily. Pick any other number you want to use.
print(sum(iter(lambda:len(sys.stdin.read(4096)), 0)))
0
Robᵩ

Tim Pietzckerからの答えは、私見では正しいものです。これを行うには、2つの同様の方法があります。を使用して:

_for line in sys.stdin:
_

そして

_for line in sys.stdin.readlines():
_

2番目のオプションは、元のコードにより近いものです。これら2つのオプションの違いは、たとえばforループ本体の次の変更および入力にキーボードを使用

_for line in sys.stdin.readlines():
    line_len = len(line)
    print('Last line was', line_len, 'chars long.')
    chrCounter += len(line)
_

最初のオプション(_for line in sys.stdin:_)を使用すると、Enterキーを押した直後に行が処理されます。

2番目のオプション(for line in sys.stdin.readlines():)を使用する場合、ファイル全体が最初に読み取られ、行に分割されてからのみ処理されます。

0
Posa