Python字符串处理优化

Python字符串处理优化,python,string,file-io,Python,String,File Io,所以最近我一直在制作一个python脚本,用于从大型文本文件(>1GB)中提取数据。问题基本上归结为从文件中选择文本行,然后从某个数组中搜索字符串(该数组中最多可以有1000个字符串)。这里的问题是,我必须找到字符串的一个特定匹配项,并且该字符串可能在该文件中出现无限次。此外,还需要一些解码和编码,这会进一步降低脚本的速度。 代码如下所示: strings = [a for a in open('file.txt')] with open("er.txt", "r") as f: fo

所以最近我一直在制作一个python脚本,用于从大型文本文件(>1GB)中提取数据。问题基本上归结为从文件中选择文本行,然后从某个数组中搜索字符串(该数组中最多可以有1000个字符串)。这里的问题是,我必须找到字符串的一个特定匹配项,并且该字符串可能在该文件中出现无限次。此外,还需要一些解码和编码,这会进一步降低脚本的速度。 代码如下所示:

strings = [a for a in open('file.txt')]

with open("er.txt", "r") as f:
    for chunk in f:
        for s in strings
            #do search, trimming, stripping ..
我的问题是: 有没有办法优化这一点?我尝试了多处理,但它没有什么帮助(或者至少是我实现它的方式)。这里的问题是,这些块操作不是独立的,
strings
list可能在其中一个过程中被更改。
任何优化都会有所帮助(字符串搜索算法、文件读取等)。我尽可能多地考虑循环中断,但它仍然运行得非常慢

考虑调用外部进程(grep等)以加快处理速度并减少必须在Python中处理的数据量

另一种方法是使用已编译的正则表达式过滤或预过滤数据,因为这样内部循环使用标准库的优化代码


对于热内部循环,您也可以尝试Cython或类似的方法,请参见,例如,有关详细信息。

如果您能够准确地知道字符串是如何以二进制(ASCII,UTF-8)编码的,您可以一次将整个文件存储到内存中;它的行为与通过
file.read()
获得的大型
bytearray/bytes
(或Python 2中的
str
)完全相同;然后这样的
mmap
对象可以通过
str
正则表达式(Python 2)或
bytes
正则表达式(Python 3)进行搜索

mmap
是许多操作系统上最快的解决方案,因为只读映射意味着操作系统可以在页面准备就绪时自由映射页面;不需要交换空间,因为数据由文件支持。操作系统还可以通过零拷贝直接映射缓冲区缓存中的数据,从而实现对裸读的双赢

例如:

import mmap
import re

pattern = re.compile(b'the ultimate answer is ([0-9]+)')
with open("datafile.txt", "rb") as f:
    # memory-map the file, size 0 means whole file
    mm = mmap.mmap(f.fileno(), 0, prot=mmap.PROT_READ)

    # PROT_READ only on *nix as the file is not writable
    for match in pattern.finditer(mm):
        # process match
        print("The answer is {}".format(match.group(1).decode('utf8')))

    mm.close()
现在,如果
datafile.txt
包含以下文本:

the ultimate answer is 42
在1GB数据量范围内,该程序将是最快的python解决方案之一:

The answer is 42
请注意,还接受可用于限制尝试匹配范围的
start
end
参数



正如所指出的,这需要1GB的可用虚拟地址空间来映射一个1GB文件(但不一定是1GB的RAM),这在32位进程中可能很困难,但几乎可以肯定在64位操作系统和CPU上是“没有问题”的。在32位进程上,这种方法仍然有效,但您需要将大文件映射到更小的块中——因此,现在操作系统和处理器的位真的很重要。

Wow。这是一个惊人的工作:你摇滚!!请注意,您必须拥有足够大的可用连续地址空间块。在x32中,获得1GB的数据块是一个问题,这是一个活生生的例子。是的,如果您正在进行大数据分析,最好使用64位计算机、64位操作系统和64位Python:)