IO在计算机中指Input/Output,也就是输入和输出。
IO编程中,Stream(流)是一个很重要的概念,Input Stream就是输入流,Output Stream就是输出流。

文件读写

读文件

# 1. 打开文件
# r代表读取文件
f = open("C:/Users/zhouzhaodong/Desktop/123.txt", "r")
# 2. 读取文件内容
# 文件打开成功,我们这里就可以使用read()直接读取所有内容。
print(f.read())
# 3. 关闭文件
# 操作完毕文件后,我们需要主动关闭文件,否则就会占用资源。
f.close()

可是我们有的时候会忘记关闭怎么办?Python为我们想到了,其引入了with语句来帮我们调用close()方法。

with open("C:/Users/zhouzhaodong/Desktop/123.txt", "r") as f:
    print(f.read())

字符编码

如果我们要读取非UTF-8的文本文档的话,我们就需要给open()函数传入encoding函数,使其用相应的字符编码打开文件。

with open("C:/Users/zhouzhaodong/Desktop/123.txt", "r", encoding="gbk") as f:
    print(f.read())

当然我们可能想要去读取一些非文本文档,如二进制文件(图片,视频...),我们就不能用r了,这时候我们就要用rb模式来打开。

with open("C:/Users/zhouzhaodong/Desktop/123.jpg", "rb") as f:
    print(f.read())

读取文件当然会遇到错误了,可能文件中存在非法编码,这时候我们在读取过程中就会报错,open()函数中会接收一个errors参数,表示我们遇到错误应该怎么处理。最直接的方式就是忽略:

with open("C:/Users/zhouzhaodong/Desktop/123.txt", "r", errors="ignore") as f:
    print(f.read())

写文件

# 1. 打开文件
f = open('123.txt', 'w')
# 2. 写入内容
f.write("Hello World!")
# 3. 关闭文件
f.close()

我们可以反复调用write()来写入文件,可是操作系统并不会实时的将数据写入,而是将数据放入内存中进行缓存,空闲的时候才会进行写入。只有在我们调用close()的时候操作系统才会将所有的数据写入,如果我们忘记调用的话,就会丢失一部分数据。
这时候我们自然就想到了之前的with,这里也是可以使用的。

# w代表写入(会覆盖文件中的内容),a代表追加(不会覆盖)
with open('123.txt', 'w') as f:
    f.write("Hello World!")

在写入内容的时候也可以指定编码格式:

with open('123.txt', 'w', encoding='gbk') as f:
    f.write("Hello World!")

StringIO和BytesIO

StringIO

数据读写并不一定是在文件中进行操作,也可以在内存中进行。

from io import StringIO

# 创建一个StringIO
f = StringIO()
# 写入内容
f.write("Hello World!")
# 读取内容
print(f.getvalue())

BytesIO

StringIO只能操作str,如果要操作二进制数据,就需要使用BytesIO。

# 创建一个StringIO
f = BytesIO()
# 写入内容
f.write("中国".encode('utf-8'))
# 读取内容
print(f.getvalue())

运行结果:
b'\xe4\xb8\xad\xe5\x9b\xbd'

这里写入的是通过UTF-8编码的bytes。
可以直接不用bytes初始化一个BytesIO,然后读取。

from io import BytesIO  
f = BytesIO(b'\xe4\xb8\xad\xe5\x9b\xbd')  
print(f.read())
运行结果:
b'\xe4\xb8\xad\xe5\x9b\xbd'

操作文件和目录

操作系统

import os

# 如果是posix说明系统是linux或者Mac Os,如果是nt说明是windows
print(os.name)
# 如果想获取更多信息就用uname(),注意此方法在windows不能使用
# print(os.uname())
运行结果:
nt

环境变量

import os

# 环境变量都存在environ这个变量中,也可以有针对性的获取某个环境变量的值
print(os.environ.get('PATH'))

操作文件和目录

import os

# 获取当前目录的绝对路径
print(os.path.abspath('.')) 
# 如果在当前目录新建一个testdir文件夹的话,地址为:  
print(os.path.join('D:\\WorkSpace\\Study\\pythonTest', 'testdir'))  
# 新建testdir文件夹
os.mkdir('D:\\WorkSpace\\Study\\pythonTest\\testdir')  
# 删除testdir文件夹
os.rmdir('D:\\WorkSpace\\Study\\pythonTest\\testdir')
# 对文件重命名:
os.rename('123.txt', '123.py')
# 删掉文件:
os.remove('123.py')

序列化

我们可以将数据进行序列化存储到本地磁盘上,下一次程序启动就可以直接进行读取操作。

import pickle

# 新建一个dict
d = dict(name='bob', age=20, score=5)
# 将该对象进行序列化
print(pickle.dumps(d))

运行结果:
b'\x80\x04\x95$\x00\x00\x00\x00\x00\x00\x00}\x94(\x8c\x04name\x94\x8c\x03bob\x94\x8c\x03age\x94K\x14\x8c\x05score\x94K\x05u.'

将该数据写入文件中

import pickle

# 新建一个dict
d = dict(name='bob', age=20, score=5)
# 将该对象进行序列化
print(pickle.dumps(d))

# 打开一个文件
f = open('123.txt', 'wb')
# 将对象序列化为一个bytes后存入文件
pickle.dump(d, f)
# 关闭文件
f.close()

# 打开文件
f = open('123.txt', 'rb')
# 反序列化读取对象
d = pickle.load(f)
# 关闭文件
f.close()
# 打印反序列化的文件
print(d)

运行结果:
b'\x80\x04\x95$\x00\x00\x00\x00\x00\x00\x00}\x94(\x8c\x04name\x94\x8c\x03bob\x94\x8c\x03age\x94K\x14\x8c\x05score\x94K\x05u.'
{'name': 'bob', 'age': 20, 'score': 5}

周兆东
107 声望21 粉丝

一个java小白的成长之路。。。