open内建函数
- 作为打开文件之门的“钥匙”,内建函数open() 提供了初始化输入/输出(I/O)操作的通用接口
- 成功打开文件后时候会返回一个文件对象,否则引发一个错误
- 基本语法:
file_object = open(file_name, mode='r', buffering=-1)
文件对象访问模式
文件模式 | 操作 |
---|---|
r | 以读方式打开(文件不存在则报错) |
w | 以写方式打开(文件存在则清空,不存在则创建) |
a | 以追加模式打开(必要时创建新文件) |
r+ | 以读写模式打开(参见r) |
w+ | 以读写模式打开(参见w) |
a+ | 以读写模式打开(参见a) |
b | 以二进制模式打开 |
文件输入
read方法
- read()方法用来直接读取字节到字符串中,最多读取给定数目个字节
- 如果没有给定size参数(默认值为-1)或者size值为负,文件将被读取直至末尾
>>> data = fobj.read()
>>> print(data)
readline方法
- 读取打开文件的一行(读取下个行结束符之前的所有字节)
- 然后整行,包括行结束符,作为字符串返回
- 它也有一个可选的size参数,默认为-1,代表读至行结束符
- 如果提供了该参数,那么在超过size个字节后会返回不完整的行
>>> data = fobj.readline()
>>> print(data)
readlines方法
- readlines()方法读取所有(剩余的)行然后把它们作为一个字符串列表返回
>>> data = fobj.readlines()
>>> print(data)
文件迭代
- 如果需要逐行处理文件,可以结合for循环迭代文件
- 迭代文件的方法与处理其他序列类型的数据类似
>>> fobj = open('star.py')
>>> for eachLine in fobj:
... print(eachLine,end='')
[root@room9pc01 ~]# cp /etc/passwd /tmp/mima
[root@room9pc01 ~]# python3
>>> f = open('/tmp/mima') #打开文件
>>> data = f.read()
>>> print(data)
>>> data = f.read()
>>> print(data) #再次读取的时候,由于第一次的数据已经读取完毕,再次读取来的数据为空
>>> f.close() #关闭文件
>>> data = f.read(4) #读取文件的前四个字节
文件输出
write方法
- write()内建方法功能与read()和readline()相反。它把含有文本数据或二进制数据块的字符串写入到文件中去
- 写入文件时,不会自动添加行结束标志,需要程序员手工输入
>>> fobj.write('Hello World!\n')
13
writelines方法
- 和readlines()一样,writelines()方法是针对列表的操
- 它接受一个字符串列表作为参数,将它们写入文件
- 行结束符并不会被自动加入,所以如果需要的话,必须在调用writelines()前给每行结尾加上行结束符
>>> fobj.writelines(['Hello World!\n','python programing\n'])
>>> f = open('/tmp/mima', 'w') # 文件不存在则创建,存在会清空
>>> f.write('hello world!\n')
13 # 返回写入到文件的字节数
>>> f.writelines(['2nd line.\n', '3rd line.\n'])
[root@room8pc16 day02]# cat /tmp/mima # 此时文件仍然是空的
>>> f.flush() # 立即将数据从缓存同步到磁盘
[root@room8pc16 day02]# cat /tmp/mima
hello world!
2nd line.
3rd line.
>>> f.write('end\n')
4
>>> f.close() # 关闭文件时,数据也会写入磁盘
处理非文本文件,与文本文件大体相似,只不过在打开文件时,需要加上b
[root@room8pc16 day02]# cp /usr/bin/ls /tmp/
>>> f = open('/tmp/ls')
>>> f.read(10) # 报错。因为打开时默认以utf8编码打开,但是ls不是文本文件。读取时,Python试图把读出来的10个字节显示为utf8字符。
>>> f.close()
>>> f = open('/tmp/ls', 'rb') # 以bytes类型打开
>>> f.read(10)
b'\x7fELF\x02\x01\x01\x00\x00\x00'
>>> f.close()
# 文本文件也能以bytes方式打开
>>> f = open('/tmp/mima', 'rb')
>>> f.read()
b'hello world!\n2nd line.\n3rd line.\nend\n'
>>> f.close()
操作文件
with子句
- with语句是用来简化代码的
- 在将打开文件的操作放在with语句中,代码块结束后,文件将自动关闭
>>> with open('foo.py') as f:
... data = f.readlines()
...
>>> f.closed
True
文件内移动
- seek(offset[, whence]):移动文件指针到不同的位
offset
是相对于某个位置的偏移量
whence
的值,0表示文件开头,1表示当前位置,2表示文件的结尾 - tell():返回当前文件指针的位置
>>> with open('/tmp/mima') as f:
... f.readline()
... f.readline()
...
'hello world!\n'
'2nd line.\n'
>>> f.readline() # 文件已经关闭,无法再读取数据
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
ValueError: I/O operation on closed file.
移动文件指针:seek(x, y)。y可以取值0,1,2,分别表示文件开头、当前位置和结尾。x是偏移量。
>>> f = open('/tmp/mima')
>>> f.tell() # 显示当前位置,永远从开头算偏移量
0
>>> f.seek(5, 0)
5
>>> f.read(1)
' '
>>> f.close()
>>> f = open('/tmp/mima')
>>> f.read() # 读取全部内容
>>> f.read() # 再读就没有数据了
''
>>> f.seek(0, 0) # 回到文件开头
0
>>> f.read() # 再次读取文件内容
>>> f.close() # 关闭文件
>>> f = open('/tmp/mima', 'rb')
>>> f.seek(-5, 2) # 指针移动到文件结尾前5个字节处
32
>>> f.read()
b'\nend\n'
f = open('/tmp/mima','rb')
print(f.tell()) #读取指针的当前位置
print(f.seek(5,0)) #将指针移动至从头开始的第五个字节
print(repr(f.read(1))) #读取当前指针开始往后的第一个字节,加repr是将对象转化为供解释器读取的形式。
print(f.seek(10,0)) #将指针重置到从头开始往后的第10个字节处
print(f.read(1)) #读取当前指针处往后的第一个字节的数据
print(f.seek(-5,2))
print(f.read())
f.close()
实际场景应用
- 创建cp.py文件
- 将/bin/ls“拷贝”到/root/目录下
- 不要修改原始文件
src_fname = '/bin/ls'
dst_name = '/tmp/list2'
src_fobj = open(src_fname,'rb')
dst_fobj = open(dst_name,'wb')
while True:
data = src_fobj.read(4096)
if len(data) == 0: #或者 if data == b'' 或者 if not data
break
dst_fobj.write(data)
src_fobj.close()
dst_fobj.close()