在python语言中,我们经常要对文件进行读写操作,笔者在这里回顾了一下文件的读写方法以及对文件指针的理解
最简单的打开文件的方式是:
open(fileaddress, mode='r', buffering=-1, encoding=None, errors=None, newline=None, closefd=True, opener=None)
参数解读:
fileaddress:表示将要打开的文件的路径,也可以是要被封装的整数类型文件描述符。
mode:是一个可选字符串,用于指定打开文件的模式,默认值是
'r'
(以文本模式打开并读取)。可选模式如下:buffering:是一个可选的整数,用于设置缓冲策略。
encoding:用于解码或编码文件的编码的名称。
errors:是一个可选的字符串,用于指定如何处理编码和解码错误(不能在二进制模式下使用)。
newline:区分换行符。
closefd:如果 closefd 为 False 并且给出了文件描述符而不是文件名,那么当文件关闭时,底层文件描述符将保持打开状态;如果给出文件名,closefd 为 True (默认值),否则将引发错误。
opener:可以通过传递可调用的 opener 来使用自定义开启器。
不过平时我们用不到这么多参数,一般简化为:
filename = r'E:\a.txt'
f = open(filename, mode='w',encoding='utf-8')
下面我们以demo的形式来理解这个过程:
上面我们创建的文件 test.txt 没有任何内容,我们向这个文件中写入一些信息,对于写操作,Python 文件对象提供了两个函数,如下所示:
函数 描述 write(str) 将字符串写入文件,返回写入字符长度 writelines(s) 向文件写入一个字符串列表 我们使用这两个函数向文件中写入一些信息,如下所示:
filename = r'' f = open(filename, 'w', encoding='utf-8') f.write('hello world\n') f.writelines(['this is a demo\n','by python']) # 关闭 f.close()
上面我们使用了 close() 函数进行关闭操作,如果打开的文件忘记了关闭,可能会对程序造成一些隐患,为了避免这个问题的出现,可以使用
with as
语句,通过这种方式,程序执行完成后会自动关闭已经打开的文件。如下:
'''
向文件中写入:
hello world
this is a demo
by python
'''
filename = r'E:\a.txt'
with open(filename,mode='w',encoding='utf-8') as f:
f.write('hello world\n')
f.writelines(['this is a demo\n','by python'])
执行过后文本内容是:
接下来我们需要读取文件的内容,python提供的函数主要是以下三个:
函数 | 描述 |
---|---|
read(size) | 读取指定的字节数,参数可选,无参或参数为负时读取所有 |
readline() | 读取一行 |
readlines() | 读取所有行并返回列表 |
with open(filename,'r',encoding='utf-8') as f:
print('read-->',f.read(5))
print('readline-->',f.readline())
print('readlines-->',f.readlines())
输出结果为:
read--> hello readline--> world readlines--> ['this is a demo\n', 'by python']
对比上面的函数我们会发现,f.read(5)返回的是文件的前面五个字符,即hello,没有问题。但是接着执行readline()和readlines()为什么就不是上述表格中描述的功能了呢?
实际上里面存在着文件指针,用来记录读或写文件进行到哪个地方了,当执行f.read(5)之后,文件指针已经移动到了第五个字符后面,接着再执行f.readline()的时候,程序就从指针当前位置继续,所以readline()返回的是word和一个换行。最后readlines()读取剩下的部分并以列表形式返回。
python对于文件指针也很贴心的给出了两个函数用于对文件指针进行控制:
函数 | 描述 |
---|---|
tell() | 返回文件指针在文件中的当前位置 |
seek(offset[, whence]) | 作用:将文件指针移动到指定的位置; 参数:offset 表示移动的偏移量; 参数:whence 为可选参数
注:whence=1或2时只能在读写二进制文件模式情况下使用 |
下面是一个文件指针位置读取与控制的示例:
with open(filename,'r',encoding='utf-8') as f:
print('read-->',f.read(1)) #读取第一个字节
position = f.tell() #获取文件指针的位置
print(f'position is:{position}') #输出文件指针位置
f.seek(5) #将文件指针移动到距离文件开头5个字节的位置上
position = f.tell() #获取文件指针的位置
print(f'moved position is:{position}') #输出文件指针位置
print('readline-->',f.readline()) #读取一行的文件内容
position = f.tell() #获取文件指针的位置
print(f'position is:{position}') #输出文件指针位置
输出结果为:
read--> h position is:1 moved position is:5 readline--> world position is:13
最后,不知道大家有没有发现一个问题:第一行是hello world,加上空格按理说也只有11个字节,为什么读完第一行指针处于13这个位置?
其实,在第一行的结尾有一个换行符\n,读第一行时候也会一并读进去,值得注意的是,\n作为换行符本身只占一个字节。为什么是13而不是12呢,原因在于在Windows系统中,换行符的写法是\r\n。所以这里才是在13的位置上