用Python操作文件
用word操作一個(gè)文件的流程如下:
1、找到文件,雙擊打開(kāi)。
2、讀或修改。
3、保存&關(guān)閉。
用Python操作文件也差不多:
f=open(filename) # 打開(kāi)文件
f.write("我是野生程序員") # 寫(xiě)操作
f.read() #讀操作
f.close() #保存并關(guān)閉
不過(guò)有一點(diǎn)跟人肉操作word文檔不同,就是word文檔只要打開(kāi)了,就即可以讀、又可以修改。 但Python比較變態(tài),只能以讀、創(chuàng)建、追加 3種模式中的任意一種打開(kāi)文件,不能即寫(xiě)又讀。
一、操作模式
- r 只讀模式
- w 創(chuàng)建模式,若文件已存在,則覆蓋舊文件
- a 追加模式,新數(shù)據(jù)會(huì)寫(xiě)到文件末尾
二、創(chuàng)建文件
f = open(file='C:/工作日常/staff.txt',mode='w')
f.write("Kwan CEO 100W\n")
f.write("KK 人事 5000\n")
f.close()
三、只讀模式
f = open(file='兼職白領(lǐng)學(xué)生空姐模特護(hù)士聯(lián)系方式.txt',mode='r')
print(f.readline()) # 讀一行
print('------分隔符-------')
data = f.read() # 讀所有,剩下的所有
print(data)
f.close()
執(zhí)行結(jié)果:
馬纖羽 深圳 173 50 13744234523
------分隔符-------
喬亦菲 廣州 172 52 15823423525
羅夢(mèng)竹 北京 175 49 18623423421
劉諾涵 北京 170 48 18623423765
岳妮妮 深圳 177 54 18835324553
賀婉萱 深圳 174 52 18933434452
葉梓萱 上海 171 49 18042432324
你得有這么個(gè)文件才能用上面的代碼。。。
四、追加模式
f = open(file='兼職白領(lǐng)學(xué)生空姐模特護(hù)士聯(lián)系方式.txt',mode='a')
f.write("黑姑娘 北京 168 48\n") # 會(huì)追加到文件尾部
f.close()
五、循環(huán)文件
f = open(file='兼職白領(lǐng)學(xué)生空姐模特護(hù)士聯(lián)系方式.txt',mode='r')
for line in f:
line = line.split()
name,addr,height,weight,phone = line
height = int(height)
weight = int(weight)
if height > 170 and weight <= 50:
print(line)
f.close()
輸出:
['馬纖羽', '深圳', '173', '50', '13744234523']
['羅夢(mèng)竹', '北京', '175', '49', '18623423421']
['葉梓萱', '上海', '171', '49', '18042432324']
六、其它功能
def mode(self) -> str:
# 返回文件打開(kāi)的模式
def name(self) -> str:
# 返回文件名
def fileno(self, *args, **kwargs): # real signature unknown
# 返回文件句柄在內(nèi)核中的索引值,以后做IO多路復(fù)用時(shí)可以用到
def flush(self, *args, **kwargs): # real signature unknown
# 把文件從內(nèi)存buffer里強(qiáng)制刷新到硬盤(pán)
def readable(self, *args, **kwargs): # real signature unknown
# 判斷是否可讀
def readline(self, *args, **kwargs): # real signature unknown
# 只讀一行,遇到\r or \n為止
def seek(self, *args, **kwargs): # real signature unknown
'''
把操作文件的光標(biāo)移到指定位置
*注意seek的長(zhǎng)度是按字節(jié)算的, 字符編碼存每個(gè)字符所占的字節(jié)長(zhǎng)度不一樣。
如“路飛學(xué)城” 用gbk存是2個(gè)字節(jié)一個(gè)字,用utf-8就是3個(gè)字節(jié),因此以gbk打開(kāi)時(shí),seek(4) 就把光標(biāo)切換到了“飛”和“學(xué)”兩個(gè)字中間。
但如果是utf8,seek(4)會(huì)導(dǎo)致,拿到了飛這個(gè)字的一部分字節(jié),打印的話會(huì)報(bào)錯(cuò),因?yàn)樘幚硎O碌奈谋緯r(shí)發(fā)現(xiàn)用utf8處理不了了,因?yàn)榫幋a對(duì)不上了。少了一個(gè)字節(jié)
'''
def seekable(self, *args, **kwargs): # real signature unknown
# 判斷文件是否可進(jìn)行seek操作
def tell(self, *args, **kwargs): # real signature unknown
# 返回當(dāng)前文件操作光標(biāo)位置
def truncate(self, *args, **kwargs): # real signature unknown
# 按指定長(zhǎng)度截?cái)辔募? # *指定長(zhǎng)度的話,就從文件開(kāi)頭開(kāi)始截?cái)嘀付ㄩL(zhǎng)度,不指定長(zhǎng)度的話,就從當(dāng)前位置到文件尾部的內(nèi)容全去掉。
def writable(self, *args, **kwargs): # real signature unknown
# 判斷文件是否可寫(xiě)
七、混合模式
- w+ 寫(xiě)讀 , 這個(gè)功能基本沒(méi)什么意義,它會(huì)創(chuàng)建一個(gè)新文件 ,寫(xiě)一段內(nèi)容,可以再把寫(xiě)的內(nèi)容讀出來(lái),沒(méi)什么卵用。
- r+ 讀寫(xiě),能讀能寫(xiě),但都是寫(xiě)在文件最后,跟追加一樣。
- a+ 追加讀,文件一打開(kāi)時(shí)光標(biāo)會(huì)在文件尾部,寫(xiě)的數(shù)據(jù)全會(huì)是追加的形式。
r+ 模式示例:
因?yàn)槟J(rèn)就是往文件尾部寫(xiě)入。
八、修改文件
嘗試直接以r+模式打開(kāi)文件,默認(rèn)會(huì)把新增的內(nèi)容追加到文件最后面。但我想要的是修改中間的內(nèi)容 ,怎么辦? 為什么會(huì)把內(nèi)容添加到尾部呢?(最新測(cè)試r+會(huì)從頭覆蓋,測(cè)試代碼如下)
問(wèn):為什么原有數(shù)據(jù)會(huì)被覆蓋呢?
這是硬盤(pán)的存儲(chǔ)原理導(dǎo)致的,當(dāng)你把文件存到硬盤(pán)上,就在硬盤(pán)上劃了一塊空間,存數(shù)據(jù),等你下次打開(kāi)這個(gè)文件 ,seek到一個(gè)位置,每改一個(gè)字,就是把原來(lái)的覆蓋掉,如果要插入,是不可能的,因?yàn)楹竺娴臄?shù)據(jù)在硬盤(pán)上不會(huì)整體向后移。所以就出現(xiàn) 當(dāng)前這個(gè)情況 ,你想插入,卻變成了會(huì)把舊內(nèi)容覆蓋掉。
問(wèn):但是人家word, vim 都可以修改文件 呀,你這不能修改算個(gè)什么玩意?
并沒(méi)說(shuō)就不能修改了,你想修改當(dāng)然可以,就是不要在硬盤(pán)上修改,把內(nèi)容全部讀到內(nèi)存里,數(shù)據(jù)在內(nèi)存里可以隨便增刪改查,修改之后,把內(nèi)容再全部寫(xiě)回硬盤(pán),把原來(lái)的數(shù)據(jù)全部覆蓋掉。vim word等各種文本編輯器都是這么干的。
問(wèn):說(shuō)的好像有道理,但你又沒(méi)看過(guò)word軟件的源碼,你憑什么這么篤定?
不需要看源碼,硬盤(pán)的存儲(chǔ)原理決定了word必須這么干 ,不信的話,還有個(gè)簡(jiǎn)單的辦法來(lái)確認(rèn)我說(shuō)的,就是用word or vim讀一個(gè)編輯一個(gè)大文件 ,至少幾百M(fèi)B的,你 會(huì)發(fā)現(xiàn),加載過(guò)程會(huì)花個(gè)數(shù)十秒,這段時(shí)間干嘛了? cpu 去玩了?去上廁所啦? 當(dāng)然不是,是在努力把數(shù)據(jù) 從硬盤(pán)上讀到內(nèi)存里。
問(wèn):還有更好的方式么?
沒(méi)有。
占硬盤(pán)方式的文件修改代碼示例 :
f_name = "兼職白領(lǐng)學(xué)生空姐模特護(hù)士聯(lián)系方式.txt"
f_new_name = "%s.new" % f_name
old_str = "劉諾涵"
new_str = "[黑姑娘]"
f = open(f_name,'r')
f_new = open(f_new_name,'w')
for line in f:
if old_str in line:
new_line = line.replace(old_str,new_str)
else:
new_line = line
f_new.write(new_line)
f.close()
f_new.close()
上面的代碼,會(huì)生成一個(gè)修改后的新文件 ,原文件不動(dòng),若想覆蓋原文件:
import os
f_name = "兼職白領(lǐng)學(xué)生空姐模特護(hù)士聯(lián)系方式.txt"
f_new_name = "%s.new" % f_name
old_str = "劉諾涵"
new_str = "[黑姑娘]"
f = open(f_name,'r')
f_new = open(f_new_name,'w')
for line in f:
if old_str in line:
new_line = line.replace(old_str,new_str)
else:
new_line = line
f_new.write(new_line)
f.close()
f_new.close()
os.rename(f_new_name,f_name) #把新文件名字改成原文件 的名字,就把之前的覆蓋掉了,windows使用os.replace # 幫助文檔說(shuō)明replace會(huì)覆蓋原文件
更多文章、技術(shù)交流、商務(wù)合作、聯(lián)系博主
微信掃碼或搜索:z360901061

微信掃一掃加我為好友
QQ號(hào)聯(lián)系: 360901061
您的支持是博主寫(xiě)作最大的動(dòng)力,如果您喜歡我的文章,感覺(jué)我的文章對(duì)您有幫助,請(qǐng)用微信掃描下面二維碼支持博主2元、5元、10元、20元等您想捐的金額吧,狠狠點(diǎn)擊下面給點(diǎn)支持吧,站長(zhǎng)非常感激您!手機(jī)微信長(zhǎng)按不能支付解決辦法:請(qǐng)將微信支付二維碼保存到相冊(cè),切換到微信,然后點(diǎn)擊微信右上角掃一掃功能,選擇支付二維碼完成支付。
【本文對(duì)您有幫助就好】元
