代码改变世界

python

2019-04-10 14:16  zYaMei  阅读(298)  评论(2编辑  收藏  举报
# 文件操作
# 1、有一个jsonline格式的文件file.txt大小约为10k
def get_lines():
    with open('file.txt', 'rb') as f:
        return f.readlines()
if __name__ == '__main__':
    for line in get_lines():
        print(line)

# 如果要处理一个大小为10G的文件,但是内存只有4G,如果在只修改get_lines 函数而其他代码保持不变的情况下,应该如何实现?需要考虑的问题都有那些?
def get_lines():
    with open('file.txt', 'rb') as f:
        for line in f:
            yield line

# 具体实现方法
from mmap import mmap

def get_lines(fp):
    with open(fp, 'r+') as f:
        m = mmap(f.fileno(), 0)
        temp = 0
        for i, char in enumerate(m):
            if char == b"\n":
                yield m[temp:i+1].decode()
                temp = i + 1
if __name__ == '__main__':
    for line in get_lines('huge_file'):
        print(line)

需要考虑的问题有:内存只有4G无法一次性读入10G文件,需要分批读入。分批读入数据要记录每次读入数据的位置,每次读取数据的大小,太小会在读取操作花费太多时间。

文件对象的访问模式

  • r 以读方式打开
  • w 以写方式打开
  • a 以追加模式打开
  • rU 以读方式打开,同时提供通用换行符
  • r+、w+、a+ 以读写模式打开
  • rb 以二进制读模式打开
  • wb 以二进制写模式打开
  • ab 以二进制追加模式打开

read()/readline()/readlines()

  • read():读取整个文件,将文件内容放到一个字符串变量中,包括换行符。如果文件太大,大于内存时,无法使用。
  • readline():每次读取一行;返回的是一个字符串对象,包括行结束符。比readlines()慢得多。
  • readlines():一次性读取整个文件,自动将文件内容分析成一个行的列表。

mmap模块

mmap是一种虚拟内存映射文件的方法,即可以将一个文件或者其它对象映射到进程的地址空间,实现文件磁盘地址和进程虚拟地址空间中一段虚拟地址的--对映关系。普通文件被映射到虚拟地址空间后,程序可以像操作内存一样操作文件,可以提高访问效率,适合处理超大文件。