1. 程式人生 > >python3 檔案操作(讀、寫)

python3 檔案操作(讀、寫)

檔案操作基本流程

計算機系統分為:計算機硬體作業系統應用程式三部分。

記憶體 存不長久
硬碟 資料的持久化
檔案操作 —— 資料持久化的一種
全棧開發:框架類

操作檔案的流程:
#1. 開啟檔案,得到檔案控制代碼並賦值給一個變數
#2. 通過控制代碼對檔案進行操作
#3. 關閉檔案

coding:檔案操作

習慣叫 f file f_obj f_handler fh
複製程式碼
#1. 開啟檔案,得到檔案控制代碼並賦值給一個變數
f=open('a.txt','r',encoding='utf-8') #預設開啟模式就為r

#2. 通過控制代碼對檔案進行操作
data=f.read()

#3. 關閉檔案
f.close()
複製程式碼

f=open('a.txt','r')分析

#1、由應用程式向作業系統發起系統呼叫open(...)
#2、作業系統開啟該檔案,並返回一個檔案控制代碼給應用程式
#3、應用程式將檔案控制代碼賦值給變數f
檔案路徑:相對路徑、絕對路徑
複製程式碼
#找到檔案詳解:檔案與py的執行檔案在相同路徑下,直接用檔案的名字就可以開啟檔案
            # 檔案與py的執行檔案不在相同路徑下,用絕對路徑找到檔案
#檔案的路徑,需要用取消轉譯的方式來表示:1.\\    2.r''
#如果以寫檔案的方式開啟一個檔案,那麼不存在的檔案會被建立,存在的檔案之前的內容會被清空
# '\n' 檔案的換行
# f = open(r'C:\\Users\\Administrator\\Desktop\\s8_tmp.txt','w',encoding='utf-8')  # \\
f = open(r'C:\Users\Administrator\Desktop\s8_tmp.txt','w',encoding='utf-8') #檔案路徑、操作模式、編碼 # r'' f.write('哈哈哈') f.close()
複製程式碼

關閉檔案的注意事項

 注意

檔案編碼

複製程式碼
f = open('歌詞','w',encoding='utf-8')    #f:檔案操作符 檔案控制代碼 檔案操作物件
f.write('7018201890')
f.close()
#open開啟檔案是依賴了作業系統的提供的途徑
#作業系統有自己的編碼,open在開啟檔案的時候預設使用作業系統的編碼
#win7\8--->gbk    mac/linux---->utf-8
複製程式碼
#這就用到了上節課講的字元編碼的知識:若要保證不亂碼,檔案以什麼方式存的,就要以什麼方式開啟。
f=open('a.txt','r',encoding='utf-8')

檔案的開啟模式

檔案控制代碼 = open('檔案路徑', '模式') 
開啟檔案
#開啟檔案
# f = open('歌詞','r',encoding='utf-8')
f = open('歌詞',encoding='utf-8')
模式
複製程式碼
#1. 開啟檔案的模式有(預設為文字模式):
r ,只讀模式【預設模式,檔案必須存在,不存在則丟擲異常】
w,只寫模式【不可讀;不存在則建立;存在則清空內容】
a, 之追加寫模式【不可讀;不存在則建立;存在則只追加內容】

#2. 對於非文字檔案,我們只能使用b模式,"b"表示以位元組的方式操作(而所有檔案也都是以位元組的形式儲存的,使用這種模式無需考慮文字檔案的字元編碼、圖片檔案的jgp格式、視訊檔案的avi格式)
rb 
wb
ab
注:以b方式開啟時,讀取到的內容是位元組型別,寫入時也需要提供位元組型別,不能指定編碼
複製程式碼 瞭解1 瞭解2
f.writable()   #判斷檔案是否可寫
f = open('1.歌詞.txt','w',encoding="utf-8")
print(f.writable())  # #判斷檔案是否可寫
f.close()  # True
f.readable()   #判斷檔案是否可讀
f = open('1.歌詞.txt','w',encoding="utf-8")
print(f.readable())  # #判斷檔案是否可寫
f.close()  # False

讀檔案

1.read方法會一次性的讀出檔案中的所有內容

複製程式碼
#1.讀檔案的第一種方式:read方法,用read方法會一次性的讀出檔案中的所有內容
f = open('1.歌詞.txt',encoding='utf-8')
content = f.read()
print('read : ',content)  #
f.close()
複製程式碼

輸出結果

複製程式碼
read :  111
222
aaa
bbb
哇哈哈
QQ星
複製程式碼

2.讀一部分內容:read(n),指定讀n個單位

複製程式碼
#2.讀一部分內容:read(n),指定讀n個單位
f = open('1.歌詞.txt',encoding='utf-8')
print(f.read(2))  # 11
f.close()
複製程式碼

3.按照行讀,每次執行readline就會往下讀一行

複製程式碼
#3.讀檔案的第三種方式:按照行讀,每次執行readline就會往下讀一行
f = open('1.歌詞.txt',encoding='utf-8')
content = f.readline()
print('readline : ',content.strip())    #strip去掉空格、製表符、換行符
content2 = f.readline()
print(content2.strip())
f.close()
複製程式碼

輸出結果

readline :  111
222

4.readlines,返回一個列表,將檔案中的每一行作為列表中的每一項返回一個列表

複製程式碼
#4.讀檔案的第四種方式:readlines,返回一個列表,將檔案中的每一行作為列表中的每一項返回一個列表
f = open('1.歌詞.txt',encoding='utf-8')
content = f.readlines()
print('readlines : ',content)  # readlines :  ['111\n', '222\n', 'aaa\n', 'bbb\n', '哇哈哈\n', 'QQ星']
f.close()
複製程式碼

5.讀:最常用for迴圈

複製程式碼
#5.讀:最常用for迴圈
f = open('1.歌詞.txt',encoding='utf-8')
for l in f:
    print(l.strip())
f.close()
複製程式碼

輸出結果

複製程式碼
111
222
aaa
bbb
哇哈哈
QQ星
複製程式碼

列子:

 1.歌詞.txt

結果:

 1.讀檔案並整理成需要的資料型別

複製程式碼
f = open('1.歌詞.txt',encoding='utf-8') #讀檔案並整理成需要的資料型別
goods_list = []
for line in f:
    if line.strip():
        goods_dic = {'name':None,'price':None}
        line = line.strip()
        goods_lst = line.split()
        print(goods_lst)
        goods_dic['name'] = goods_lst[0]
        goods_dic['price'] = goods_lst[1]
        goods_list.append(goods_dic)
print(goods_list)
f.close()
複製程式碼

輸出結果:

 結果:
2.只顯示檔案中有內容的行
複製程式碼
f = open('1.歌詞.txt',encoding='utf-8')    #只顯示檔案中有內容的行
goods_list = []
for line in f:
   if line.strip():
       print(line.strip())
f.close()
複製程式碼

輸出結果:

 結果:

檔案內的游標移動

一: read(3):

  1. 檔案開啟方式為文字模式時,代表讀取3個字元

  2. 檔案開啟方式為b模式時,代表讀取3個位元組

二: 其餘的檔案內游標移動都是以位元組為單位如seek,tell,truncate

注意:

  1. seek有三種移動方式0,1,2,其中1和2必須在b模式下進行,但無論哪種模式,都是以bytes為單位移動的

 seek引數詳解

  2. truncate是截斷檔案,所以檔案的開啟方式必須可寫,但是不能用w或w+等方式開啟,因為那樣直接清空檔案了,所以truncate要在r+或a或a+等模式下測試效果

#tell: 告訴你當前游標所在的位置
 tell
#seek 游標移動到第幾個位元組的位置
  # f.seek(0)    移動到最開始
  # f.seek(0,2)  移動到最末尾

#truncate: 保留n個位元組
  ps:
  
 1.txt

從檔案開始的位置只保留指定位元組的內容
複製程式碼
f = open('1.歌詞.txt','r+',encoding='utf-8')
f.truncate(3)  #從檔案開始的位置只保留指定位元組的內容
content2 = f.readline()
print(content2.strip())  # aab
f.close()
複製程式碼

 檢視1.txt檔案,已被修改,只有aab3個位元組了。

檔案的修改

檔案的資料是存放於硬碟上的,因而只存在覆蓋、不存在修改這麼一說,我們平時看到的修改檔案,都是模擬出來的效果,具體的說有兩種實現方式:

方式一:將硬碟存放的該檔案的內容全部載入到記憶體,在記憶體中是可以修改的,修改完畢後,再由記憶體覆蓋到硬碟(word,vim,nodpad++等編輯器)

複製程式碼
import os

with open('a.txt') as read_f,open('.a.txt.swap','w') as write_f:
    data=read_f.read() #全部讀入記憶體,如果檔案很大,會很卡
    data=data.replace('alex','SB') #在記憶體中完成修改

    write_f.write(data) #一次性寫入新檔案

os.remove('a.txt')
os.rename('.a.txt.swap','a.txt') 
複製程式碼

方式二:將硬碟存放的該檔案的內容一行一行地讀入記憶體,修改完畢就寫入新檔案,最後用新檔案覆蓋原始檔

複製程式碼
import os

with open('a.txt') as read_f,open('.a.txt.swap','w') as write_f:
    for line in read_f:
        line=line.replace('alex','SB')
        write_f.write(line)

os.remove('a.txt')
os.rename('.a.txt.swap','a.txt') 
複製程式碼