学习目标

掌握文件的基本操作
掌握二进制文件的处理
了解文件的系统操作
了解常见文件格式的读写

文件分类

按文件中数据的组织形式分类:

  1. 文本文件
  • 存储的是常规字符串,由若干文本行组成,每行以换行符“\n”结尾。
  • 可以使用文本编辑器进行显示、编辑并且能够直接阅读。
  • 如网页文件、记事本文件、程序源代码文件等。
  1. 二进制文件
  • 存储的是字节串bytes。
  • 需要使用专门的软件进行解码后才能读取、显示、修改或执行。
  • 如图形图像文件、音视频文件、可执行文件、数据库文件等。

    打开文件

    向(从)一个文件写(读)数据之前,需要先创建一个和物理文件相关的文件对象,然后通过该文件对象对文件内容进行读取、写入、删除、修改等操作,最后关闭并保存文件内容。
    Python内置的open()函数可以按指定的模式打开指定的文件并创建文件对象。 ``` ‘’’ open函数打开文件file,返回一个指向文件file的文件对象file_object ‘’’

file_object = open(file, mode = ‘r’, buffering = -1, encoding)

  1. open函数参数说明:
  2. - filename:要访问的文件名称。file是一个包含文件所在路径及文件名称的字符串值,如'C:\\User\\test.txt'。(这里要注意是两个右斜杠)
  3. - mode:指定打开文件后的处理方式:只读,写入,追加等。这个参数是非强制的,默认文件访问模式为只读(r)。
  4. - buffering0表示不缓存,1表示缓存。大于1表示缓冲区的大小。-1表示缓冲区的大小为系统默认值。
  5. - encoding:指定对文本进行编码和解码的方式,只适用于文本模式,可以使用Python支持的任何格式,如gbkutf8cp936等。
  6. Python使用open()方法打开一个文件,并返回一个可迭代的文本对象,通过该文本对象可以对文件进行读写操作。如果文本不存在、访问权限不够、磁盘空间不足或其他原因导致创建文件对象失败,open()函数就会抛出一个IOError的错误,并且给出错误码和详细的信息。<br />磁盘满、无法写入,打开文件要读取但文件不存在,或文件路径错误。这些是文件读写过程中随时可能遇到的问题。<br />凡是涉及文件输入输出的操作,这类问题在程序设计时是必然要考虑的因素,否则程序的设计并不完整和严谨。
  7. <a name="e9KdA"></a>
  8. ## 文件打开模式
  9. 打开模式定义了打开文件后的处理方式。
  10. | 模式 | 功能描述 |
  11. | --- | --- |
  12. | r | 只读模式 |
  13. | w | 写模式,若存在则覆盖原有内容 |
  14. | a | 追加模式 |
  15. | r+ | 读写,不创建 |
  16. | w+ | 读写,若不存在则创建 |
  17. | a+ | 追加模式但可读 |
  18. | rt, wt | 默认为文本方式,相当于r, w |
  19. | rb, wb | 读写二进制文件 |
  20. 文件打开的不同模式的详细描述:
  21. | 模式 | 描述 |
  22. | --- | --- |
  23. | r | 以只读方式打开文件,文件的指针放在文件的开头。这是默认模式,可省略。 |
  24. | r+ | 以读写格式打开一个文件,文件指针放在文件的开头。 |
  25. | w | 以写入格式打开一个文件,如果该文件已存在,则将其覆盖。如果该文件不存在,则创建新文件。 |
  26. | w+ | 以读写格式打开一个文件,如果该文件已存在则将其覆盖。如果该文件不存在,则创建新文件。 |
  27. | a | 以追加格式打开一个文件,如果该文件已存在,文件指针将会放在文件的结尾。也就是说,新的内容将会被写入到已有内容之后。如果该文件不存在,创建新文件进行写入。 |
  28. | a+ | 以读写格式打开一个文件,如果该文件已存在,文件指针将会放在文件的结尾。如果该文件不存在,创建新文件用于读写。 |
  29. <a name="SEv0d"></a>
  30. ## 文件对象属性
  31. 一个文件被打开后,返回一个文件对象,通过文件对象可以得到有关该文件的各种信息。<br />文件对象的属性如表所示:
  32. | 属性 | 描述 |
  33. | --- | --- |
  34. | closed | 判断文件是否关闭,如果文件已被关闭,返回True;否则返回False |
  35. | mode | 返回被打开文件的访问模式 |
  36. | name | 返回文件的名称 |
  37. ```python
  38. file_object = open('C:\\test\\scores.txt', 'r')
  39. print('文件名:', file_object.name)
  40. print('是否已关闭:', file_object.closed)
  41. print('访问模式:', file_object.mode)

文件对象

文件对象常用方法

方法 功能描述
close() 刷新缓冲区里还没写入的信息,并关闭该文件
flush() 刷新文件内部缓冲,把内部缓冲区的数据立刻写入文件,但不关闭文件
next() 返回文件下一行
read([size]) 从文件的开始位置读取指定的size个字符数,如果未给定则读取所有
readline() 读取整行,包括“\n”字符
readlines() 把文本文件中的每行文本作为一个字符串存入列表中并返回该列表
seek(offset[, from]) 用于移动文件读取指针到指定位置,offset为需要移动的字节数;from指定从哪个位置开始移动,默认值为0,0代表从文件开头开始,1代表从当前位置开始,2代表从文件末尾开始。
tell() 方法返回文件的当前位置,即文件指针当前位置
truncate([size]) 删除从当前指针位置到文件末尾的内容。如果指定了size,则不论指针在什么位置
write(str) 把字符串str的内容写入文件中,没有返回值。由于缓冲,字符串内容可能没有加入到实际的文件中,直到调用flush()或close()方法被调用。
writelines([str]) 用于向文件中写入字符串序列
writabe() 测试当前文件是否可写
readable() 测试当前文件是否可读

文件关闭

当对文件内容操作完成以后,必须关闭文件,这样能够保证所做的修改得到保存。
close()方法用于关闭一个已打开的文件,可以将缓冲的数据写入文件,然后关闭文件。
关闭后的文件不能再进行读写操作,否则会触发ValueError错误。
close()方法允许调用多次。
flush()方法将缓冲的数据写入文件,但是不关闭文件。
使用上下文管理语句with可以自动管理资源,在代码块执行完毕后自动还原进入该代码块之前的现场或上下文。

  1. with context_expr[as var]:
  2. with语句块
  1. with open('myfile.txt') as f:
  2. for line in f:
  3. print(line, end = '')

使用with语句的好处:

  • 使用with自动关闭资源,可以在代码块执行完毕后还原进入该代码块时的现场。
  • 不论何种原因跳出with块,不论是否发生异常,总能保证文件被正确关闭,资源被正确释放。

    文件读写

    写文件

    当一个文件以“写”的方式打开后,可以使用write()方法和writelines()方法,将字符串写入文本文件。
  1. write()方法:

write(s)方法用于向一个打开的文件中写入指定的字符串。在文件关闭前或缓冲区刷新前,字符串内容存储在缓冲区中,这时在文件中是看不到写入的内容的。
write()方法不会在字符串的结尾添加换行符“\n”。

  1. '''
  2. 参数str:要写入文件的字符串
  3. 返回值:返回的是写入的字符长度
  4. '''
  5. fileObject.write(str)

在操作文件时,每调用一次write()方法, 写入的数据就会追加到文件末尾。

  1. '''
  2. 程序运行时是,会在程序的当前路径下,生成一个名为test.txt文件,打开该文件,可以看到数据成功被写入
  3. '''
  4. fp = open('test.txt', 'w')
  5. fp.write('My name is Guido van Rossum!\n')
  6. fp.close()

注意:当向文件写入数据时,如果文件不存在,那么系统会自动创建一个文件并写入数据。如果文件存在,那么会清空原来文件的数据,重新写入新数据。

  1. writelines()方法

writelines()方法把字符串列表写入文本文件,不添加换行符“\n”。

  1. data = ['My', 'name', 'is', 'John!\n', 'How', 'are', 'you!']
  2. with open('data_desc.txt', 'w') as fp:
  3. fp.writelines(data)
  4. with open('data_desc.txt', 'r') as fp:
  5. for line in fp:
  6. print(line)

读文件

文件打开后从文件中读取数据的三种方式:

方法 功能描述
read([size]) 从文件读取指定的size个字符数,如果未给定则读取所有。
readline() 读取整行
readlines() 把文本文件中的每行文本作为一个字符串存入列表中并返回该列表。

注意:打开一个已经存在的文件,读取正常,当试图打开一个不存在的文件,系统会给出错误信息。

每种方法可以接受一个变量以限制每次读取的数据数量。

  1. read()方法

read()方法从文件当前位置起读取size个字符串,若无参数size,则表示读取至文件结束为止。如果使用多次,那么后面读取的数据是从上次读完后的位置开始。

  1. '''
  2. 参数size:从文件中读取的字符数。如果没有指定字符数,那么就表示读取文件的全部内容。
  3. 返回值:返回从字符串读取的字符内容。
  4. '''
  5. fileObject.read(size)
  1. fp = open('test.txt', 'r')
  2. # 读取10个字节数据
  3. content = fp.read(10)
  4. print(content)
  1. readline()方法

该方法每次读出一行内容,该方法读取时占用内存小,比较适合大文件,该方法返回一个字符串对象。

  1. '''
  2. 返回值:返回读取的字符串
  3. '''
  4. fileObject.readline()
  1. fp = open('test.txt', 'r')
  2. line = fp.readline()
  3. print('读取第一行:%s' %(line))
  4. print('--------------华丽的分割线------------------')
  5. while line:
  6. print(line)
  7. line = fp.readline()
  8. fp.close()
  9. print('文件', f.name, '已经成功分行读出!')
  1. readlines()方法

readlines()方法读取文件的所有行,保存在一个列表中,每行作为一个元素,但读取大文件会比较占内存。该列表可以由Python的for … in … 结构进行处理。

  1. '''
  2. 返回值:此方法返回包含所有行的列表
  3. '''
  4. fileObject.readlines()
  1. fp = open('test.txt', 'r')
  2. lines = fp.readlines()
  3. print('行的数据类型:', type(lines))
  4. print('列表形式存放每一行:%s' %(lines))
  5. print('-----------------华丽的分割线------------------')
  6. for line in lines:
  7. line = line.strip()
  8. print('读取的数据为:%s' %(line))
  9. fp.close
  10. print('文件', f.name, '已经成功把所有行读出!')

Windows平台下open()函数在打开文件的时候缺省的编码(encoding)为gbk(cp936),并不是UTF-8,因此在打开文件的时候应指定编码为UTF-8,否则读取文件会出现错误。

  1. fname = r'C:\test\shi.txt'
  2. with open(fname, 'r', encoding = 'utf-8') as f:
  3. lines = f.readlines()
  4. for line in lines:
  5. print(line.rstrip())
  1. 从文件逐行读取数据
    1. with open('test.txt') as f:
    2. for line in f:
    3. print(line, end = '')

    文件指针的定位

    文件对象的tell()方法返回文件的当前位置,即文件指针当前位置。
    使用文件对象的read()方法读取文件之后,文件指针到达文件的末尾,如果再来一次read()将会发现读取的是空内容,如果想在此读取全部内容,或读取文件中的某行字符,必须将文件指针移动到文件开始或某行开始,这可通过文件对象的seek()方法来实现。 ```python ‘’’ 函数作用:用于移动文件读取指针到指定位置 offset:需要移动的字节数 whence:指定从哪个位置开始移,默认值为0。
    1. 0代表从文件开头开始,1代表从当前位置开始,2代表从文件末尾开始。
    ‘’’

seek(offset[, whence])

  1. > 注意:Python3不允许非二进制打开的文件相对于文件末尾的定位
  2. ```python
  3. '''
  4. 运行结果显示s为空串,通过tell()方法查看文件指针,可以看出文件的指针在该文件的末尾。
  5. '''
  6. with open('test.txt','a+') as f:
  7. s = f.read(5)
  8. print('in file ->', s)
  9. point = f.tell()
  10. print(point)
  1. with open('test.txt', 'a+') as f:
  2. f.write('\n Python is a programming language. \n')
  3. # 清空缓冲区,确保数据保存到文件
  4. f.flush()
  5. # 将文件指针转移到文件首部
  6. f.seek(0)
  7. s = f.readlines()
  8. # 逐行读取文件数据
  9. for line in s:
  10. print(line)

二进制文件

二进制文件包括图像文件、可执行文件、音视频文件、字处理文档等。
二进制文件不能使用记事本或其他文本编辑软件直接读写。

二进制文件的读写

二进制文件读写的是bytes字节串。

  1. '''
  2. 由于写入的是一个字符串,非字节串,系统会抛出异常。
  3. '''
  4. with open('test.bt', 'wb') as fp:
  5. fp.write('abcd')

二进制文件模式表:

文件使用方式 意义
rb 只读打开一个二进制文件,只允许读数据。如文件存在,则打开后可以顺序读;如文件不存在,则打开失败。
wb 只写打开或建立一个二进制文件,只允许写数据。如文件不存在,则建立一个空文件;如文件已经存在,则把原文件内容清空。
ab 追加打开一个文本文件,并在文件末尾写数据。如文件不存在,则建立一个空文件;如文件已经存在,则把原文件打开,并保持原内容不变,文件位置指针指向末尾,新写入的数据追加在文件末尾。

因为二进制文件是字节流,因此二进制文件在打开读写时不用指定编码,也不存在readline,readlines读一行或多行的操作函数。
一般二进制文件使用read函数读取,使用write函数写入。

  1. 写二进制文件 ```python ‘’’ 把二进制数据data写入文件 ‘’’

文件对象.write(data)

  1. 2. 读二进制文件
  2. ```python
  3. '''
  4. 如果不指定要读取的字符数n,使用read()读,则读到整个文件的内容。
  5. 如果使用read(n)指定要读取的字符数,要么就按要求读取n个字符;
  6. 如果要读n个字符,而文件没有那么多字符,那么就读取所有文件内容。
  7. '''
  8. 文件对象.read(n)
  1. def writeFile():
  2. fobj = open('abc.txt', 'wb')
  3. fobj.write('Python文件'. encode())
  4. fobj.close()
  5. def readFile():
  6. fobj = open('aabc.txt', 'rb')
  7. data = fobj.read()
  8. print(data.decode())
  9. fobj.close()
  10. writeFile()
  11. readFile()
  1. with open('test.bt', 'wb+') as fp:
  2. # 转换成使用utf-8编码
  3. fp.write(bypes('我爱中国'.encode('utf-8')))
  4. # 文件指定定位到开头
  5. fp.seek(0)
  6. # 解码方式和编码方式要一致
  7. b = fp.read().decode('utf-8')
  8. print(b)

可以看出如果直接用文本文件或二进制文件格式存储Python中的各种对象,通常需要进行繁琐的转换。
Python程序在内存中的数据一般是放置在列表、元组、字典等各类对象之中。当进行文件保存或网络处理时,不能直接送入这些对象本身,必须将这些对象进行序列化,以转化为字节码才能进行处理。
第七章 文件操作 - 图1

  1. import pickle
  2. name = '张三'
  3. age = 20
  4. scores = [65, 70, 76, 80]
  5. with open('test.bt', 'wb+') as fp:
  6. # 写入文件
  7. pickle.dump(name, fp)
  8. pickle.dump(age, fp)
  9. pickle.dump(scores, fp)
  10. # 将文件指针移动到文件开头
  11. fp.seek(0)
  12. # 读出文件的全部内容,返回一个字节串
  13. print(fp.read())
  14. fp.seek(0)
  15. # 读取文件
  16. name = pickle.load(fp)
  17. age = pickle.load(fp)
  18. scores = pickle.load(fp)
  19. print(name, ';', age, ';', scores)
  20. ''' b'\x80\x04\x95\n\x00\x00\x00\x00\x00\x00\x00\x8c\x06\xe5\xbc\xa0\xe4\xb8\x89\x94.\x80\x04K\x14.\x80\x04\x95\r\x00\x00\x00\x00\x00\x00\x00]\x94(KAKFKLKPe.'
  21. 张三 ; 20 ; [65, 70, 76, 80]
  22. '''

文件系统操作

os模块

os模块除了提供使用操作系统功能和访问文件系统的简便方法外,还提供了大量文件和目录操作的方法。

1. 文件的重命名

os.rename()方法用于重命名文件或目录,如果dst是一个存在的目录,将抛出OSError。

  1. '''
  2. src:要修改的目录名
  3. dst:修改后的目录名
  4. 返回值:该方法没有返回值
  5. '''
  6. os.rename(src, dst)

2. 文件的删除

os.remove()方法用于删除指定路径的文件。如果指定的路径是一个目录,将抛出OSError。

  1. '''
  2. path:要移除的文件路径
  3. 返回值:该方法没有返回值
  4. '''
  5. os.remove(path)
  1. import os
  2. # 列出当前目录下的文件和子目录
  3. print('目录为:%s' %os.listdir(os.getcwd()))
  4. # 重命名文件
  5. os.rename('test.txt', 'test1.txt')
  6. print('重命名成功!')
  7. print('重命名后目录为:%s' %os.listdir(os.getcwd()))
  8. # 删除文件
  9. os.remove('test1.txt')
  10. print('删除成功!')
  11. print('删除后目录为:%s' %os.listdir(os.getcwd()))

3. 判断是否是文件

  1. '''
  2. 作用:判断path是否是一个文件
  3. 返回值:True或False
  4. '''
  5. os.path.isfile(path)

4. 文件的复制

  1. '''
  2. 作用:将文件src复制到文件或目录dst中
  3. 返回值:返回目标文件名
  4. '''
  5. shutil.copy(src, dst)

5. 检查文件是否存在

  1. '''
  2. 作用:检查文件的存在性
  3. 返回值:返回一个布尔值
  4. '''
  5. os.path.exists(path)

6. 获取绝对路径名

  1. '''
  2. 作用:获取绝对路径名
  3. 返回值:返回path的绝对路径名
  4. '''
  5. os.path.abspath(path)
  1. import os.shutil
  2. # 当前目录下1.py文件不存在
  3. if not os.path.exists(r'.\1.py'):
  4. # 创建1.py文件
  5. with open(r'.\1.py', 'w') as fp:
  6. fp.write("print('hello world!')\n")
  7. # 复制1.py到C:\test目录下
  8. filename = shutil.copy(r'.\1.py', 'C:\\test')
  9. # 打印1.py文件所在的绝对路径
  10. print(os.path.abspath('1.py'))

7. os模块的常用文件操作方法

方法 功能说明
access(path, mode) 按照mode指定的权限访问文件
open(path, flags, mode = 511) 按mode指定的权限打开文件,默认权限为可读、可写、可执行
chmod(path, mode, * ,dir_fd = None) 改变文件的访问权限
remove(path) 删除指定的文件
rename(src, dst) 重命名文件或目录
stat(path) 返回文件的所有属性
fstat(path) 返回打开的文件的所有属性
startfile(filepath[, operation]) 使用关联的应用程序打开指定文件
mkdir(path, mode = 511) 创建目录
makedirs(path1 / path2 …, mode = 511) 创建多级目录
rmdir(path) 删除目录
removedirs(path1 / path2 …) 删除多级目录
listdir(path) 返回指定目录下的文件和目录信息
getcwd() 返回当前工作目录
get_exec_path() 返回可执行文件的搜索路径
chdir(path) 把path设为当前工作目录
walk(top, topdown = True) 遍历目录树,该方法返回一个元组,包括3个元素:所有路径名、所有目录列表与文件列表
sep 当前操作系统所使用的路径分隔符
estsep 当前操作系统所使用的文件扩展名分隔符

8. os.path模块的常用文件操作方法

方法 功能描述
abspath(path) 返回绝对路径
dirname(p) 返回目录的路径
exists(path) 判断文件是否存在
getatime(filename) 返回文件的最后访问时间
getctime(filename) 返回文件的创建时间
getmtime(filename) 返回文件的最后修改时间
getsize(filename) 返回文件的大小
isabs(path) 判断path是否为绝对路径
isdir(path) 判断path是否为目录
idfile(path) 判断path是否为文件
join(path, *paths) 连接两个或多个path
split(path) 对路径进行分割,以列表形式返回
splitext(path) 从路径中分割文件的扩展名
splitdrive(path) 从路径中分割驱动器的名称

在实际开发中,有时需要用程序的方式对文件夹进行一定的操作。比如创建、删除、显示目录内容等,可以通过os和os.path模块提供的方法来完成。

  1. '''
  2. 作用:批量修改文件和目录名的小程序,实现文件和目录名前加上Python-前缀
  3. '''
  4. import os
  5. folderName = './test/'
  6. # 获取指定路径下所有文件和子目录的名字
  7. dirList = os.listdir(folderName)
  8. # 遍历输出所有文件和子目录的名字
  9. for name in dirList:
  10. print('修改前文件名:', name)
  11. newName = 'Python-' + name
  12. print('修改后文件名:', newName)
  13. os.rename(os.path.join(folderName, name), os.path.join(folderName, newName))

shutil模块

shutil模块也属于Python标准库,是对os模块的补充。
shutil模块可以与os模块配合使用,基本可以完成一般的文件系统功能。

使用shutil操作文件与文件夹

shutil模块拥有许多文件(夹)操作的功能,包括复制、移动、重命名、删除、压缩包处理等。

  1. shutil.copyfileobj(fsrc, fdst)

将文件内容从源fsrc文件复制到fdst文件中去,前提是目标文件fdst具备可写权限。
fsrc、fdst参数是打开的文件对象。

  1. shutil.copy(fsrc, destination)

将fsrc文件复制到destination文件夹中,两个参数都是字符串格式。如果destination是一个文件名称,那么它会被用来当作复制后的文件名称,即等于“复制 + 重命名”。

  1. shutil.copytree(source, destination)

复制整个文件夹,将source文件夹中的所有内容复制到destination中,包括source里面的文件、子文件夹都会被复制过去。两个参数都是字符串格式。

  1. shutil.move(source, destination)

将source文件或文件夹移动到destination中。返回值是移动后文件的绝对路径字符串。如果destination指向一个文件夹,那么source文件将被移动到destination中,并且保持其原有名字。如果source指向一个文件,destination指向一个文件,那么source文件将被移动并重命名。

  1. import shutil, os
  2. # 进入文件所在目录
  3. os.chdir('C:\\test')
  4. shutil.copy('scores.txt', 'sample1.txt')

读写常见文件格式

CSV文件
Excel文件
Json文件

CSV文件

CSV格式属于电子表格文件,其中数据存储在单元格内。每个单元格按照行和列结构进行组织。
CSV中的每一行代表一个观察,通常称为一条记录。每个记录可以包含一个或多个由逗号分隔的字段。如果文件中不使用逗号分隔,而是使用制表符进行分隔,这样的文件格式称为TSV(制表符分隔符)文件格式。

csv文件的读取和写入

csv(comma separated values,逗号分隔值)文件是一种用来存储表格数据(数字和文本)的纯文本格式文件,文档的内容是由“,”分隔的一列列的数据构成,它可以被导入各种电子表格和数据库中。纯文本意味着该文件是一个字符序列。
在csv文件中,数据“栏”(数据所在列,相当于数据库的字段)以逗号分隔,可允许程序通过读取文件为数据重新创建正确的栏结构(如把两个数据栏的数据组合在一起),并在每次遇到逗号时开始新的一栏。
csv文件由任意数目的记录组成,记录间以某种换行符间隔,一行即为数据表的一行;每条记录由字段组成,字段间的分隔符最常见的是逗号或制表符。
可使用Word、记事本、Excel等方式打开csv文件。
创建csv文件的方法有很多,最常用的方法是用电子表格创建,如Microsoft Excel。在Microsoft Excel中,选择“文件”>“另存为”,然后在“文件类型”下拉选择框中选择“CSV(逗号分隔)(*.csv)”,然后点击保存即创建了一个csv格式的文件。
Python的csv模块提供了多种读取和写入csv格式文件的方法。
本节基于consumer.csv文件,其内容为:

客户年龄 平均每次消费金额 平均消费周期
23 318 10
22 147 13
24 172 17
27 194 57
  1. csv文件的读取csv.reader(csvfile, dialect = 'excel')

参数说明:

  • csvfile:可以使文件(file)对象或者列表(list)对象,如果csvfile是文件对象,要求该文件要以newline = ''的方式打开,否则两行之间会空一行。
  • dialect:编码风格,默认为excel的风格,也就是用逗号(,)分隔,dialect方式也支持自定义,通过调用register_dialect方法来注册。

第七章 文件操作 - 图2

  1. import csv, shutil, os
  2. # 进入文件所在目录
  3. os.chdir('C:/bigdata/juputer code')
  4. with open('consumer.csv', newline = '') as csvfile:
  5. # 返回的是迭代类型
  6. spamreader = csv.reader(csvfile)
  7. for row in spamreader:
  8. # 以逗号连接各字段
  9. print(','.join(row))
  10. # 文件指针移动到文件开始
  11. csvfile.seek(0)
  12. for row in spamreader:
  13. print(row)
  1. csv文件的写入csv.writer(csvfile, dialect = 'excel', **fmtpatams)

参数说明:

  • csvfile:可以使文件(file)对象或列表(list)对象。
  • dialect:编码风格,默认为excel的风格,也就是用逗号(,)分隔,dialect方式也支持自定义,通过调用register_dialect方法来注册。

csv。writer()所生成csv.writer文件对象支持一下写入csv文件的方法:

  • writerow(row):写入一行数据
  • writerows(rows):写入多行数据

第七章 文件操作 - 图3

  1. import csv, shutil, os
  2. # 进入文件所在目录
  3. os.chdir('C:/bigdata/jupyter code')
  4. with open('consumer.csv', 'w', newline = '') as csvfile:
  5. # 写入的数据将覆盖consumer.csv文件
  6. # 生成csv.writer文件对象
  7. spamwriter = csv.writer(csvfile)
  8. # 写入一行数据
  9. spamwriter.writerow(['55', '555', '55'])
  10. spamwriter.writerows([('35', '355', '35'), ('18', '188', '18')])
  11. #重新打开文件
  12. with open('consumer.csv', newline = '') as csvfile:
  13. sapmreader = csv.reader(csvfile)
  14. # 输出数据文件
  15. for row in spamreader:
  16. print(row)
  1. import csv
  2. def csv_write(path, data):
  3. with open(path, 'w', encoding = 'utf-8', newline = '') as f:
  4. writer = csv.writer(f, dialect = 'excel')
  5. for row in data:
  6. writer.writerow(row)
  7. return True
  8. data = [
  9. ['姓名','年龄', '身高(cm)', '体重(kg)'],
  10. ['张三', 38, '176cm', '75'],
  11. ['李四', 25, '160cm', '46'],
  12. ['王五', 28, '170cm', '62']
  13. ]
  14. csv_write('persons.csv', data)

很多情况下,读取csv数据时,往往先把csv文件中的数据读成字典的形式,即为读出的每条记录中的数据添加一条说明性的关键词,这样便于理解。

  1. 将csv文件读取为字典csv.DictReader(csvfile, fieldnames = None, dialect = 'excel')

作用:

  • 返回一个csv.DictReader对象,可以将读取的信息映射为字典,其关键字由可选参数fieldnames来指定。

参数说明:

  • csvfile:可以是文件(file)对象或列表(list)对象。
  • fieldnames:是一个序列,用于为输出的数据指定字典关键字,如果没有指定,则以第一行的各字段名作为字典关键字。
  • dialect:编码风格,默认为excel的风格。
    1. import csv
    2. with open('consumer.csv', 'r') as csvfile:
    3. dict_reader = csv.DictReader(csvfile)
    4. for row in dict_reader:
    5. print(row)
  1. 将字典形式的记录数据写入csv文件csv.DictWriter(csvfile, fieldnames, dialect = 'excel')

说明:操作方法与参数含义与dictReader()类似

  1. import csv
  2. dict_record = [
  3. {'客户年龄':23, '平均每次消费金额':318, '平均消费周期':10},
  4. {'客户年龄':22, '平均每次消费金额':147, '平均消费周期':13}
  5. ]
  6. keys = ['客户年龄', '平均每次消费金额', '平均消费周期']
  7. with open('consumer1.csv', 'w+', newline = '') as csvfile:
  8. dictwriter = csv.DictWriter(csvfile, fieldnames = keys)
  9. # 若直接写入会导致没有数据名,先执行writeheader()将头文件写入
  10. # writeheader()没有参数,建立对象dictwriter时已指定fieldnames
  11. dictwriter.writeheader()
  12. for item in dict_record:
  13. dictwriter.writerow(item)
  1. import csv
  2. print('以csv.DictReader()读取consumer1.csv:')
  3. with open('consumer1.csv', 'r') as csvfile:
  4. reader = csv.DictReader(csvfile)
  5. for row in reader:
  6. print(row)

csv文件的格式化参数

创建csv.reader或csv.writer对象时,可以指定csv文件格式化参数。
csv文件格式化参数表:

参数 描述
delimiter 单字词,默认值为“,”,用来分割字段。
doublequote 如果为True(默认值),字符串中的双引号用””表示,若为False,使用转义字符escapechar指定的字符。
escapechar 转义字符,一个单词串,当quoting被设置成QUOTE_NONE、doublequote被设置为False,被writer用来转义delimiter。
lineterminator 被writer用来换行,默认为’\r\n’。
quotechar 单字串,用于包含特殊符号的引用字段,默认值为’”‘。

自定义dialect

dialect用来指定csv文件的编码风格,默认为excel的风格,也就是用逗号“,”分隔,dialect支持自定义,即通过调用register_dialect方法来注册csv文件的编码风格。
csv.register_dialect(name[, dialect], **fmtparams)
作用:

  • 这个函数是用来自定义dialect的。

参数说明:

  • name:所自定义的dialect的名字,比如默认的是’excel’,你可以定义成’mydialect’。
  • delimiter:分隔符,默认的是逗号。
  • fmtparams:用于指定特定格式,以覆盖dialect中的格式。
    1. import csv
    2. # 自定义了一个命名为mydialect的dialect
    3. # 参数只设置了delimiter和quoting这两个,其他的仍然采用默认值
    4. # 其中以':'为分隔符
    5. # quoting用于指定使用双引号的规则,QUOTE_ALL(全部)
    6. csv.register_dialect('mydialect', delimiter = ':',quoting = csv.QUOTE_ALL)
    7. with open('consumer.csv', newline = '') as f:
    8. spamreader = csv.reader(f, dialect = 'mydialect')
    9. for row in spamreader:
    10. print(row)

    Excel文件

    Excel是常见的电子表格文件,常用openpyxl模块读写Excel表格中的数据。
    在安装jupyter notebook时已经安装好了openpyxl模块。
    可在编辑器中输入并运行conda list查看这个模块。
    一个Excel文档也称为一个工作簿(workbook),每个工作簿里可以有多个工作表(worksheet),当前打开的工作表又叫活动表。
    每个工作表里有行和列,特定的行与列相交的放个称为单元格(cell)。
    在进行Excel文件读写时,应首先进行工作簿(’workbook’)的获取,然后从工作簿中处理表单(’sheet’)。进入表单处理环节后,即可按行或列进行数据的读取,或是按单元格的方式处理数据。
    Excel文件写入的步骤:
    第七章 文件操作 - 图4 ```python import openpyxl wb = openpyxl.Workbook() sheet = wb.active sheet.title = ‘student’ rows = [[‘学号’, ‘姓名’, ‘班级’], [‘201401’, ‘张三’, ‘14班’], [‘201302’, ‘李四’, ‘14班’]] for i in rows: sheet.append(i) print(rows) wb.save(‘student.xlsx’)

‘’’ [[‘学号’, ‘姓名’, ‘班级’], [‘201401’, ‘张三’, ‘14班’], [‘201302’, ‘李四’, ‘14班’]] ‘’’

  1. Excel文件读取的步骤:<br />![](https://cdn.nlark.com/yuque/0/2022/jpeg/25684216/1653313430595-5f66b156-2936-45eb-abeb-9adb256e7cd9.jpeg)
  2. ```python
  3. import openpyxl
  4. wb = openpyxl.load_workbook('student1.xlsx')
  5. sheet = wb['student']
  6. columns = sheet.max_column
  7. rows = sheet.max_row
  8. row_data = []
  9. for i in range(1, rows + 1):
  10. for j in range(1, columns + 1):
  11. cell_value = sheet.cell(i, j).value
  12. row_data.append(cell_value)
  13. print(row_data)

Json文件

Json是一种使用广泛的轻量级数据格式,它可以将JavaScript对象中表示的一组数据转换为字符串,常用于数据的存储和交换。
从数据格式来看,Python中的字典类型与Json数据格式很接近。

  1. d = {
  2. 'a':123,
  3. 'b':{
  4. 'x':['A', 'B', 'C']
  5. },
  6. 'c':True,
  7. 'd':Nune
  8. }
  1. d = {
  2. "a":123,
  3. "b":{
  4. "x":["A", "B", "C"]
  5. },
  6. "c":true,
  7. "d":null
  8. }

Python字典类型数据与Json类型数据的区别:

  • Python中的字符串允许单引号和双引号,而Json数据中要求必须是双引号
  • 二者在布尔类型、空值的处理方面也有区别

Python标准库中的json模块可以直接将Python数据类型转化为Json。

  1. import json
  2. d = {}
  3. d['a'] = 123
  4. d['b'] = {'x':['A', 'B', 'C']}
  5. d['c'] = True
  6. d['d'] = None
  7. print(d)
  8. # 转换成Json字符串
  9. json_str = json.dumps(d)
  10. print(json_str)
  11. # 将Json转换成Python字典类型
  12. e = json.loads(json_str)
  13. print(e)
  14. '''
  15. {'a': 123, 'b': {'x': ['A', 'B', 'C']}, 'c': True, 'd': None}
  16. {"a": 123, "b": {"x": ["A", "B", "C"]}, "c": true, "d": null}
  17. {'a': 123, 'b': {'x': ['A', 'B', 'C']}, 'c': True, 'd': None}
  18. '''

总结

pickle模块可用于对二进制数据进行序列化和反序列化
os、os.path、shutil的文件操作系统方法
CSV文件、Excel文件和Json文件的读写方法