Python之mmap模块的使用

 mmap模块的作用

  建立一个文件的内在映射将使用操作系统内存来直接访问文件系统上的数据,而不是使用常规的I/O函数访问数据。内存映射通常可以提高I/O性能,因为使用映射时,不需要对每个访问都建立一个单独的系统调用,
也不需要在缓冲区之间复制数据;实际上,内核和用户应用都能直接访问内存。

 准备测试的内容

Lorem ipsum dolor sit amet, consectetuer adipiscing elit.
Donec egestas, enim et consectetuer ullamcorper, lectus ligula rutrum leo,
a elementum elit tortor eu quam. Duis tincidunt nisi ut ante. Nulla
facilisi. Sed tristique eros eu libero. Pellentesque vel
arcu. Vivamus purus orci, iaculis ac, suscipit sit amet, pulvinar eu,
lacus. Praesent placerat tortor sed nisl. Nunc blandit diam egestas
dui. Pellentesque habitant morbi tristique senectus et netus et
malesuada fames ac turpis egestas. Aliquam viverra fringilla
leo. Nulla feugiat augue eleifend nulla. Vivamus mauris. Vivamus sed
mauris in nibh placerat egestas. Suspendisse potenti. Mauris
massa. Ut eget velit auctor tortor blandit sollicitudin. Suspendisse
imperdiet justo.
lorem.txt

 1、mmap模块的读取

import mmap

with open('lorem.txt', 'r') as rf:
    with mmap.mmap(rf.fileno(),
                   0,
                   access=mmap.ACCESS_READ) as m:
        print('读取前10个字节:', m.read(10))
        print('切片获取前10个字节', m[:10])
        print('读取切片后10个字节', m.read(10))
mmap_read.py

 测试效果

读取前10个字节: b'Lorem ipsu'
切片获取前10个字节 b'Lorem ipsu'
读取切片后10个字节 b'm dolor si'

 2、mmap模块切片写入,同步修改文本内容

import shutil
import mmap

# 拷贝多一个份文件
shutil.copyfile('lorem.txt', 'lorem_copy.txt')

word = b'consectetuer'

# 字符串反转
reversed = word[::-1]

print('原来的字符串', word)
print('反转后的字符串', reversed)

with open('lorem_copy.txt', 'r+') as f:
    with mmap.mmap(f.fileno(), 0) as m:
        print('之前的mmap数据\n{}'.format(m.readline().rstrip()))
        m.seek(0)  # 指针回至0
        loc = m.find(word)
        m[loc:loc + len(word)] = reversed
        m.flush()

        m.seek(0)  # 指针回至0
        print('查看替换之后的mmap数据\n{}'.format(m.readline().rstrip()))
        f.seek(0)
        print('查看替换之后的文本数据\n{}'.format(f.readline().rstrip()))
mmap_write_slice.py

 测试效果

原来的字符串 b'consectetuer'
反转后的字符串 b'reutetcesnoc'
之前的mmap数据
b'Lorem ipsum dolor sit amet, consectetuer adipiscing elit.'
查看替换之后的mmap数据
b'Lorem ipsum dolor sit amet, reutetcesnoc adipiscing elit.'
查看替换之后的文本数据
Lorem ipsum dolor sit amet, reutetcesnoc adipiscing elit.

 3、mmap模块切片写入,不修改文本内容

import shutil
import mmap

# 拷贝多一个份文件
shutil.copyfile('lorem.txt', 'lorem_copy.txt')

word = b'consectetuer'

# 字符串反转
reversed = word[::-1]

print('原来的字符串', word)
print('反转后的字符串', reversed)

with open('lorem_copy.txt', 'r+') as f:
    with mmap.mmap(f.fileno(), 0,
                   access=mmap.ACCESS_COPY) as m:
        print('之前的mmap数据\n{}'.format(m.readline().rstrip()))
        m.seek(0)  # 指针回至0
        loc = m.find(word)
        m[loc:loc + len(word)] = reversed
        m.flush()

        m.seek(0)  # 指针回至0
        print('查看替换之后的mmap数据\n{}'.format(m.readline().rstrip()))
        f.seek(0)
        print('查看替换之后的文本数据\n{}'.format(f.readline().rstrip()))
mmap_write_copy.py

 

测试效果

原来的字符串 b'consectetuer'
反转后的字符串 b'reutetcesnoc'
之前的mmap数据 b'Lorem ipsum dolor sit amet, consectetuer adipiscing elit.'
查看替换之后的mmap数据 b'Lorem ipsum dolor sit amet, reutetcesnoc adipiscing elit.'

查看替换之后的文本数据 Lorem ipsum dolor sit amet, consectetuer adipiscing elit.

 

4、mmap模块与re模块结合,查询内容并且替换内容 

import re
import mmap

pattern = re.compile(rb'(\.\W+)?([^.]?nulla[^.]*?\.)',
                     re.DOTALL | re.IGNORECASE | re.MULTILINE)

with open('lorem.txt', 'r') as rf:
    with mmap.mmap(rf.fileno(), 0, access=mmap.ACCESS_READ) as m:
        for match in pattern.findall(m):
            print(match[1].replace(b'\n', b' '))
mmap_regex.py

 

 测试效果

b'Nulla\r facilisi.'
b'Nulla feugiat augue eleifend nulla.'
posted @ 2020-05-07 16:38  小粉优化大师  阅读(1472)  评论(0编辑  收藏  举报