特に満足できる回答はありません。そのため、役立つ小さなスニペットを以下に示します。
class LineSeekableFile:
def __init__(self, seekable):
self.fin = seekable
self.line_map = list() # Map from line index -> file position.
self.line_map.append(0)
while seekable.readline():
self.line_map.append(seekable.tell())
def __getitem__(self, index):
# NOTE: This assumes that you're not reading the file sequentially.
# For that, just use 'for line in file'.
self.fin.seek(self.line_map[index])
return self.fin.readline()
使用例:
In: !cat /tmp/test.txt
Out:
Line zero.
Line one!
Line three.
End of file, line four.
In:
with open("/tmp/test.txt", 'rt') as fin:
seeker = LineSeekableFile(fin)
print(seeker[1])
Out:
Line one!
これには多くのファイルシークが含まれますが、ファイル全体をメモリに収めることができない場合に役立ちます。行の場所を取得するために最初の1回の読み取りを行い(ファイル全体を読み取りますが、すべてをメモリに保持するわけではありません)、その後、アクセスごとにファイルのシークを行います。
ユーザーの裁量で、MITまたはApacheライセンスに基づいて上記のスニペットを提供します。