IO指input/output。
Input Stream就是数据从外面(磁盘、网络)流入内存,Output Stream就是数据从内存流出。
一、文件编写
读文件
f = open('/Users/michael/test.txt', 'r')
f.read()
f.close()
打开文件,一次性读取文件全部内容,后关闭文件。
ps:一定记得关文件,因为文件对象会占用操作系统的资源,且操作系统同一时间能打开的文件数量有限。
但是如果读取文件出现错误,即IOError,那f.close就不会被调用。所以python引入了with语句:
with open('/path/to/file', 'r') as f:
print(f.read())
这个语句不需要我们再调用f.close。
前面说到,read会直接一次性调运文件所有内容,如果内容十分庞大,那内存就爆炸了,所以我们可以使用read(size)或readline(),前者每次调用size字节个内容,后者一次调取一行内容。
还有一个readlines(),一次读取所有内容并按行返回list
。
二进制文件
当然,不止文本文件,如何读取二进制文件,比如图片、视频等。
用'rb'
模式打开文件即可:
f = open('/Users/michael/test.jpg', 'rb')
f.read()
字符编码
要读取非UTF-8编码的文本文件,需要给open()
函数传入encoding
参数:
f = open('/Users/michael/gbk.txt', 'r', encoding='gbk')
f.read()
遇到有些编码不规范的文件,可能会遇到UnicodeDecodeError
,因为在文本文件中可能夹杂了一些非法编码的字符。这时open()
函数还接收一个errors
参数:
f = open('/Users/michael/gbk.txt', 'r', encoding='gbk', errors='ignore')
写文件
传入标识符'w'
或者'wb'
表示写文本文件或写二进制文件:
with open('/Users/michael/test.txt', 'w') as f:
f.write('Hello, world!')
以'w'
模式写入文件时,如果文件已存在,会直接覆盖。如果我们希望追加到文件末尾,可以传入'a'
以追加(append)模式写入。
string IO 和 BytesIO
StringIO
即在内存中读写数据。
from io import StringIO
f = StringIO()
f.write('hello')
print(f.getvalue())
BytesIO
操作二进制数据
from io import BytesIO
f = BytesIO()
f.write('中文'.encode('utf-8'))
print(f.getvalue())
>>>b'\xe4\xb8\xad\xe6\x96\x87'
ps:写入的不是str,而是经过UTF-8编码的bytes。
操作文件和目录
操作系统提供的接口函数,Python内置的os
模块可以实现。
环境变量
在操作系统中定义的环境变量,全部保存在os.environ
这个变量中。
要获取某个环境变量的值,可以调用os.environ.get('key')。
操作文件和目录
操作文件和目录的函数一部分放在os
模块中,一部分放在os.path
模块中:
# 查看当前目录的绝对路径:
>>> os.path.abspath('.')
'/Users/michael'
# 在某个目录下创建一个新目录,首先把新目录的完整路径表示出来:
>>> os.path.join('/Users/michael', 'testdir')
'/Users/michael/testdir'
# 然后创建一个目录:
>>> os.mkdir('/Users/michael/testdir')
# 删掉一个目录:
>>> os.rmdir('/Users/michael/testdir')
合并和拆分路径
合并路径运用os.path.join()
函数,拆分路径运用os.path.split()
函数。
ps:复制文件的函数在os
模块中不存在
shutil
模块提供了copyfile()
的函数,它可以看做是os
模块的补充。
序列化
变量从内存中变成可存储或传输的过程称之为序列化(pickling)。
把变量内容从序列化的对象重新读到内存里称之为反序列化(unpickling)。
Python提供了pickle
模块来实现序列化。
import pickle
>>> d = dict(name='Bob', age=20, score=88)
>>> pickle.dumps(d)
b'\x80\x03}q\x00(X\x03\x00\x00\x00ageq\x01K\x14X\x05\x00\x00\x00scoreq\x02KXX\x04\x00\x00\x00nameq\x03X\x03\x00\x00\x00Bobq\x04u.'
pickle.dumps()
方法把任意对象序列化成一个bytes
,然后,把这个bytes
写入文件。
。。。