一、文件操作:
文件操作的流程:
1 #1、打开i文件,获取文件句柄,并赋值给一个变量 2 #2、通过文件句柄对文件进行操作 3 #3、关闭文件
二、Python中的文件操作流程:
1 #1. 打开文件,得到文件句柄并赋值给一个变量 2 f=open('a.txt','r',encoding='utf-8') #默认打开模式就为r,encoding是打开 该文件是用的编码方式,并不是文件的编码方式 3 4 #2. 通过句柄对文件进行操作 5 data=f.read() 6 7 #3. 关闭文件 8 f.close()
三、fl = open('/PATH/file.txt', 'r', encoding='utf-8')的过程分析
1 # 由应用程序(pycharm)向系统调用open() 2 3 # 操作系统打开该文件,并返回一个文件句柄给应用程序 4 5 #应用程序将文件句柄赋值给变量fl
四、特殊注意点:
1 # 打开一个文件包含两部分资源,一个是操作系统打开的文件,一个是应用程序变量。在操作完一个文件后,必须把这两部分资源回收,而且,变量回收必须在文件结束之后,否则导致文件关闭不了,导致内存白白浪费。但是由于Python自带的垃圾回收机制,变量回收不需要我们去操作。只要执行f.close() 2 3 # 因为有时候还是会忘记关闭文件,所以有如下的方法处理: 4 with open(‘a.txt’,'r',encoding='utf8)as f: 5 pass 6 7 利用with,等文件操作完后,文件会自动关闭,不需人为操作,with后可以跟多个,如: 8 9 with open('a.txt','r') as read_f,open('b.txt','w') as write_f: 10 data=read_f.read() 11 write_f.write(data) 12 # 但是注意的是,这样,两个文件名不能一样,比如文件修改: 13 # 文件修改 14 src_f=open('xxx','r',encoding='gbk') 15 data=src_f.readlines() 16 src_f.close() 17 18 dst_f=open('xxx','w',encoding='gbk') 19 dst_f.write(data[0]) 20 dst_f.close()
1 f=open(...)是由操作系统打开文件,那么如果我们没有为open指定编码,那么打开文件的默认编码很明显是操作系统说了算了,操作系统会用自己的默认编码去打开文件,在windows下是gbk,在linux下是utf-8。 2 若要保证不乱码,文件以什么方式存的,就要以什么方式打开。 3 4 f=open('a.txt','r',encoding='utf-8') 5 6 字符串 ----> encode ----> 二进制 7 二进制 ----> decode ----> 字符串
五、打开文件的模式:
1 #1、打开文件的基本模式(默认文本模式,txt 。。。) 2 r : 只读 ,文件必须存在,不存在抛出异常 3 w : 只写 ,文件不存在时创建,存在时覆盖原文件(也可以说清空) 4 a :追加 ,文件存在时,追加,不存在时创建 5 6 # 2、对于非文本文件,我们只能用b模式,表示以字节的方式处理文件(而所有文件也都是以字节的形式存储的,使用这种模式无需考虑文本文件的字符编码、图片文件的jgp格式、视频文件的avi格式) 7 rb : 8 wb : 9 ab : 10 注:以b方式打开时,读取到的内容是字节类型,写入时也需要提供字节类型,不能指定编码 11 12 #3. 了解部分 13 "+" 表示可以同时读写某个文件 14 r+, 读写【可读,可写】 15 w+,写读【可读,可写】 16 a+, 写读【可读,可写】
1、文件处理读操作:
1 f=open('a','r',encoding='utf-8') # 等于 f=open('陈粒',encoding='utf-8') 2 data=f.read() 3 # print(data) 4 print(f.readable()) # 是否可读 5 print('第1行',f.readline(),end='') # 每执行一次读一行 6 print('第2行',f.readline()) 7 print('第3行',f.readline()) 8 # for i in range(1): 9 # pass 10 print('第4行',f.readline()) 11 print('第5行',f.readline()) 12 print('第6行',f.readline()) 13 print('第7行',f.readline()) 14 15 data=f.readlines() # 将每一行内容作为列表的元素(包括回车符),生成一个列表 16 print(data) 17 f.close() 18 19 20 ## 注意,如果先执行read()后,光标直接移到最后,后续的操作就没有打印出现了
2、文件处理写操作
1 f=open('陈粒','w',encoding='utf8') 2 # f.read() # 没有读操作 3 f.write('11111111 ') 4 f.write('222222222 ') 5 f.write('333 4444 555 ') 6 # # f.writable() #是否可写 7 f.writelines(['555 ','6666 ']) 8 f.writelines(['555 ','6666 ',1]) # 文件内容只能是字符串,只能写字符串 9 # f.close()
3、文件处理追加操作
1 f=open('陈粒1','a',encoding='utf-8') 2 f.write('写到文件最后') 3 f.close()
4、修改文件
1 # 事实上,文件的修改是,打开原文件,把原文件copy到新的文件,同事修改要改变的地方,再覆盖原来的文件 2 3 # 修改文件: 4 f = open('a.txt','r',encoding='utf-8') 5 data = f.readlines() 6 f.close 7 8 f = open('a.txt','w',encoding='utf-8') 9 data[0] = 'jack' 10 f.writelines(data) 11 f.close()
1 import os 2 3 with open('a.txt') as read_f,open('.a.txt.swap','w') as write_f: 4 for line in read_f: 5 line=line.replace('alex','SB') 6 write_f.write(line) 7 8 os.remove('a.txt') 9 os.rename('.a.txt.swap','a.txt')
5、b模式
1 # f=open('a.txt','rb',encoding='utf-8') #b的方式不能指定编码 2 f=open('a.txt','rb') #b的方式不能指定编码 3 data=f.read() 4 # #'字符串'---------encode---------》bytes 5 # #bytes---------decode---------》'字符串' 6 print(data) #b'111 222 333 444 555 ' win平台换行 7 print(data.decode('utf-8')) # a.txt是utf-8编码的 8 # f.close() 9 10 f=open('test22.py','wb') #b的方式不能指定编码 11 f.write(bytes('1111 ',encoding='utf-8')) 12 f.write('杨件'.encode('utf-8')) # 或者调用字符串的encode()方法 13 14 f=open('test22.py','ab') #b的方式不能指定编码 15 f.write(' 杨件hhh'.encode('utf-8'))
6、文件操作的其他方法
1 # f=open('a.txt','r+',encoding='utf-8') 2 # # data=f.read() 3 # # print(data) 4 # f.write('你好') 5 6 7 # f=open('a.txt','r',encoding='utf-8',newline='') #读取文件中真正的换行符号 8 # print(f.readlines()) # ['你好 '] 9 # f=open('a.txt','r+',encoding='utf-8',newline='') #读取文件中真正的换行符号 10 11 # print(f.closed) 12 # print(f.encoding) 13 # f.flush() # 将内存中的内flush到磁盘中 14 # print(f.readlines()) 15 16 # print(f.tell()) #获得光标位置 17 # f.readline() 18 # print(f.tell()) 19 20 # f.seek(1) # 移动光标 21 # print(f.tell()) 22 # print(f.readlines()) 23 # f.seek(3) 24 # print(f.tell()) 25 # print(f.read()) 26 27 # data=f.read(1) # 文件操作中 read是一个一个读字符 28 # print(data) 29 30 31 32 # f.flush() #讲文件内容从内存刷到硬盘 33 # 34 # f.closed #文件如果关闭则返回True 35 # 36 # f.encoding #查看使用open打开文件的编码 37 # f.tell() #查看文件处理当前的光标位置 38 # 39 # f.seek(3) #从开头开始算,将光标移动到第三个字节 40 # f.truncate(10) #从开头开始算,将文件只保留从0-10个字节的内容,文件必须以写方式打开,但是w和w+除外 41 # 42 # f=open('d.txt','r',newline='') 43 # 44 # data=f.readline().encode('utf-8') 45 # print(data) 46 # print(f.tell()) 47 48 49 50 51 52 53 54 # f=open('seek.txt','r',encoding='utf-8') 55 # print(f.tell()) 56 # f.seek(10) 57 # print(f.tell()) 58 # f.seek(3) 59 # print(f.tell()) 60 61 # f=open('seek.txt','rb') 62 # print(f.tell()) 63 # f.seek(10,1) 64 # print(f.tell()) 65 # f.seek(3,1) 66 # print(f.tell()) 67 68 # seek() 如果不用相对位置,可以不用b模式,但是只要用相对位置,就必须用b模式 69 # seek() 的第一个参数是位置,正序 为 正数,倒序为负数,第二个参数:0 默认从0开始,1 从上次位置开始,2 倒序 70 71 # f=open('a.txt','rb') 72 # print(f.tell()) 73 # f.seek(-5,2) 74 # print(f.read()) 75 # # print(f.tell()) 76 # f.seek(3,1) 77 # print(f.tell()) 78 79 ## 只要不是倒序,都是正序,也就是说,如果倒序读到某个位置,此时要在读文件,就是从此处往后读 80 81 82 83 84 85 86 87 # f=open('日志文件','rb') 88 # data=f.readlines() 89 # print(data[-1].decode('utf-8')) 90 # 91 # f=open('日志文件','rb') 92 # 93 # for i in f.readlines(): 94 # print(i) 95 96 #循环文件的推荐方式,不是一次去不加载到内存中,用一行读一行 97 # for i in f: 98 # print(i) 99 100 101 102 # for i in f: 103 # offs=-10 104 # while True: 105 # f.seek(offs,2) 106 # data=f.readlines() 107 # if len(data) > 1: 108 # print('文件的最后一行是%s' %(data[-1].decode('utf-8'))) 109 # break 110 # offs*=2
文件对象方法总结:
方法 | 描述 |
f.close() | 关闭文件,记住用open()打开文件后一定要记得关闭它,否则会占用系统的可打开文件句柄数。 |
f.fileno() | 获得文件描述符,是一个数字 |
f.flush() | 刷新输出缓存 |
f.isatty() | 如果文件是一个交互终端,则返回True,否则返回False。 |
f.read([count]) | 读出文件,如果有count,则读出count个字节。 |
f.readline() | 读出一行信息。 |
f.readlines() | 读出所有行,也就是读出整个文件的信息。列表显示 |
f.seek(offset[,where]) | 把文件指针移动到相对于where的offset位置。where为0表示文件开始处,这是默认值 ;1表示当前位置;2表示文件结尾。 |
f.tell() | 获得文件指针位置。 |
f.truncate([size]) | 截取文件,使文件的大小为size。 |
f.write(string) | 把string字符串写入文件。 |
f.writelines(list) | 把list中的字符串一行一行地写入文件,是连续写入文件,没有换行。 |