1. 程式人生 > >第028講:檔案:因為懂你,所以永恆

第028講:檔案:因為懂你,所以永恆

目錄

測試題

0. 下邊只有一種方式不能開啟檔案,請問是哪一種,為什麼?

1. 開啟一個檔案我們使用open()函式,通過設定檔案的開啟模式,決定開啟的檔案具有那些性質,請問預設的開啟模式是什麼呢?

2. 請問 >>> open('E:\\Test.bin', 'xb') 是以什麼樣的模式開啟檔案的?

3. 儘管Python有所謂的“垃圾回收機制”,但對於打開了的檔案,在不需要用到的時候我們仍然需要使用f.close()將檔案物件“關閉”,這是為什麼呢?

4. 如何將一個檔案物件(f)中的資料存放進列表中?

5. 如何迭代打印出檔案物件(f)中的每一行資料?

6. 檔案物件的內建方法f.read([size=-1])作用是讀取檔案物件內容,size引數是可選的,那如果設定了size=10,例如f.read(10),將返回什麼內容呢?

7. 如何獲得檔案物件(f)當前檔案指標的位置?

8. 還是視訊中的那個演示檔案(record.txt),請問為何f.seek(45, 0)不會出錯,但f.seek(46)就出錯了呢?

動動手

0. 嘗試將檔案( ​ OpenMe.mp3 (700 Bytes, 下載次數: 7051) )列印到螢幕上

1. 編寫程式碼,將上一題中的檔案(OpenMe.mp3)儲存為新檔案(OpenMe.txt)

2. 請寫下這一節課你學習到的內容:格式不限,回憶並複述是加強記憶的好方式!


測試題

0. 下邊只有一種方式不能開啟檔案,請問是哪一種,為什麼?

  1. >>> f = open('E:/test.txt', 'w')   # A
  2. >>> f = open('E:\test.txt', 'w')   # B
  3. >>> f = open('E://test.txt', 'w')  # C
  4. >>> f = open('E:\\test.txt', 'w')  # D

答:B不能開啟檔案。

Windows在路徑名中既可以接受斜線(/)也可以接受反斜線(\),不過如果使用反斜線作為路徑名的分隔符的話,要注意使用雙反斜線(\\)進行轉義,否則Python會將反斜線進行轉義,例如(\n)看成一個換行符,(\t)看作一個製表符等。

1. 開啟一個檔案我們使用open()函式,通過設定檔案的開啟模式,決定開啟的檔案具有那些性質,請問預設的開啟模式是什麼呢?

答:open()函式預設的開啟模式是'rt',即可讀、文字的模式開啟。

2. 請問 >>> open('E:\\Test.bin', 'xb') 是以什麼樣的模式開啟檔案的?

答:以“可寫入以及二進位制模式”開啟檔案“E:\\Test.bin”。

這裡要注意的是'x'和'w'均是以“可寫入”的模式開啟檔案,但以'x'模式開啟的時候,如果路徑下已經存在相同的檔名,會丟擲異常,而'w'模式的話會直接覆蓋同名檔案。

因此,'w'模式開啟檔案會比較危險,容易導致此前的內容遺失,因此使用'w'模式開啟檔案前先檢查該檔名是否已經存在顯得非常重要!下節課小甲魚會教你如何安全的開啟一個檔案^_^

3. 儘管Python有所謂的“垃圾回收機制”,但對於打開了的檔案,在不需要用到的時候我們仍然需要使用f.close()將檔案物件“關閉”,這是為什麼呢?

答:Python擁有垃圾收集機制,會在檔案物件的引用計數降至零的時候自動關閉檔案,所以在Python程式設計裡,如果忘記關閉檔案並不會造成記憶體洩漏那麼危險。

但並不是說就可以不要關閉檔案,如果你對檔案進行了寫入操作,那麼你應該在完成寫入之後進行關閉檔案。因為Python可能會快取你寫入的資料,如果這中間斷電了神馬的,那些快取的資料根本就不會寫入到檔案中。所以,為了安全起見,要養成使用完檔案後立刻關閉的優雅習慣。

4. 如何將一個檔案物件(f)中的資料存放進列表中?

答:list(f),是不是非常的方便!

5. 如何迭代打印出檔案物件(f)中的每一行資料?

答:直接使用for語句把檔案物件迭代出來即可:

  1. for each_line in f:
  2.         print(each_line)

6. 檔案物件的內建方法f.read([size=-1])作用是讀取檔案物件內容,size引數是可選的,那如果設定了size=10,例如f.read(10),將返回什麼內容呢?

答:將返回從檔案指標開始(注意這裡並不是檔案頭哦)的連續10個字元。

7. 如何獲得檔案物件(f)當前檔案指標的位置?

答:f.tell()會告訴你^_^

8. 還是視訊中的那個演示檔案(record.txt),請問為何f.seek(45, 0)不會出錯,但f.seek(46)就出錯了呢?

  1. >>> f.seek(46)
  2. 46
  3. >>> f.readline()
  4. Traceback (most recent call last):
  5.   File "<pyshell#18>", line 1, in <module>
  6.     f.readline()
  7. UnicodeDecodeError: 'gbk' codec can't decode byte 0xe3 in position 4: illegal multibyte sequence

答:因為使用f.seek()定位的檔案指標是按位元組為單位進行計算的,演示檔案(record.txt)是以GBK進行編碼的,按照規則,一個漢字需要佔用兩個位元組,f.seek(45)的位置位於字元“小”的開始位置,因此可以正常列印,而f.seek(46)的位置剛好位於字元“小”的中間位置,因此按照GBK編碼的形式無法將其解碼!


動動手

0. 嘗試將檔案(  OpenMe.mp3 (700 Bytes, 下載次數: 7051) )列印到螢幕上

答:直接使用開啟文字檔案的形式開啟即可,至於為什麼?開啟後會告訴你@[email protected]

  1. f = open('OpenMe.mp3')
  2. for each_line in f:
  3.         print(each_line, end='')
  4. f.close()

1. 編寫程式碼,將上一題中的檔案(OpenMe.mp3)儲存為新檔案(OpenMe.txt)

f1 = open('OpenMe.mp3')
f2 = open('OpenMe.txt', 'x')        # 使用”x”開啟更安全
f2.write(f1.read())
f2.close()
f1.close()

2. 請寫下這一節課你學習到的內容:格式不限,回憶並複述是加強記憶的好方式!

檔案開啟模式

開啟模式 執行操作
'r' 以只讀方式開啟檔案(預設)
'w' 以寫入的方式開啟檔案,會覆蓋已存在的檔案
'x' 如果檔案已經存在,使用此模式開啟將引發異常
'a' 以寫入模式開啟,如果檔案存在,則在末尾追加寫入
'b' 以二進位制模式開啟檔案
't' 以文字模式開啟(預設)
'+' 可讀寫模式(可新增到其他模式中使用)
'U' 通用換行符支援

檔案物件方法

檔案物件方法 執行操作
f.close() 關閉檔案
f.read([size=-1]) 從檔案讀取size個字元,當未給定size或給定負值的時候,讀取剩餘的所有字元,然後作為字串返回
f.readline([size=-1]) 從檔案中讀取並返回一行(包括行結束符),如果有size有定義則返回size個字元
f.write(str) 將字串str寫入檔案
f.writelines(seq) 向檔案寫入字串序列seq,seq應該是一個返回字串的可迭代物件
f.seek(offset, from) 在檔案中移動檔案指標,從from(0代表檔案起始位置,1代表當前位置,2代表檔案末尾)偏移offset個位元組
f.tell() 返回當前在檔案中的位置
f.truncate([size=file.tell()]) 擷取檔案到size個位元組,預設是擷取到檔案指標當前位置