目录

(一)路径和路径名

1)绝对路径和相对路径

2)当前工作目录

3)使用pathlib模块访问目录

4)路径名的处理

使用os.path处理路径名

用pathlib处理路径名

(二)获取文件信息

(三)文件系统的其他操作

设计一个计算文件大小的程序

(四)file对象

1)打开和关闭文件

2)使用with关键字

3)读写文本函数

readlines函数

将file对象视为迭代器

写入文件

(五)文件操作的其他模块


文件操作涉及两件事情,即基本的I/O操作和文件系统操作(如文件的命名、创建、移动和引用)。

Python中处理文件路径和文件系统操作的传统方式,是通过os和os.path模块中的函数来完成的。自Python3.5开始,引入了新的pathlib库,可以用更加面向对象、更统一的方式来完成文件操作。

 

(一)路径和路径名

所有的操作系统都会用字符串来引用文件和目录,字符串中包含了给定文件或目录的名称。这种字符串通常被称为“路径名”,有时简称为路径。因为路径名是个字符串,所以在使用时也带来了一定的复杂性。Python做了大量工作,提供了很多函数来避免这种复杂性。

路径名在各种操作系统中的写法都非常相似,因为几乎所有操作系统都把文件系统建模为树状结构,磁盘就是根目录,文件夹、子文件夹就是分支、子分支,依此类推。

对于Windows的路径名大家可能比较熟悉:

C:\Windows\Help\Help

当然,对于不同的操作系统路径名的精确写法还是有差别的。然而Python提供的函数和常量可完成常见的路径名操作,而不必关心这些语法上的细节。只要稍加小心,就可以不管底层文件系统是什么,都能编写出正常运行的Python程序。

1)绝对路径和相对路径

操作系统支持以下两种路径表示法:

  • 绝对路径指明了文件在整个文件系统中的确切位置,不会有什么歧义。绝对路径将给出文件的完整路径,从文件系统的根目录开始。
  • 相对路径指明了文件相对于文件系统某点的位置,该相对点并不是由相对路径本身给出的。相对路径起始点的绝对位置,是由调用时的上下文给出的。

相对路径需要根据上下文来确定实际的位置,上下文一般由两种方式来给出。

  • 相对简单的方式是在已有的绝对路径上添加相对路径,以生成一个新的绝对路径;
  • 相对路径获得上下文的第二种方式,是通过对当前工作目录的隐式引用。当前工作目录是指,在运行Python程序的任意时刻,程序记录的当前所在目录。例如,os.listdir(path)命令用了相对路径作为参数,则该相对路径就以当前工作目录作为锚点(anchor),结果中文件名所在目录的路径就是当前工作目录加上参数指定的相对路径。

2)当前工作目录

每当在计算机上编辑文档时,都会有一个位置概念,即文档在计算机文件结构中所处的当前位置。类似地,每当Python运行时,也有一个当前位置地概念,即某时刻所处地目录结构。这一点很重要,因为程序可能需要获取当前目录中的文件列表。Python程序所在的目录被称为该程序的当前工作目录,当前工作目录可能与存放该程序的目录不同。

可以使用os.getcwd()命令(获取当前工作目录)查看Python初始状态下的当前工作目录:

>>> import os
>>> os.getcwd()
'D:\\python37'

以上是在windows上面的。注意调用函数os.getcwd()时是不带参数的,以强调返回值不是固定不变的。如果执行了修改当前工作目录的命令,其返回结果就会发生变化。当前工作目录可能是存放Python程序的目录,也可能是启动Python时所在的目录。在Linux系统上,返回结果会是/home/myuser,也就是当前用户的主目录(home)。

在windows上,路径中会有额外的反斜杠插入,因为Windows系统用“/”作为路径分隔符。

下面输入:

>>> os.listdir(os.curdir)
['as.py', 'assert.py', 'circle.py', 'circle__cm.py', 'conclusion.py', 'DLLs', 'Doc', 'include', 'Lib', 'libs', 'LICENSE.txt', 'NEWS.txt', 'pymysql', 'python.exe', 'python3.dll', 'python37.dll', 'pythonw.exe', 'qwes.py', 'Scripts', 'tcl', 'Tools', 'vcruntime140.dll', '__pycache__', '列表.py']

属性os.curdir返回的是系统用来表示当前目录的字符串。该字符串是个相对路径,也就是说os.listdir会将其加到当前工作目录的路径之后,路径其实没有发生变化。上述命令将会返回当前工作目录中所有文件/文件夹的列表。任选择一个文件夹名称,键入以下命令:

>>> os.chdir('Lib')     #修改当前目录
>>> os.getcwd()
'D:\\python37\\Lib'

由上可见,Python会移入os.chdir函数参数指定的文件夹中。这时再次调用os.listdir(os.curdir),将会返回folder文件夹中的文件列表,因为os.curdir将相对新的当前工作目录而言。Python中有很多文件操作系统,都是以这种方式使用当前工作目录的。

 

3)使用pathlib模块访问目录

用pathlib获取当前目录的步骤如下:

>>> import pathlib
>>> cur_path = pathlib.Path()
>>> cur_path.cwd()
WindowsPath('D:/python37')

pathlib不提供像os.chdir()那样改变当前工作目录的函数,但可以通过创建path对象来新建文件夹。

 

4)路径名的处理

 

使用os.path处理路径名

Python提供了处理路径名的功能,这些功能由os.path子模块中的一些函数和常量构成,利用这些功能处理路径名时,就无须显式采用任何与操作系统相关的语法了。路径名仍然用字符串来表示,但不用当作字符串来处理了。

可用os.path.join函数在各种操作系统中构建一些路径名:

>>> import os
>>> print(os.path.join('bin','utils','disktools'))
bin\utils\disktools

os.path.join()函数将参数解释为一系列的目录名或文件名,这些路径将被拼接起来形成单个字符串,底层操作系统将该字符串理解为相对路径。

注意,os.path.join()函数可以由一系列目录或文件名生成文件路径,并且不必关心底层操作系统的语法规则。上面代码是在Windows系统中运行的,结果返回的是反斜杠连接的路径名。同样在Linux/UNIX系统中,会采用正斜杠作为路径名。如果想让构建文件路径的方式不受未来运行环境的限制,那么采用os.path.join就是基本的方式。

os.path.join的参数不一定非得是单个目录或文件名,也可以是子路径,连起来可以形成更长的路径名。以下例子演示了在Windows环境中的这种用法,并且这时必须在字符串中使用双反斜杠。注意,这时用正斜杠(/)输入路径名也是可以的,因为Python在与Windows操作系统交互之前会进行转换:

>>> import os
>>> print(os.path.join('mydir\\bin', 'utils\\disktools\\chkdisk'))
mydir\bin\utils\disktools\chkdisk

当然,如果始终用os.path.join来建立路径,就几乎不必操心上述问题。可以写成可移植的形式:

>>> path1 = os.path.join('mydir', 'bin')
>>> path2 = os.path.join('utils', 'disktools', 'chkdisk')
>>> print(os.path.join(path1, path2))
mydir\bin\utils\disktools\chkdisk

在不同的底层系统中,os.path.join()函数还会对绝对路径名和相对路径名做出一定的处理。

Linux/unix中:

  • 绝对路径始终以/开头,因为单个斜杠表示整个系统的顶级目录,其他所有内容都在其下,包括可用的各种软盘和CD驱动器。
  • UNIX中的相对路径是指不以斜杠开头的合法路径。

Windows中:

  • 如果路径名以驱动器字母开头,后跟冒号和反斜杠,那么就是绝对路径,如C:\Program\Files\Doom。注意,如果仅是C:,尾部不带反斜杠,那么并不能可靠地表示C:驱动器地顶级目录。必须用C:\来引用C:驱动器地顶级目录。这种要求沿用了DOS的传统,而不是Python的设计规则。
  • 如果路径名既不以驱动器字母开头,也不以反斜杠开头,那么就是相对路径,如mydirectory\letters\business。
  • 如果路径名以\\开头,后跟服务器名称,那么是网络资源的路径。
  • 其他路径都被视为无效路径。

无论采用什么操作系统,os.path.join都不会对生成的路径名进行完整性检查。生成的路径名中可能会包含操作系统禁用的字符,不同的操作系统禁止用于路径名称的字符各不相同。如果需要对结果进行检查,最好的解决方案可能就是自行编写一个小小的路径合法性检查函数。

 

其他常用的路径名处理函数:

>>> import os

#将路径名拆分为文件名(路径尾部的单个文件或目录名称)和其余部分

>>> print(os.path.split(os.path.join('name', 'directory', 'path')))
('name\\directory', 'path')

#只返回路径中的文件名

>>> os.path.basename(os.path.join('some', 'directory', 'path.jpg'))
'path.jpg'

#只返回前面的路径部分

>>> os.path.dirname(os.path.join('some', 'directory', 'path.jpg'))
'some\\directory'

#处理以.标识的文件扩展名

>>> os.path.splitext(os.path.join('some', 'directory', 'path.jpg'))
('some\\directory\\path', '.jpg')

#将环境变量扩展为完成的路径

>>> os.path.expandvars('$HOME\\temp')
'C:\\Users\\administrator\\temp'

 

用pathlib处理路径名

这里用到了Path对象的方法。

>>> from pathlib import Path
>>> cur_path = Path()
>>> print(cur_path.joinpath('bin', 'utils', 'disktools'))
bin\utils\disktools

直接用“/”操作符也可以达到同样效果:

>>> cur_path / 'bin' / 'utils' / 'disktools'
WindowsPath('bin/utils/disktools')

Path对象的常用属性:

#Path对象的parts属性将会返回一个元组,元素就是路径的各个组成部分

>>> a_path = Path('bin/utils/disktools')
>>> print(a_path.parts)
('bin', 'utils', 'disktools')

#Path对象的name属性将只返回路径的文件名部分

>>> a_path = Path('some', 'directory', 'path.jpg')
>>> a_path.name
'path.jpg'

#parent属性将返回除文件名外的部分

>>> print(a_path.parent)
some\directory

# Path对象的suffix属性将返回带.的扩展名部分

>>> a_path.suffix
'.jpg'

Path对象还拥有其他一些方法,可灵活地对路径名和文件进行处理,请参考官方文档。

 

(二)获取文件信息

文件路径应该用来表示硬盘中的实际文件和目录。因为需要了解路径指向的文件信息,所以路径对象还有可能被传来传去。Python为获取文件信息提供了很多函数。

  • os.path.exists():接收一个路径参数,如果参数是文件系统中存在的路径,则返回True,否则返回False。
>>> os.path.exists('C:\Huawei Share')
True
  • os.path.isfile():接收一个路径参数,当且仅当接收的路径表示某种类型的普通数据文件(包括可执行文件)时,函数返回True,否则返回False(包括参数指向的不是文件系统中的内容)
>>> os.path.isfile('file:///C:/Users/administrator/Desktop/机械制造基础/ch01.pdf')
False
>>> os.path.isfile('D:\Z\文件夹\序号.docx')
True
  • os.path.isdir():接收一个路径参数,当且仅当参数表示的是目录时,函数返回True,否则返回False。
>>> os.path.isdir('file:///C:/Users/administrator/Desktop/机械制造基础/ch01.pdf')
False
>>> os.path.isdir('D:\Z')
True
  • os.scandir():获取整个目录下文件的更为完整的信息,os.scandir将返回os.DirEntry迭代器对象。os.DirEntry对象能够展示目录中每一项的文件属性,因此用os.scandir将会比组合使用os.listdir与os.path操作更加快速有效。
  • 例如,要知道某个目录项引用的是文件还是目录,os.scandir的功能就有用得多,能够获取到更多的目录信息。os.DirEntry对象具备的方法,很多都与上面提到的os.path函数相对应,包括exists、is_dir、is_file、is_socket和is_symlink。
  • os.scandir还支持由with提供的上下文管理器,为了确保资源的妥善释放,推荐使用这个。以下示例将遍历目录中的所有条目,打印出条目的名称以及是否为文件:
>>> with os.scandir(".") as my_dir:
	for every in my_dir:
		print(every.name, every.is_file())

		
as.py True
assert.py True
circle.py True
circle__cm.py True
conclusion.py True
DLLs False
Doc False
include False
Lib False
libs False
LICENSE.txt True
NEWS.txt True
pymysql False
python.exe True
python3.dll True
python37.dll True
pythonw.exe True
qwes.py True
Scripts False
tcl False
Tools False
vcruntime140.dll True
__pycache__ False
列表.py True

 

(三)文件系统的其他操作

除了获取文件相关信息之外,Python还支持某些对文件系统的直接操作,这时通过os模块中的一些基础而有用的函数来完成的。

  • 在glob模块中有个glob函数,能够扩展路径名中的通配符和字符序列,返回当前工作目录中匹配的文件。“*”将匹配任意字符序列,“?”将匹配任意单个字符:
>>> glob.glob("*")
['as.py', 'assert.py', 'circle.py', 'circle__cm.py', 'conclusion.py', 'DLLs', 'Doc', 'include', 'Lib', 'libs', 'LICENSE.txt', 'NEWS.txt', 'pymysql', 'python.exe', 'python3.dll', 'python37.dll', 'pythonw.exe', 'qwes.py', 'Scripts', 'tcl', 'Tools', 'vcruntime140.dll', '__pycache__', '列表.py']
>>> glob.glob("NEWS.t?t")
['NEWS.txt']
  • os.rename可以重命名(移动)文件或目录,os.rename不仅可以在目录内移动(重命名)文件,还可以子啊目录之间移动文件:
>>> os.rename('列表.py','列表liebiao.py')
>>> os.listdir(os.curdir)
['as.py', 'assert.py', 'circle.py', 'circle__cm.py', 'conclusion.py', 'DLLs', 'Doc', 'include', 'Lib', 'libs', 'LICENSE.txt', 'NEWS.txt', 'pymysql', 'python.exe', 'python3.dll', 'python37.dll', 'pythonw.exe', 'qwes.py', 'Scripts', 'tcl', 'Tools', 'vcruntime140.dll', '__pycache__', '列表liebiao.py']
  • os.remove可以删除文件,注意不能用os.remove删除目录。这时一种安全限制,确保不会因为误操作将整个目录都删除了:
>>> os.remove('列表liebiao.py')
>>> os.listdir(os.curdir)
['as.py', 'assert.py', 'circle.py', 'circle__cm.py', 'conclusion.py', 'DLLs', 'Doc', 'include', 'Lib', 'libs', 'LICENSE.txt', 'NEWS.txt', 'pymysql', 'python.exe', 'python3.dll', 'python37.dll', 'pythonw.exe', 'qwes.py', 'Scripts', 'tcl', 'Tools', 'vcruntime140.dll', '__pycache__']
  • 如果要创建目录,可以使用os.makedirs或os.mkdir,这两个区别是,os.makedirs会连同必要的中间目录一起创建,但os.mkdir不会:
>>> os.makedirs('mydir')
>>> os.listdir(os.curdir)
['as.py', 'assert.py', 'circle.py', 'circle__cm.py', 'conclusion.py', 'DLLs', 'Doc', 'include', 'Lib', 'libs', 'LICENSE.txt', 'mydir', 'NEWS.txt', 'pymysql', 'python.exe', 'python3.dll', 'python37.dll', 'pythonw.exe', 'qwes.py', 'Scripts', 'tcl', 'Tools', 'vcruntime140.dll', '__pycache__']
>>> os.path.isdir('mydir')
True
  • 使用os.rmdir删除空目录,如果视图删除非空目录,则会引发异常:
>>> os.rmdir('mydir')
>>> os.listdir(os.curdir)
['as.py', 'assert.py', 'circle.py', 'circle__cm.py', 'conclusion.py', 'DLLs', 'Doc', 'include', 'Lib', 'libs', 'LICENSE.txt', 'NEWS.txt', 'pymysql', 'python.exe', 'python3.dll', 'python37.dll', 'pythonw.exe', 'qwes.py', 'Scripts', 'tcl', 'Tools', 'vcruntime140.dll', '__pycache__']

如果要删除非空目录,可以使用shutil.rmtree。

 

设计一个计算文件大小的程序

这里通过os模块的一些函数,读取文件目录或者是文件的大小,并且进行输出。

import os

# 自定义统计目录大小函数
def stat_dir_size(dir_path):

    total = 0

    if os.path.isdir(dir_path):
        dlist = os.listdir(dir_path)
        for f in dlist:
            subdir = os.path.join(dir_path, f)
            if os.path.isfile(subdir):
                total = total + os.path.getsize(subdir)
            if os.path.isdir(subdir):
                total = total + stat_dir_size(subdir)
        return total

    elif os.path.isfile(dir_path):
        return os.path.getsize(dir_path)
    else:
        return -1
    
# 测试
path = input("请输入目录:")
size = stat_dir_size(path)
if size == -1:
    print("(Error) \"{}\" is not a directory.".format(path))
else:
    print("目录大小:", size, "Bytes")

 

(四)file对象

Python处处皆对象,文件也是Python的对象。

 

1)打开和关闭文件

python使用open()函数打开文件。

  • open不会读取文件中的内容,而是返回一个file对象,可用于访问被打开的文件。
  • file对象会对文件及读写位置进行跟踪记录。
  • open的第一个参数是路径名,第二个参数是表示文件打开方式的字符串。‘r’表示以只读模式打开文件;‘w’表示以写入模式打开文件,文件中已有的数据将被全部清除;‘a’表示以追加模式打开文件,新数据将被追加到文件已有数据的尾部。如果打开文件只是为了读取数据,第二个参数可以省略,其默认值就是‘r’。
  • open还有第三个可选参数,定义了文件读写缓冲模式。缓冲(buffering)是将数据暂时保存在内存中,直到需要读取或写入数据足够多,值得花费一次磁盘访问的时间时,再去执行真正的磁盘读写。
  • open方法还有其他参数,其中encoding控制着文本文件的编码格式,以及文本文件的换行符处理方式。

 

>>> file_open = open('README.txt','r')
>>> while True:
	print(file_open.readline())

	
Traceback (most recent call last):
  File "<pyshell#3>", line 2, in <module>
    print(file_open.readline())
UnicodeDecodeError: 'gbk' codec can't decode byte 0xac in position 39: illegal multibyte sequence

以上代码运行之后会报错,这是一种常见的编码解码错误的问题,解决方案如下:

(0)将‘gbk’换成‘utf-8’也适用。 
(1)、首先在打开文本的时候,设置其编码格式,如:open(‘1.txt’,encoding=’gbk’); 
(2)、若(1)不能解决,可能是文本中出现的一些特殊符号超出了gbk的编码范围,可以选择编码范围更广的‘gb18030’,如:open(‘1.txt’,encoding=’gb18030’); 
(3)、若(2)仍不能解决,说明文中出现了连‘gb18030’也无法编码的字符,可以使用‘ignore’属性进行忽略,如:open(‘1.txt’,encoding=’gb18030’,errors=‘ignore’); 
(4)、还有一种常见解决方法为open(‘1.txt’).read().decode(‘gb18030’,’ignore’)

 

当我们将代码修改之后:

>>> file_open = open('README.txt','r',encoding = 'utf-8')
>>> while True:
	print(file_open.readline())

	
# Python_Learning

我们会发现,现在README.txt中的文本可以读取出来了,但是新的问题又来了,就是我们这个while将会一直循环下去,因为这里的readline()函数:

  • 第一次调用readline函数将返回file对象的第一行,包括第一个换行符在内。如果文件中不包含换行符,则返回整个文件的内容;
  • 下一次调用readline函数将返回file对象的第二行(如果存在),依此类推。
  • 当file对象中没有数据可读了,将会返回空的字符串。

上面代码之所以会出现死循环,就是应为readline函数返回的空字符串一直被打印。解决办法也很简单:

>>> file_open = open('README.txt','r',encoding = 'utf-8')
>>> while file_open.readline() != "":
	print(file_open.readline())

这里为循环设置一个推出条件:当readline函数返回空的字符串时就退出。

 

对file对象读写完毕后,应该将其关闭。关闭file对象会释放系统资源,并允许该文件能被其他代码读写,通常能提高程序的可靠性。对于小型脚本程序而言,不关闭文件对象通常不会造成太大的影响。在脚本或程序运行结束时,文件对象将会被自动关闭,对于大型程序来说,打开的文件对象太多,可能会耗尽系统资源,导致程序异常终止。

当文件对象使用完毕后,可以用close方法来关闭它:

>>> file_open = open('README.txt','r',encoding = 'utf-8')
>>> print(file_open.readline())
Python_Learning

>>> file_open.readline() != ""
True
>>> file_open.close()

 

 

2)使用with关键字

对于打开之后需要关闭的情况,python提供了with关键字,可以实现自动关闭文件:

>>> file_open = open('README.txt','r',encoding = 'utf-8')
>>> with open('README.txt','r',encoding = 'utf-8') as file_open:
	while file_open.readline() != "":
		print(file_open.readline())

		
# 以下为README.txt中的内容:

本项目包含 Python 的相关练习和作业代码

以周(week)为目录进行编排,具体如下:

对于以上代码中的README.txt文件,存在于我的Python目录下面,所以直接输入文件名字就可以访问了。当然输入其他的文件的路径名也是可以进行访问的。

在Spyder中打开文件:

with open('D:\python37\NEWS.txt', 'r') as file_object:
    line = file_object.readline()

这里会报错如下:

SyntaxError: (unicode error) 'unicodeescape' codec can't decode bytes in position 11-12: malformed \N character escape

这是由于路径名中的反斜杠也代表着转义字符,window 读取文件可以用\,但是在字符串中\是被当作转义字符来使用,经过转义之后可能就找不到路径的资源了,例如\t会转义为tab键。

总结有三种解决方法:

一:更换为绝对路径的写法
func1("C:\\Users\\renyc")

二:显式声明字符串不用转义(加r)
func1(r"C:\Users\renyc")

三:使用Linux的路径/
func1("C:/Users/renyc")

修改后可以正常运行:

with open(r'D:\python37\NEWS.txt', 'r',encoding = 'utf-8') as file_object:
    #line = file_object.readline()
    while file_object.readline() != "":
        print(file_object.readline())

 

3)读写文本函数

最常用的文本文件读取函数就是readline,上面已经介绍过了。用这个函数可以读取文本文件,还可以用来计算出来文件中的文本行数:

with open(r'D:\python37\filetext.txt','r') as file_object:
    
    #line = file_object.readline()
    while file_object.readline() != "":
        count += 1
        print(file_object.readline())
        
    print(count)

注意:以上涉及到open函数打开文件时,对应的目录下面给都需要由相应的文件,否则会报FileNotFoundError错误。

readlines函数

具体到以上问题,更简短的设计方案是用内置的readlines方法。readlines将读取文件中的所有行,并作为字符串列表返回,每行就是一个字符串,尾部的换行符仍然保留:

with open(r'D:\python37\filetext.txt','r') as file_object:
    file_list = file_object.readlines()
    print(file_list)
    print(len(file_list))

输出:

['hello python\n', 'hello world\n', 'hello China']
3

当然,如果要对一个大型文件统计行数,readlines方法可能会导致计算机内存不足,因为它会一次性将整个文件读入内存。如果要从大型文件中读取一行,偏偏该文件中不含换行符,那么用了readline也可能导致内存溢出,当然这种情况不大可能发生。为了应对这种情况,readline和readlines都可带一个可选参数,可以控制每次读取的数据量。详细信息可以看看官方文档。

将file对象视为迭代器

另一种遍历文件全部数据行的方法,是将file对象视为for循环中的迭代器:

file_object = open(r'D:\python37\filetext.txt','r')
count = 0
for line in file_object:
    count += 1
print(count)
file_object.close()

迭代器方式具备一个优点,每行数据都是按需读入内存的。因此即便是面对大型文件,也不用担心内存不足的问题。另外,迭代器方式还具有更简单、可读性更好的优点。

写入文件

与readline和readlines方法相对应的写入方法是write和writelines。注意,不存在writeline方法。

write方法将写入一个字符串,如果字符串中包含了换行符,则可以一次写入多行。

file_object = open(r'D:\python37\filetext.txt','a')
file_object.write('Hello nefu\n')
file_object.close()
with open(r'D:\python37\filetext.txt','r') as file_object:
    file_list = file_object.readlines()
    print(file_list)
    print(len(file_list))

输出:

['hello python\n', 'hello world\n', 'hello ChinaHello nefuHello nefuHello nefuHello nefu\n', 'Hello nefu\n', 'Hello nefu\n']
5

记住,要在写入文件之后关闭文件,再在只读模式下用readlines读取文本。如果直接读取会报UnsupportedOperation错误。

虽然这里显示出来了后面的\n换行符,但是世界打开这个文件的时候是这样的;

python文件操作join python文件操作步骤_Python

 

 

(五)文件操作的其他模块

Python文件操作除了上面提道德os模块以外,Python还提供了其他模块。在不同的场合下,它们工作的效率也不同,这里也只是简单介绍一下,等我们真正去调试一个项目代码的时候,就会有更深切的体会了。

还有pathlib、struct、pickle、shelve等可以去用。它们的效率、安全性也不同,这里先介绍这些。

剩下的还要我们慢慢去了解。