Python基础13-文件处理

news/2024/7/3 0:46:34

目录

用内置函数open打开文件

以文本方式打开文件

只读模式r

只写模式w

追加模式a

覆盖模式+

以二进制方式打开文件

以二进制方式读

以二进制方式写

open函数的newline参数

file object的方法

tell显示当前光标的位置

seek控制光标的移动

truncate切片文件


用内置函数open打开文件

open打开文件,返回文件句柄。通过句柄关闭文件。Python默认使用utf-8编码,但是open函数不是,open函数会检测当前操作系统的编码。read读取文件的全部内容。

# file1
# 苟利国家生死以
# 岂因祸福避趋之
f = open('file1.txt', encoding='utf-8')
data = f.read()
print(data)
f.close()

以文本方式打开文件

只读模式r

打开文件有不同的模式。用readable和writable方法判断是否可读写。

只读模式r,如果进行写操作会报错。只读是默认模式。用read读取全部内容。用readline读取一行。用readlines读取所有行放在一个列表里。

# file2
# 生不逢时
# 爱不逢人
# 所到之处
# 皆是命数
f = open('file2.txt')
print('line1:--->', f.readline(), end='')
print('line2:--->', f.readline(), end='')
f.close()f = open('file2.txt')
ss = f.readlines()
print(type(ss), ss)
# <class 'list'> ['生不逢时\n', '爱不逢人\n', '所到之处\n', '皆是命数\n']
for s in ss:print(s, end='')pass
f.close()

只写模式w

只写模式w,如果进行读操作会报错。如果文件不存在,那么会创建一个新文件。如果文件已经存在,那么会在打开文件时清空文件内容,再进行后续操作,慎重慎重。write方法只写但不加空格,writelines方法入参一个字符串列表,每个元素写一下,自己加换行。注意只能写字符串!

f = open('file3.txt', 'w', encoding='utf-8')
f.write('我是身经百战了!')
f.write('见的多了!\n')
f.write('西方哪一个国家我没有去过啊?\n')
f.close()
# file3内容是两行,写write需要自己加换行
# 我是身经百战了!见的多了!
# 西方哪一个国家我没有去过啊?f = open('file3.txt', 'w', encoding='utf-8')
seq = ['我是身经百战了!\n', '见的多了!\n', '西方哪一个国家我没有去过啊?\n']
f.writelines(seq)
f.close()
# 我是身经百战了!
# 见的多了!
# 西方哪一个国家我没有去过啊?

追加模式a

追加模式a,写的内容写到文件最后,不清空文件原有内容。适用于写日志。

f = open('file4.txt', 'a', encoding='utf-8')
f.write('写到文件字后\n')
f.close()

覆盖模式+

可读可写,写就直接从头开始覆盖已有内容。

f = open('file4.txt', mode='r+', encoding='gbk')
print(f.readable(), f.writable())
# True True
f.close()

以二进制方式打开文件

应用中,以二进制方式打开文件的情况可能更多,图片、视频、音频等都是以二进制方式读写的。

以二进制方式读

以文本方式打开文件是默认方式,还可以以二进制方式打开,也就是mode='b'。因为是以二进制方式打开,不再涉及编码,不能用 encoding入参指定编码方式。此时,read读取的数据都是一个一个的字节。如果要将一个一个的字节转换成可读的文字,那么需要进行解码decode。

# file3
# 我是身经百战了!
# 见的多了!
# 西方哪一个国家我没有去过啊?
f = open('file3.txt', mode='rb')
data = f.read()
print(data)
# b'\xe6\x88\x91\xe6\x98\xaf\xe8\xba\xab\xe7\xbb\x8f\xe7\x99\xbe\xe6\x88\x98\xe4\xba\x86\xef\xbc\x81\r\n\xe8\xa7\x81\xe7\x9a\x84\xe5\xa4\x9a\xe4\xba\x86\xef\xbc\x81\r\n\xe8\xa5\xbf\xe6\x96\xb9\xe5\x93\xaa\xe4\xb8\x80\xe4\xb8\xaa\xe5\x9b\xbd\xe5\xae\xb6\xe6\x88\x91\xe6\xb2\xa1\xe6\x9c\x89\xe5\x8e\xbb\xe8\xbf\x87\xe5\x95\x8a\xef\xbc\x9f\r\n'
print(data.decode('utf-8'))
# 解码为可读的字符
f.close()

以二进制方式写

以二进制方式写,mode='wb'或'ab'。因为是以二进制方式打开,不再涉及编码,不能用 encoding入参指定编码方式。此时write写入的都是一个一个字节,,不能直接写字符串,而要将字符串编码转换成字节流。

f = open('file6.txt', mode='wb')
# 以二进制方式写,不能直接写字符串,而要将字符串编码转换成字节流
f.write('苟利国家生死以,岂因祸福避趋之。'.encode('utf-8'))
f.close()

open函数的newline参数

在大多数操作系统里面,换行是\n。然而,windows里面换行是\r\n。

以文本模式打开文件时,newline参数对换行符进行转换。如果不指定,那么换行符都是\n。如果传入newline='',那么换行符按照操作系统转换为特定符号,windows下换行符转换为\r\n。

f = open('file1.txt', mode='r', encoding='utf-8')
d = f.readlines()
print(d)
# ['苟利国家生死以\n', '岂因祸福避趋之\n']
f.close()f = open('file1.txt', mode='r', encoding='utf-8', newline='')
d = f.readlines()
print(d)
# ['苟利国家生死以\r\n', '岂因祸福避趋之\r\n']
f.close()

file object的方法

tell显示当前光标的位置

文件以utf-8编码的文本形式打开,刚打开光标在0。读取一行,共7个汉字,因为utf-8编码汉字用3个字节,windows换行\r\n占两个字节,所以移动了3*7+2=23个字节。

# file1.txt
# 苟利国家生死以
# 岂因祸福避趋之
f = open('file1.txt', mode='r', encoding='utf-8')
print(f.tell())
# 0
d = f.readline()
print(d, end='')
# 苟利国家生死以
print(f.tell())
# 23
f.close()

seek控制光标的移动

除了read方法,其他光标的移动都是以字节为单位,seek也是一样。read读取3个字符“苟利国”,seek将光标移动到3个字节,也就是utf-8一个字符的位置,再读取3个字符“利国家”。

如果,用seek方法的第二个参数whence来控制seek的方式,那么必须以二进制方式打开文件,此时read读取的数列也是字节数。

seek第二个参数0,表示从文件开头开始seek,必须seek正数字节。

seek第二个参数1,表示从当前位置开始seek,可以seek正数、负数。

seek第二个参数2,表示从文件结尾开始seek,必须seek负数字节。

# file1.txt
# 苟利国家生死以
# 岂因祸福避趋之
f = open('file1.txt', mode='rb')
# 刚打开,光标位置为0,读取9个字节,得到 苟利国
d = f.read(9)
print(d.decode('utf-8'))
# 苟利国# seek从头开始3个字节,再读取9个字节,得到 利国家
f.seek(3)
d = f.read(9)
print(d.decode('utf-8'))
# 利国家# whence=1,也就是从当前位置11个字节,跳过生死以和\r\n
# 读取9个字节,得到 岂因祸
f.seek(11, 1)
d = f.read(9)
print(d.decode('utf-8'))
# 岂因祸# whence=2,也就是从文件最后倒着读取,跳过最后的\r\n和避趋之
# 读取9个字节,得到 避趋之
f.seek(-11, 2)
d = f.read(9)
print(d.decode('utf-8'))
# 避趋之
f.close()

seek方法的一个应用就是读取文件的最后一行。方法是从文件结尾,倒着seek再读取。如果不是读取多行,那么增大倒着seek的范围,直到能读取多行。打印最后一行。

# 如何读取文件的最后一行
# 方法是尝试读取多行,如果不是多行,那么增加读取范围
# 增加范围不一定用+1的办法,*2扩大一倍的办法更快
# file2.txt 用gbk编码
# 生不逢时
# 爱不逢人
# 所到之处
# 皆是命数
f = open('file2.txt', mode='rb')
offs = -1
while True:f.seek(offs, 2)d = f.readlines()if len(d) > 1:print('最后一行是:%s' % d[-1].decode('gbk'))breakpassoffs *= 2
f.close()

truncate切片文件

truncate是写操作,因此open文件的时候必须用'+',但是不能用'w+'。同样也是以字节为单位。

# file1.txt
# 苟利国家生死以
# 岂因祸福避趋之
f = open('file1.txt', mode='r+', encoding='utf-8')
f.truncate(12)
f.close()
# file1.txt 只剩下 苟利国家 四个字

 


http://lihuaxi.xjx100.cn/news/236090.html

相关文章

区块链技术特点之去中心化特性

想知道更多关于区块链技术知识&#xff0c;请百度【链客区块链技术问答社区】 链客&#xff0c;有问必答&#xff01;&#xff01; 由于区块链技术去中心化的特性&#xff0c;其在我们生活中的很多重要领域&#xff08;如金融、管理&#xff09;等方面具有重要的意义。例如&…

Java8 新特性之流式数据处理

2019独角兽企业重金招聘Python工程师标准>>> 一、流式处理简介 在我接触到java8流式处理的时候&#xff0c;我的第一感觉是流式处理让集合操作变得简洁了许多&#xff0c;通常我们需要多行代码才能完成的操作&#xff0c;借助于流式处理可以在一行中实现。比如我们希…

Python基础14-迭代器与生成器

目录 迭代器 官方文档对迭代器的解释 迭代器协议 基于迭代器协议的统一的for循环机制 生成器 官方文档对生成器的解释 生成器函数 生成器表达式 生成器用法举例 利用生成器用单线程实现生产者消费者问题模型 生成器只能遍历一次 迭代器 官方文档对迭代器的解释 Thi…

Java泛型进阶 - 如何取出泛型类型参数

在JDK5引入了泛型特性之后&#xff0c;她迅速地成为Java编程中不可或缺的元素。然而&#xff0c;就跟泛型乍一看似乎非常容易一样&#xff0c;许多开发者也非常容易就迷失在这项特性里。多数Java开发者都会注意到Java编译器的类型擦除实现方式&#xff0c;Type Erasure会导致关…

爬虫原理与数据抓取----- urllib2:URLError与HTTPError

urllib2 的异常错误处理 在我们用urlopen或opener.open方法发出一个请求时&#xff0c;如果urlopen或opener.open不能处理这个response&#xff0c;就产生错误。 这里主要说的是URLError和HTTPError&#xff0c;以及对它们的错误处理。 URLError URLError 产生的原因主要有&…

CV00-02-CV基本操作1

目录 数字图像属性 opencv-python环境搭建 基本操作I Read in / Show out&#xff0c;读取、显示图像&#xff1b; Change color&#xff0c;修改颜色&#xff1b; Gamma Correction&#xff0c;伽马校正&#xff1b; Crop&#xff0c;切割&#xff1b; Histogram&…

嵌入式课程安排 嵌入式培训课程大纲参考

嵌入式是一门综合性的学科&#xff0c;现在学习嵌入式开发不是单纯局限于单片机或者Linux&#xff0c;嵌入式课程中包含着非常多的内容。以粤嵌嵌入式课程进行参考&#xff0c;看看我们要学习嵌入式的话&#xff0c;要掌握哪些必备的技能。嵌入式课程安排包含&#xff1a;1、入…

EMQ学习笔记---Clean Session和Retained Message

MQTT会话(Clean Session)MQTT客户端向服务器发起CONNECT请求时&#xff0c;可以通过’Clean Session’标志设置会话。‘Clean Session’设置为0&#xff0c;表示创建一个持久会话&#xff0c;在客户端断开连接时&#xff0c;会话仍然保持并保存离线消息&#xff0c;直到会话超时…