2009-01-01 37 views
13

我有以下文件:線讀取扼流圈0x1A的

abcde 
kwakwa 
<0x1A> 
line3 
linllll 

其中<0x1A>代表與0x1A的的十六進制值一個字節。當試圖在Python中讀取此文件時:

for line in open('t.txt'): 
    print line, 

它只讀取前兩行,並退出循環。

的解決方案似乎是打開二進制文件(或通用換行模式)的文件 - 「RB」或「儒的。你能解釋這種行爲嗎?

+0

你怎麼知道這個字節代表<0x1A>。對我來說,它只是在記事本中說'SUB'++ – Programmer 2012-08-23 06:13:28

+0

另一個解決方法是使用Python 3或[`io.open()`](https://docs.python.org/2/library/io.html #io.open)在Python 2中;就操作系統而言,`io`文件對象總是以二進制模式使用文件,所以Windows不會過早地「結束」文件。 – 2016-04-19 21:24:32

回答

28

0x1A是Ctrl-Z,歷史上DOS使用它作爲文件結束標記。例如,嘗試使用命令提示符,然後「鍵入」文件。它只會在Ctrl-Z上顯示內容。

Python使用視窗CRT功能_wfopen,它實現了 「CTRL-Z是EOF」 語義。

9

Ned當然是正確的。

如果你的好奇心運行得更深一點,根本原因是向後兼容性被採取到極致。 Windows與DOS兼容,它使用Ctrl-Z作爲文本文件的文件標記的可選結尾。你可能不知道的是DOS與PC/PC之前在小型計算機上流行的CP/M兼容。 CP/M的文件系統沒有跟蹤文件大小,直到字節級別,它只跟蹤軟盤扇區的數量。如果您的文件不是128字節的精確倍數,則需要一種標記文本結尾的方法。 This Wikipedia article意味着Ctrl-Z的選擇基於DEC使用的更老的約定。